@vuu-ui/vuu-filters 0.9.2 → 0.9.3
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/cjs/FilterModel.js +1 -1
- package/cjs/FilterModel.js.map +1 -1
- package/cjs/custom-filters/CustomFilters.js.map +1 -1
- package/cjs/custom-filters/filterBarFocusManagement.js.map +1 -1
- package/cjs/custom-filters/useCustomFilters.js.map +1 -1
- package/cjs/custom-filters/useFilterState.js.map +1 -1
- package/cjs/filter-bar/FilterBar.js.map +1 -1
- package/cjs/filter-bar/useFilterBar.js.map +1 -1
- package/cjs/filter-clause/ColumnPicker.js.map +1 -1
- package/cjs/filter-clause/ExpandoCombobox.js.map +1 -1
- package/cjs/filter-clause/FilterClause.js.map +1 -1
- package/cjs/filter-clause/OperatorPicker.js.map +1 -1
- package/cjs/filter-clause/filterClauseFocusManagement.js.map +1 -1
- package/cjs/filter-clause/operator-utils.js.map +1 -1
- package/cjs/filter-clause/useFilterClause.js.map +1 -1
- package/cjs/filter-clause/value-editors/FilterClauseValueEditor.js.map +1 -1
- package/cjs/filter-clause/value-editors/FilterClauseValueEditorDate.js.map +1 -1
- package/cjs/filter-clause/value-editors/FilterClauseValueEditorNumber.js.map +1 -1
- package/cjs/filter-clause/value-editors/FilterClauseValueEditorText.js.map +1 -1
- package/cjs/filter-editor/FilterClauseCombinator.js.map +1 -1
- package/cjs/filter-editor/FilterEditor.js.map +1 -1
- package/cjs/filter-editor/useFilterEditor.js.map +1 -1
- package/cjs/filter-pill/FilterPill.js.map +1 -1
- package/cjs/filter-pill/FilterPillMenuOptions.js.map +1 -1
- package/cjs/filter-pill/filterAsReactNode.js.map +1 -1
- package/cjs/filter-pill/getFilterLabel.js.map +1 -1
- package/cjs/filter-pill/getFilterTooltipText.js.map +1 -1
- package/cjs/filter-utils.js.map +1 -1
- package/cjs/inline-filter/InlineFilter.js.map +1 -1
- package/cjs/inline-filter/useInlineFilter.js.map +1 -1
- package/cjs/quick-filters/QuickFilters.js.map +1 -1
- package/cjs/quick-filters/useQuickFilters.js.map +1 -1
- package/esm/FilterModel.js +1 -1
- package/esm/FilterModel.js.map +1 -1
- package/esm/custom-filters/CustomFilters.js.map +1 -1
- package/esm/custom-filters/filterBarFocusManagement.js.map +1 -1
- package/esm/custom-filters/useCustomFilters.js.map +1 -1
- package/esm/custom-filters/useFilterState.js.map +1 -1
- package/esm/filter-bar/FilterBar.js.map +1 -1
- package/esm/filter-bar/useFilterBar.js.map +1 -1
- package/esm/filter-clause/ColumnPicker.js.map +1 -1
- package/esm/filter-clause/ExpandoCombobox.js.map +1 -1
- package/esm/filter-clause/FilterClause.js.map +1 -1
- package/esm/filter-clause/OperatorPicker.js.map +1 -1
- package/esm/filter-clause/filterClauseFocusManagement.js.map +1 -1
- package/esm/filter-clause/operator-utils.js.map +1 -1
- package/esm/filter-clause/useFilterClause.js.map +1 -1
- package/esm/filter-clause/value-editors/FilterClauseValueEditor.js.map +1 -1
- package/esm/filter-clause/value-editors/FilterClauseValueEditorDate.js.map +1 -1
- package/esm/filter-clause/value-editors/FilterClauseValueEditorNumber.js.map +1 -1
- package/esm/filter-clause/value-editors/FilterClauseValueEditorText.js.map +1 -1
- package/esm/filter-editor/FilterClauseCombinator.js.map +1 -1
- package/esm/filter-editor/FilterEditor.js.map +1 -1
- package/esm/filter-editor/useFilterEditor.js.map +1 -1
- package/esm/filter-pill/FilterPill.js.map +1 -1
- package/esm/filter-pill/FilterPillMenuOptions.js.map +1 -1
- package/esm/filter-pill/filterAsReactNode.js.map +1 -1
- package/esm/filter-pill/getFilterLabel.js.map +1 -1
- package/esm/filter-pill/getFilterTooltipText.js.map +1 -1
- package/esm/filter-utils.js.map +1 -1
- package/esm/inline-filter/InlineFilter.js.map +1 -1
- package/esm/inline-filter/useInlineFilter.js.map +1 -1
- package/esm/quick-filters/QuickFilters.js.map +1 -1
- package/esm/quick-filters/useQuickFilters.js.map +1 -1
- package/package.json +13 -15
- package/types/custom-filters/CustomFilters.d.ts +1 -1
- package/types/filter-bar/FilterBar.d.ts +1 -1
- package/types/filter-bar/FilterBarMenu.d.ts +1 -2
- package/types/filter-clause/FilterClause.d.ts +1 -1
- package/types/filter-clause/FilterMenu.d.ts +1 -2
- package/types/filter-clause/filterClauseTypes.d.ts +3 -3
- package/types/filter-clause/value-editors/FilterClauseValueEditor.d.ts +4 -5
- package/types/filter-clause/value-editors/FilterClauseValueEditorDate.d.ts +1 -2
- package/types/filter-editor/FilterClauseCombinator.d.ts +1 -1
- package/types/filter-editor/FilterEditor.d.ts +1 -1
- package/types/filter-pill/FilterPill.d.ts +1 -2
- package/types/filter-pill-menu/FilterPillMenu.d.ts +1 -2
- package/types/inline-filter/InlineFilter.d.ts +1 -1
- package/types/inline-filter/useInlineFilter.d.ts +0 -1
- package/types/quick-filters/QuickFilters.d.ts +1 -1
package/cjs/FilterModel.js
CHANGED
|
@@ -11,7 +11,7 @@ var __publicField = (obj, key, value) => __defNormalProp(obj, typeof key !== "sy
|
|
|
11
11
|
var __accessCheck = (obj, member, msg) => member.has(obj) || __typeError("Cannot " + msg);
|
|
12
12
|
var __privateGet = (obj, member, getter) => (__accessCheck(obj, member, "read from private field"), getter ? getter.call(obj) : member.get(obj));
|
|
13
13
|
var __privateAdd = (obj, member, value) => member.has(obj) ? __typeError("Cannot add the same private member more than once") : member instanceof WeakSet ? member.add(obj) : member.set(obj, value);
|
|
14
|
-
var __privateSet = (obj, member, value, setter) => (__accessCheck(obj, member, "write to private field"),
|
|
14
|
+
var __privateSet = (obj, member, value, setter) => (__accessCheck(obj, member, "write to private field"), member.set(obj, value), value);
|
|
15
15
|
var _filterClause, _isValid, _children, _isValid2, _op;
|
|
16
16
|
const hasValues = ({ values }) => Array.isArray(values) && values.length > 0;
|
|
17
17
|
const isValidFilterClause = (filterClause) => {
|
package/cjs/FilterModel.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"FilterModel.js","sources":["../src/FilterModel.ts"],"sourcesContent":["import {\n Filter,\n FilterClause,\n FilterClauseOp,\n FilterCombinatorOp,\n MultiClauseFilter,\n MultiValueFilterClause,\n SingleValueFilterClause,\n} from \"@vuu-ui/vuu-filter-types\";\nimport {\n EventEmitter,\n isMultiClauseFilter,\n isMultiValueFilter,\n isSingleValueFilter,\n} from \"@vuu-ui/vuu-utils\";\n\nexport type FilterStatusChangeHandler = (isValid: boolean) => void;\nexport type FilterChangeHandler = (\n filter: Partial<Filter>,\n isValid: boolean,\n) => void;\nexport type FilterClauseChangeHandler = (\n filter: Partial<FilterClause>,\n isValid: boolean,\n) => void;\n\nconst hasValues = ({ values }: MultiValueFilterClause) =>\n Array.isArray(values) && values.length > 0;\n\nconst isValidFilterClause = (\n filterClause: Partial<FilterClause>,\n): filterClause is FilterClause => {\n if (filterClause.op === undefined || filterClause.column === undefined) {\n return false;\n } else if (isMultiValueFilter(filterClause)) {\n return hasValues(filterClause);\n } else if (isSingleValueFilter(filterClause)) {\n return filterClause.value !== undefined && filterClause.value !== \"\";\n }\n throw Error(\"isValidFilterClause should never reach this far\");\n};\n\nconst isValidFilter = (filter?: Filter): boolean => {\n if (filter === undefined) {\n return false;\n } else if (isMultiClauseFilter(filter)) {\n return filter.filters.every(isValidFilter);\n } else {\n return isValidFilterClause(filter);\n }\n};\n\nconst isValidFilterModel = (filterModel: FilterModel) => {\n if (filterModel.isMultiClauseFilter) {\n return filterModel.filterClauses.every((f) => f.isValid);\n } else {\n return (\n filterModel.filterClauses.length === 1 &&\n filterModel.filterClauses[0].isValid\n );\n }\n};\n\nexport type FilterClauseModelEvents = {\n filterClause: FilterClauseChangeHandler;\n isValid: FilterStatusChangeHandler;\n};\n\nexport type FilterModelEvents = {\n // TODO do we need an incomplate filter type\n filter: FilterChangeHandler;\n isValid: FilterStatusChangeHandler;\n};\n\nexport class FilterClauseModel extends EventEmitter<FilterClauseModelEvents> {\n #filterClause: Partial<FilterClause>;\n #isValid: boolean;\n constructor(filterClause: Partial<FilterClause>) {\n super();\n this.#filterClause = filterClause;\n this.#isValid = isValidFilterClause(filterClause);\n }\n get isValid() {\n return this.#isValid;\n }\n\n private setIsValid(isValid: boolean) {\n this.#isValid = isValid;\n this.emit(\"isValid\", isValid);\n }\n\n get column() {\n return this.#filterClause.column;\n }\n\n set column(column: undefined | string) {\n // TODO set op, value to empty\n this.#filterClause = {\n column,\n };\n\n const isValid = isValidFilterClause(this.#filterClause);\n this.emit(\"filterClause\", this.#filterClause, isValid);\n if (isValid !== this.#isValid) {\n this.setIsValid(isValid);\n }\n }\n\n get op() {\n return this.#filterClause.op;\n }\n\n setOp(op: undefined | FilterClauseOp) {\n this.#filterClause = {\n ...this.#filterClause,\n op,\n };\n const isValid = isValidFilterClause(this.#filterClause);\n this.emit(\"filterClause\", this.#filterClause, isValid);\n if (isValid !== this.#isValid) {\n this.setIsValid(isValid);\n }\n }\n\n setValue(\n value:\n | undefined\n | string\n | string[]\n | number\n | number[]\n | boolean\n | boolean[],\n isFinal = true,\n ) {\n if (isSingleValueFilter(this.#filterClause)) {\n this.#filterClause = {\n ...this.#filterClause,\n value,\n } as SingleValueFilterClause;\n } else if (Array.isArray(value)) {\n this.#filterClause = {\n ...this.#filterClause,\n values: value,\n } as MultiValueFilterClause;\n }\n\n const isValid = isValidFilterClause(this.#filterClause);\n if (isValid !== this.#isValid) {\n this.setIsValid(isValid);\n }\n if (isFinal) {\n this.emit(\"filterClause\", this.#filterClause, isValid);\n }\n }\n\n asFilter(throwIfInvalid = true): FilterClause {\n if (throwIfInvalid && !this.#isValid) {\n throw Error(\"Invalid filter model cannot be returned as Filter\");\n }\n return this.#filterClause as FilterClause;\n }\n}\n\nexport class FilterModel extends EventEmitter<FilterModelEvents> {\n #children: FilterClauseModel[] = [];\n #isValid: boolean;\n #op?: FilterCombinatorOp;\n\n constructor(filter?: Filter) {\n super();\n if (isMultiClauseFilter(filter)) {\n this.#op = filter.op;\n filter.filters.forEach((f) => this.addFilterClause(f as FilterClause));\n } else if (filter) {\n this.addFilterClause(filter);\n } else {\n this.addNewFilterClause();\n }\n\n this.#isValid = isValidFilter(filter);\n }\n get isValid() {\n return this.#isValid;\n }\n\n private setIsValid(isValid: boolean) {\n this.#isValid = isValid;\n this.emit(\"isValid\", isValid);\n }\n\n addNewFilterClause(operator?: FilterCombinatorOp) {\n const count = this.#children.length;\n if (!operator && !this.#op && count === 1) {\n this.#op = \"and\";\n } else if (operator && !this.#op && count === 1) {\n this.#op = operator;\n } else if (operator && this.#op && operator !== this.#op) {\n throw Error(\n \"FilterModel: use setOp to change the Filter combinator operator\",\n );\n }\n\n const filterClauseModel = new FilterClauseModel({});\n filterClauseModel.on(\"isValid\", this.onFilterClauseStatusChange);\n filterClauseModel.on(\"filterClause\", this.onFilterClauseChange);\n this.#children.push(filterClauseModel);\n this.setIsValid(false);\n }\n\n addFilterClause(filterClause: Partial<FilterClause> = {}) {\n const filterClauseModel = new FilterClauseModel(filterClause);\n filterClauseModel.on(\"isValid\", this.onFilterClauseStatusChange);\n filterClauseModel.on(\"filterClause\", this.onFilterClauseChange);\n this.#children.push(filterClauseModel);\n }\n\n removeFilterClause(filterClause: FilterClauseModel) {\n // We never allow the last clause to be removed\n if (this.isMultiClauseFilter) {\n const doomedFilter = this.filterClauses.indexOf(filterClause);\n if (doomedFilter !== -1) {\n this.filterClauses.splice(doomedFilter, 1);\n // If we're down the the last clause, we are no longer multi-clause\n if (this.filterClauses.length === 1) {\n this.#op = undefined;\n }\n this.checkValidStatus();\n }\n }\n }\n\n checkValidStatus() {\n const nowValid = isValidFilterModel(this);\n\n if (nowValid !== this.#isValid) {\n this.setIsValid(nowValid);\n }\n }\n\n onFilterClauseChange: FilterChangeHandler = () => {\n this.emit(\"filter\", this.asFilter(false), this.#isValid);\n };\n\n onFilterClauseStatusChange = (isValid: boolean) => {\n if (!isValid && this.#isValid) {\n this.setIsValid(false);\n } else {\n this.checkValidStatus();\n }\n };\n\n getFilterClause(index: number) {\n return this.#children[index];\n }\n\n get op() {\n return this.#op;\n }\n\n setOp(op: FilterCombinatorOp) {\n this.#op = op;\n this.emit(\"filter\", this.asFilter(false), this.#isValid);\n }\n\n get filterClauses() {\n return this.#children;\n }\n\n get isMultiClauseFilter() {\n return this.#op === \"and\" || this.#op === \"or\";\n }\n\n asFilter(throwIfInvalid = true): Filter {\n if (throwIfInvalid && !this.#isValid) {\n throw Error(\"Invalid filter model cannot be returned as Filter\");\n }\n if (this.#op === \"and\" || this.#op === \"or\") {\n return {\n op: this.#op,\n filters: this.#children.map((f) => f.asFilter(throwIfInvalid)),\n } as MultiClauseFilter;\n } else {\n return this.#children[0].asFilter(throwIfInvalid);\n }\n }\n}\n"],"names":["_isValid","isMultiValueFilter","isSingleValueFilter","isMultiClauseFilter","EventEmitter"],"mappings":"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"}
|
|
1
|
+
{"version":3,"file":"FilterModel.js","sources":["../src/FilterModel.ts"],"sourcesContent":["import {\n Filter,\n FilterClause,\n FilterClauseOp,\n FilterCombinatorOp,\n MultiClauseFilter,\n MultiValueFilterClause,\n SingleValueFilterClause,\n} from \"@vuu-ui/vuu-filter-types\";\nimport {\n EventEmitter,\n isMultiClauseFilter,\n isMultiValueFilter,\n isSingleValueFilter,\n} from \"@vuu-ui/vuu-utils\";\n\nexport type FilterStatusChangeHandler = (isValid: boolean) => void;\nexport type FilterChangeHandler = (\n filter: Partial<Filter>,\n isValid: boolean,\n) => void;\nexport type FilterClauseChangeHandler = (\n filter: Partial<FilterClause>,\n isValid: boolean,\n) => void;\n\nconst hasValues = ({ values }: MultiValueFilterClause) =>\n Array.isArray(values) && values.length > 0;\n\nconst isValidFilterClause = (\n filterClause: Partial<FilterClause>,\n): filterClause is FilterClause => {\n if (filterClause.op === undefined || filterClause.column === undefined) {\n return false;\n } else if (isMultiValueFilter(filterClause)) {\n return hasValues(filterClause);\n } else if (isSingleValueFilter(filterClause)) {\n return filterClause.value !== undefined && filterClause.value !== \"\";\n }\n throw Error(\"isValidFilterClause should never reach this far\");\n};\n\nconst isValidFilter = (filter?: Filter): boolean => {\n if (filter === undefined) {\n return false;\n } else if (isMultiClauseFilter(filter)) {\n return filter.filters.every(isValidFilter);\n } else {\n return isValidFilterClause(filter);\n }\n};\n\nconst isValidFilterModel = (filterModel: FilterModel) => {\n if (filterModel.isMultiClauseFilter) {\n return filterModel.filterClauses.every((f) => f.isValid);\n } else {\n return (\n filterModel.filterClauses.length === 1 &&\n filterModel.filterClauses[0].isValid\n );\n }\n};\n\nexport type FilterClauseModelEvents = {\n filterClause: FilterClauseChangeHandler;\n isValid: FilterStatusChangeHandler;\n};\n\nexport type FilterModelEvents = {\n // TODO do we need an incomplate filter type\n filter: FilterChangeHandler;\n isValid: FilterStatusChangeHandler;\n};\n\nexport class FilterClauseModel extends EventEmitter<FilterClauseModelEvents> {\n #filterClause: Partial<FilterClause>;\n #isValid: boolean;\n constructor(filterClause: Partial<FilterClause>) {\n super();\n this.#filterClause = filterClause;\n this.#isValid = isValidFilterClause(filterClause);\n }\n get isValid() {\n return this.#isValid;\n }\n\n private setIsValid(isValid: boolean) {\n this.#isValid = isValid;\n this.emit(\"isValid\", isValid);\n }\n\n get column() {\n return this.#filterClause.column;\n }\n\n set column(column: undefined | string) {\n // TODO set op, value to empty\n this.#filterClause = {\n column,\n };\n\n const isValid = isValidFilterClause(this.#filterClause);\n this.emit(\"filterClause\", this.#filterClause, isValid);\n if (isValid !== this.#isValid) {\n this.setIsValid(isValid);\n }\n }\n\n get op() {\n return this.#filterClause.op;\n }\n\n setOp(op: undefined | FilterClauseOp) {\n this.#filterClause = {\n ...this.#filterClause,\n op,\n };\n const isValid = isValidFilterClause(this.#filterClause);\n this.emit(\"filterClause\", this.#filterClause, isValid);\n if (isValid !== this.#isValid) {\n this.setIsValid(isValid);\n }\n }\n\n setValue(\n value:\n | undefined\n | string\n | string[]\n | number\n | number[]\n | boolean\n | boolean[],\n isFinal = true,\n ) {\n if (isSingleValueFilter(this.#filterClause)) {\n this.#filterClause = {\n ...this.#filterClause,\n value,\n } as SingleValueFilterClause;\n } else if (Array.isArray(value)) {\n this.#filterClause = {\n ...this.#filterClause,\n values: value,\n } as MultiValueFilterClause;\n }\n\n const isValid = isValidFilterClause(this.#filterClause);\n if (isValid !== this.#isValid) {\n this.setIsValid(isValid);\n }\n if (isFinal) {\n this.emit(\"filterClause\", this.#filterClause, isValid);\n }\n }\n\n asFilter(throwIfInvalid = true): FilterClause {\n if (throwIfInvalid && !this.#isValid) {\n throw Error(\"Invalid filter model cannot be returned as Filter\");\n }\n return this.#filterClause as FilterClause;\n }\n}\n\nexport class FilterModel extends EventEmitter<FilterModelEvents> {\n #children: FilterClauseModel[] = [];\n #isValid: boolean;\n #op?: FilterCombinatorOp;\n\n constructor(filter?: Filter) {\n super();\n if (isMultiClauseFilter(filter)) {\n this.#op = filter.op;\n filter.filters.forEach((f) => this.addFilterClause(f as FilterClause));\n } else if (filter) {\n this.addFilterClause(filter);\n } else {\n this.addNewFilterClause();\n }\n\n this.#isValid = isValidFilter(filter);\n }\n get isValid() {\n return this.#isValid;\n }\n\n private setIsValid(isValid: boolean) {\n this.#isValid = isValid;\n this.emit(\"isValid\", isValid);\n }\n\n addNewFilterClause(operator?: FilterCombinatorOp) {\n const count = this.#children.length;\n if (!operator && !this.#op && count === 1) {\n this.#op = \"and\";\n } else if (operator && !this.#op && count === 1) {\n this.#op = operator;\n } else if (operator && this.#op && operator !== this.#op) {\n throw Error(\n \"FilterModel: use setOp to change the Filter combinator operator\",\n );\n }\n\n const filterClauseModel = new FilterClauseModel({});\n filterClauseModel.on(\"isValid\", this.onFilterClauseStatusChange);\n filterClauseModel.on(\"filterClause\", this.onFilterClauseChange);\n this.#children.push(filterClauseModel);\n this.setIsValid(false);\n }\n\n addFilterClause(filterClause: Partial<FilterClause> = {}) {\n const filterClauseModel = new FilterClauseModel(filterClause);\n filterClauseModel.on(\"isValid\", this.onFilterClauseStatusChange);\n filterClauseModel.on(\"filterClause\", this.onFilterClauseChange);\n this.#children.push(filterClauseModel);\n }\n\n removeFilterClause(filterClause: FilterClauseModel) {\n // We never allow the last clause to be removed\n if (this.isMultiClauseFilter) {\n const doomedFilter = this.filterClauses.indexOf(filterClause);\n if (doomedFilter !== -1) {\n this.filterClauses.splice(doomedFilter, 1);\n // If we're down the the last clause, we are no longer multi-clause\n if (this.filterClauses.length === 1) {\n this.#op = undefined;\n }\n this.checkValidStatus();\n }\n }\n }\n\n checkValidStatus() {\n const nowValid = isValidFilterModel(this);\n\n if (nowValid !== this.#isValid) {\n this.setIsValid(nowValid);\n }\n }\n\n onFilterClauseChange: FilterChangeHandler = () => {\n this.emit(\"filter\", this.asFilter(false), this.#isValid);\n };\n\n onFilterClauseStatusChange = (isValid: boolean) => {\n if (!isValid && this.#isValid) {\n this.setIsValid(false);\n } else {\n this.checkValidStatus();\n }\n };\n\n getFilterClause(index: number) {\n return this.#children[index];\n }\n\n get op() {\n return this.#op;\n }\n\n setOp(op: FilterCombinatorOp) {\n this.#op = op;\n this.emit(\"filter\", this.asFilter(false), this.#isValid);\n }\n\n get filterClauses() {\n return this.#children;\n }\n\n get isMultiClauseFilter() {\n return this.#op === \"and\" || this.#op === \"or\";\n }\n\n asFilter(throwIfInvalid = true): Filter {\n if (throwIfInvalid && !this.#isValid) {\n throw Error(\"Invalid filter model cannot be returned as Filter\");\n }\n if (this.#op === \"and\" || this.#op === \"or\") {\n return {\n op: this.#op,\n filters: this.#children.map((f) => f.asFilter(throwIfInvalid)),\n } as MultiClauseFilter;\n } else {\n return this.#children[0].asFilter(throwIfInvalid);\n }\n }\n}\n"],"names":["_isValid","isMultiValueFilter","isSingleValueFilter","isMultiClauseFilter","EventEmitter"],"mappings":"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"}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"CustomFilters.js","sources":["../../src/custom-filters/CustomFilters.tsx"],"sourcesContent":["import { Prompt } from \"@vuu-ui/vuu-popups\";\nimport type { ColumnDescriptor } from \"@vuu-ui/vuu-table-types\";\nimport { IconButton } from \"@vuu-ui/vuu-ui-controls\";\nimport { HTMLAttributes, ReactElement, useRef } from \"react\";\nimport { type FilterBarProps } from \"../filter-bar\";\nimport { FilterEditor } from \"../filter-editor\";\nimport { FilterPill } from \"../filter-pill\";\nimport { FilterModel } from \"../FilterModel\";\nimport { isEditFilterState, useCustomFilters } from \"./useCustomFilters\";\n\nconst classBase = \"vuuCustomFilters\";\n\nexport interface CustomFilterProps\n extends HTMLAttributes<HTMLDivElement>,\n Pick<\n FilterBarProps,\n | \"defaultFilterState\"\n | \"filterState\"\n | \"onApplyFilter\"\n | \"onFilterDeleted\"\n | \"onFilterRenamed\"\n | \"onFilterStateChanged\"\n | \"tableSchema\"\n > {\n columnDescriptors: ColumnDescriptor[];\n}\n\nexport const CustomFilters = ({\n columnDescriptors,\n defaultFilterState,\n filterState,\n onApplyFilter,\n onFilterDeleted,\n onFilterRenamed,\n onFilterStateChanged,\n tableSchema,\n}: CustomFilterProps) => {\n const rootRef = useRef<HTMLDivElement>(null);\n\n const {\n activeFilterIndex,\n addButtonProps,\n columnsByName,\n filters,\n interactedFilterState,\n onCancelEdit,\n onSave,\n FilterPillProps,\n promptProps,\n } = useCustomFilters({\n containerRef: rootRef,\n columnDescriptors,\n defaultFilterState,\n filterState,\n onApplyFilter,\n onFilterStateChanged,\n onFilterDeleted,\n onFilterRenamed,\n });\n\n const indexOfFilterBeingRenamed =\n interactedFilterState?.state === \"rename\"\n ? interactedFilterState.index\n : -1;\n\n const filterModel = isEditFilterState(interactedFilterState?.state)\n ? new FilterModel(interactedFilterState.filter)\n : undefined;\n\n const getFilterPills = () => {\n const items: ReactElement[] = [];\n filters.forEach((filter, i) => {\n items.push(\n <FilterPill\n {...FilterPillProps}\n editing={indexOfFilterBeingRenamed === i}\n columnsByName={columnsByName}\n data-index={i}\n filter={filter}\n key={`filter-${i}`}\n selected={activeFilterIndex.includes(i)}\n />,\n );\n });\n return items;\n };\n\n return (\n <>\n <div className=\"vuuCustomFilters\" ref={rootRef}>\n <div className={`${classBase}-filters`}>{getFilterPills()}</div>\n <IconButton\n {...addButtonProps}\n aria-label=\"Add filter\"\n data-selectable={false}\n icon=\"plus\"\n key=\"filter-add\"\n tabIndex={0}\n variant=\"secondary\"\n />\n\n {promptProps ? (\n <Prompt\n {...promptProps}\n PopupProps={{\n anchorElement: rootRef,\n offsetTop: 16,\n placement: \"below-center\",\n }}\n />\n ) : null}\n </div>\n {filterModel && tableSchema && (\n <FilterEditor\n columnDescriptors={columnDescriptors}\n key=\"filter-editor\"\n onCancel={onCancelEdit}\n onSave={onSave}\n filter={interactedFilterState?.filter}\n tableSchema={tableSchema}\n />\n )}\n </>\n );\n};\n"],"names":["useRef","useCustomFilters","isEditFilterState","FilterModel","createElement","FilterPill","jsxs","Fragment","jsx","IconButton","Prompt","FilterEditor"],"mappings":";;;;;;;;;;;AAUA,MAAM,SAAY,GAAA,kBAAA
|
|
1
|
+
{"version":3,"file":"CustomFilters.js","sources":["../../src/custom-filters/CustomFilters.tsx"],"sourcesContent":["import { Prompt } from \"@vuu-ui/vuu-popups\";\nimport type { ColumnDescriptor } from \"@vuu-ui/vuu-table-types\";\nimport { IconButton } from \"@vuu-ui/vuu-ui-controls\";\nimport { HTMLAttributes, ReactElement, useRef } from \"react\";\nimport { type FilterBarProps } from \"../filter-bar\";\nimport { FilterEditor } from \"../filter-editor\";\nimport { FilterPill } from \"../filter-pill\";\nimport { FilterModel } from \"../FilterModel\";\nimport { isEditFilterState, useCustomFilters } from \"./useCustomFilters\";\n\nconst classBase = \"vuuCustomFilters\";\n\nexport interface CustomFilterProps\n extends HTMLAttributes<HTMLDivElement>,\n Pick<\n FilterBarProps,\n | \"defaultFilterState\"\n | \"filterState\"\n | \"onApplyFilter\"\n | \"onFilterDeleted\"\n | \"onFilterRenamed\"\n | \"onFilterStateChanged\"\n | \"tableSchema\"\n > {\n columnDescriptors: ColumnDescriptor[];\n}\n\nexport const CustomFilters = ({\n columnDescriptors,\n defaultFilterState,\n filterState,\n onApplyFilter,\n onFilterDeleted,\n onFilterRenamed,\n onFilterStateChanged,\n tableSchema,\n}: CustomFilterProps) => {\n const rootRef = useRef<HTMLDivElement>(null);\n\n const {\n activeFilterIndex,\n addButtonProps,\n columnsByName,\n filters,\n interactedFilterState,\n onCancelEdit,\n onSave,\n FilterPillProps,\n promptProps,\n } = useCustomFilters({\n containerRef: rootRef,\n columnDescriptors,\n defaultFilterState,\n filterState,\n onApplyFilter,\n onFilterStateChanged,\n onFilterDeleted,\n onFilterRenamed,\n });\n\n const indexOfFilterBeingRenamed =\n interactedFilterState?.state === \"rename\"\n ? interactedFilterState.index\n : -1;\n\n const filterModel = isEditFilterState(interactedFilterState?.state)\n ? new FilterModel(interactedFilterState.filter)\n : undefined;\n\n const getFilterPills = () => {\n const items: ReactElement[] = [];\n filters.forEach((filter, i) => {\n items.push(\n <FilterPill\n {...FilterPillProps}\n editing={indexOfFilterBeingRenamed === i}\n columnsByName={columnsByName}\n data-index={i}\n filter={filter}\n key={`filter-${i}`}\n selected={activeFilterIndex.includes(i)}\n />,\n );\n });\n return items;\n };\n\n return (\n <>\n <div className=\"vuuCustomFilters\" ref={rootRef}>\n <div className={`${classBase}-filters`}>{getFilterPills()}</div>\n <IconButton\n {...addButtonProps}\n aria-label=\"Add filter\"\n data-selectable={false}\n icon=\"plus\"\n key=\"filter-add\"\n tabIndex={0}\n variant=\"secondary\"\n />\n\n {promptProps ? (\n <Prompt\n {...promptProps}\n PopupProps={{\n anchorElement: rootRef,\n offsetTop: 16,\n placement: \"below-center\",\n }}\n />\n ) : null}\n </div>\n {filterModel && tableSchema && (\n <FilterEditor\n columnDescriptors={columnDescriptors}\n key=\"filter-editor\"\n onCancel={onCancelEdit}\n onSave={onSave}\n filter={interactedFilterState?.filter}\n tableSchema={tableSchema}\n />\n )}\n </>\n );\n};\n"],"names":["useRef","useCustomFilters","isEditFilterState","FilterModel","createElement","FilterPill","jsxs","Fragment","jsx","IconButton","Prompt","FilterEditor"],"mappings":";;;;;;;;;;;AAUA,MAAM,SAAY,GAAA,kBAAA;AAiBX,MAAM,gBAAgB,CAAC;AAAA,EAC5B,iBAAA;AAAA,EACA,kBAAA;AAAA,EACA,WAAA;AAAA,EACA,aAAA;AAAA,EACA,eAAA;AAAA,EACA,eAAA;AAAA,EACA,oBAAA;AAAA,EACA;AACF,CAAyB,KAAA;AACvB,EAAM,MAAA,OAAA,GAAUA,aAAuB,IAAI,CAAA;AAE3C,EAAM,MAAA;AAAA,IACJ,iBAAA;AAAA,IACA,cAAA;AAAA,IACA,aAAA;AAAA,IACA,OAAA;AAAA,IACA,qBAAA;AAAA,IACA,YAAA;AAAA,IACA,MAAA;AAAA,IACA,eAAA;AAAA,IACA;AAAA,MACEC,iCAAiB,CAAA;AAAA,IACnB,YAAc,EAAA,OAAA;AAAA,IACd,iBAAA;AAAA,IACA,kBAAA;AAAA,IACA,WAAA;AAAA,IACA,aAAA;AAAA,IACA,oBAAA;AAAA,IACA,eAAA;AAAA,IACA;AAAA,GACD,CAAA;AAED,EAAA,MAAM,yBACJ,GAAA,qBAAA,EAAuB,KAAU,KAAA,QAAA,GAC7B,sBAAsB,KACtB,GAAA,CAAA,CAAA;AAEN,EAAM,MAAA,WAAA,GAAcC,mCAAkB,qBAAuB,EAAA,KAAK,IAC9D,IAAIC,uBAAA,CAAY,qBAAsB,CAAA,MAAM,CAC5C,GAAA,KAAA,CAAA;AAEJ,EAAA,MAAM,iBAAiB,MAAM;AAC3B,IAAA,MAAM,QAAwB,EAAC;AAC/B,IAAQ,OAAA,CAAA,OAAA,CAAQ,CAAC,MAAA,EAAQ,CAAM,KAAA;AAC7B,MAAM,KAAA,CAAA,IAAA;AAAA,wBACJC,mBAAA;AAAA,UAACC,qBAAA;AAAA,UAAA;AAAA,YACE,GAAG,eAAA;AAAA,YACJ,SAAS,yBAA8B,KAAA,CAAA;AAAA,YACvC,aAAA;AAAA,YACA,YAAY,EAAA,CAAA;AAAA,YACZ,MAAA;AAAA,YACA,GAAA,EAAK,UAAU,CAAC,CAAA,CAAA;AAAA,YAChB,QAAA,EAAU,iBAAkB,CAAA,QAAA,CAAS,CAAC;AAAA;AAAA;AACxC,OACF;AAAA,KACD,CAAA;AACD,IAAO,OAAA,KAAA;AAAA,GACT;AAEA,EAAA,uBAEIC,eAAA,CAAAC,mBAAA,EAAA,EAAA,QAAA,EAAA;AAAA,oBAAAD,eAAA,CAAC,KAAI,EAAA,EAAA,SAAA,EAAU,kBAAmB,EAAA,GAAA,EAAK,OACrC,EAAA,QAAA,EAAA;AAAA,sBAAAE,cAAA,CAAC,SAAI,SAAW,EAAA,CAAA,EAAG,SAAS,CAAA,QAAA,CAAA,EAAa,0BAAiB,EAAA,CAAA;AAAA,sBAC1DJ,mBAAA;AAAA,QAACK,wBAAA;AAAA,QAAA;AAAA,UACE,GAAG,cAAA;AAAA,UACJ,YAAW,EAAA,YAAA;AAAA,UACX,iBAAiB,EAAA,KAAA;AAAA,UACjB,IAAK,EAAA,MAAA;AAAA,UACL,GAAI,EAAA,YAAA;AAAA,UACJ,QAAU,EAAA,CAAA;AAAA,UACV,OAAQ,EAAA;AAAA;AAAA,OACV;AAAA,MAEC,WACC,mBAAAD,cAAA;AAAA,QAACE,gBAAA;AAAA,QAAA;AAAA,UACE,GAAG,WAAA;AAAA,UACJ,UAAY,EAAA;AAAA,YACV,aAAe,EAAA,OAAA;AAAA,YACf,SAAW,EAAA,EAAA;AAAA,YACX,SAAW,EAAA;AAAA;AACb;AAAA,OAEA,GAAA;AAAA,KACN,EAAA,CAAA;AAAA,IACC,eAAe,WACd,oBAAAF,cAAA;AAAA,MAACG,yBAAA;AAAA,MAAA;AAAA,QACC,iBAAA;AAAA,QAEA,QAAU,EAAA,YAAA;AAAA,QACV,MAAA;AAAA,QACA,QAAQ,qBAAuB,EAAA,MAAA;AAAA,QAC/B;AAAA,OAAA;AAAA,MAJI;AAAA;AAKN,GAEJ,EAAA,CAAA;AAEJ;;;;"}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"filterBarFocusManagement.js","sources":["../../src/custom-filters/filterBarFocusManagement.ts"],"sourcesContent":["import {\n getElementByDataIndex,\n getElementDataIndex,\n queryClosest,\n} from \"@vuu-ui/vuu-utils\";\n\nconst QUERY_ADD_BUTTON = '.saltButton:has([aria-label=\"Add filter\"])';\n\nexport const navigateToNextItem = (\n el: HTMLElement | EventTarget,\n direction: \"bwd\" | \"fwd\" = \"fwd\",\n) => {\n const pill = queryClosest(el, \".vuuFilterPill\");\n if (pill) {\n const index = getElementDataIndex(pill);\n if (typeof index === \"number\") {\n const target =\n direction === \"fwd\"\n ? getElementByDataIndex(pill.parentElement, index + 1)\n : getElementByDataIndex(pill.parentElement, index - 1);\n if (target) {\n target.focus();\n } else if (direction === \"fwd\") {\n const filterBar = queryClosest(el, \".vuuFilterBar\");\n const addButton = filterBar?.querySelector(\n QUERY_ADD_BUTTON,\n ) as HTMLElement;\n addButton?.focus();\n }\n }\n } else {\n const button = queryClosest(el, QUERY_ADD_BUTTON);\n if (button) {\n const filterBar = queryClosest(el, \".vuuFilterBar\");\n const target = filterBar?.querySelector(\n \".vuuFilterPill:last-child\",\n ) as HTMLElement;\n target?.focus();\n }\n }\n};\n"],"names":["queryClosest","getElementDataIndex","getElementByDataIndex"],"mappings":";;;;AAMA,MAAM,gBAAmB,GAAA,4CAAA
|
|
1
|
+
{"version":3,"file":"filterBarFocusManagement.js","sources":["../../src/custom-filters/filterBarFocusManagement.ts"],"sourcesContent":["import {\n getElementByDataIndex,\n getElementDataIndex,\n queryClosest,\n} from \"@vuu-ui/vuu-utils\";\n\nconst QUERY_ADD_BUTTON = '.saltButton:has([aria-label=\"Add filter\"])';\n\nexport const navigateToNextItem = (\n el: HTMLElement | EventTarget,\n direction: \"bwd\" | \"fwd\" = \"fwd\",\n) => {\n const pill = queryClosest(el, \".vuuFilterPill\");\n if (pill) {\n const index = getElementDataIndex(pill);\n if (typeof index === \"number\") {\n const target =\n direction === \"fwd\"\n ? getElementByDataIndex(pill.parentElement, index + 1)\n : getElementByDataIndex(pill.parentElement, index - 1);\n if (target) {\n target.focus();\n } else if (direction === \"fwd\") {\n const filterBar = queryClosest(el, \".vuuFilterBar\");\n const addButton = filterBar?.querySelector(\n QUERY_ADD_BUTTON,\n ) as HTMLElement;\n addButton?.focus();\n }\n }\n } else {\n const button = queryClosest(el, QUERY_ADD_BUTTON);\n if (button) {\n const filterBar = queryClosest(el, \".vuuFilterBar\");\n const target = filterBar?.querySelector(\n \".vuuFilterPill:last-child\",\n ) as HTMLElement;\n target?.focus();\n }\n }\n};\n"],"names":["queryClosest","getElementDataIndex","getElementByDataIndex"],"mappings":";;;;AAMA,MAAM,gBAAmB,GAAA,4CAAA;AAElB,MAAM,kBAAqB,GAAA,CAChC,EACA,EAAA,SAAA,GAA2B,KACxB,KAAA;AACH,EAAM,MAAA,IAAA,GAAOA,qBAAa,CAAA,EAAA,EAAI,gBAAgB,CAAA;AAC9C,EAAA,IAAI,IAAM,EAAA;AACR,IAAM,MAAA,KAAA,GAAQC,6BAAoB,IAAI,CAAA;AACtC,IAAI,IAAA,OAAO,UAAU,QAAU,EAAA;AAC7B,MAAA,MAAM,MACJ,GAAA,SAAA,KAAc,KACV,GAAAC,8BAAA,CAAsB,IAAK,CAAA,aAAA,EAAe,KAAQ,GAAA,CAAC,CACnD,GAAAA,8BAAA,CAAsB,IAAK,CAAA,aAAA,EAAe,QAAQ,CAAC,CAAA;AACzD,MAAA,IAAI,MAAQ,EAAA;AACV,QAAA,MAAA,CAAO,KAAM,EAAA;AAAA,OACf,MAAA,IAAW,cAAc,KAAO,EAAA;AAC9B,QAAM,MAAA,SAAA,GAAYF,qBAAa,CAAA,EAAA,EAAI,eAAe,CAAA;AAClD,QAAA,MAAM,YAAY,SAAW,EAAA,aAAA;AAAA,UAC3B;AAAA,SACF;AACA,QAAA,SAAA,EAAW,KAAM,EAAA;AAAA;AACnB;AACF,GACK,MAAA;AACL,IAAM,MAAA,MAAA,GAASA,qBAAa,CAAA,EAAA,EAAI,gBAAgB,CAAA;AAChD,IAAA,IAAI,MAAQ,EAAA;AACV,MAAM,MAAA,SAAA,GAAYA,qBAAa,CAAA,EAAA,EAAI,eAAe,CAAA;AAClD,MAAA,MAAM,SAAS,SAAW,EAAA,aAAA;AAAA,QACxB;AAAA,OACF;AACA,MAAA,MAAA,EAAQ,KAAM,EAAA;AAAA;AAChB;AAEJ;;;;"}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"useCustomFilters.js","sources":["../../src/custom-filters/useCustomFilters.ts"],"sourcesContent":["import { MenuActionHandler } from \"@vuu-ui/vuu-data-types\";\nimport { ColumnDescriptorsByName, Filter } from \"@vuu-ui/vuu-filter-types\";\nimport { PromptProps } from \"@vuu-ui/vuu-popups\";\nimport { ColumnDescriptor } from \"@vuu-ui/vuu-table-types\";\nimport {\n EditableLabelProps,\n EditAPI,\n NullEditAPI,\n} from \"@vuu-ui/vuu-ui-controls\";\nimport {\n filterAsQuery,\n getElementDataIndex,\n queryClosest,\n} from \"@vuu-ui/vuu-utils\";\nimport {\n KeyboardEventHandler,\n MouseEventHandler,\n RefObject,\n useCallback,\n useEffect,\n useMemo,\n useRef,\n useState,\n} from \"react\";\nimport { FilterBarProps } from \"../filter-bar\";\nimport {\n FilterEditCancelHandler,\n FilterEditSaveHandler,\n} from \"../filter-editor\";\nimport { FilterPillProps } from \"../filter-pill\";\nimport { FilterMenuOptions } from \"../filter-pill-menu\";\nimport { navigateToNextItem } from \"./filterBarFocusManagement\";\nimport { useFilterState } from \"./useFilterState\";\n\nexport type EditFilterState = \"create\" | \"edit\";\nexport type FilterState = EditFilterState | \"rename\";\nexport const isEditFilterState = (\n filterState?: string,\n): filterState is EditFilterState =>\n filterState === \"edit\" || filterState === \"create\";\n\ntype InteractedFilterState = {\n filter?: Filter;\n index: number;\n state: FilterState;\n};\n\nexport interface CustomFilterHookProps\n extends Pick<\n FilterBarProps,\n | \"columnDescriptors\"\n | \"defaultFilterState\"\n | \"filterState\"\n | \"onApplyFilter\"\n | \"onFilterDeleted\"\n | \"onFilterRenamed\"\n | \"onFilterStateChanged\"\n > {\n containerRef: RefObject<HTMLDivElement>;\n}\n\nexport const useCustomFilters = ({\n columnDescriptors,\n containerRef,\n defaultFilterState,\n filterState,\n onApplyFilter,\n onFilterDeleted,\n onFilterRenamed,\n onFilterStateChanged,\n}: CustomFilterHookProps) => {\n const addButtonRef = useRef<HTMLButtonElement>(null);\n const [interactedFilterState, setInteractedFilterState] = useState<\n InteractedFilterState | undefined\n >();\n const [promptProps, setPromptProps] = useState<PromptProps | null>(null);\n const editPillLabelAPI = useRef<EditAPI>(NullEditAPI);\n\n const columnsByName = useMemo(\n () => columnDescriptorsByName(columnDescriptors),\n [columnDescriptors],\n );\n\n const {\n activeFilterIndex,\n filters,\n onAddFilter,\n onChangeFilter,\n onDeleteFilter,\n onRenameFilter,\n onToggleFilterActive,\n } = useFilterState({\n defaultFilterState,\n filterState,\n onFilterDeleted,\n onFilterRenamed,\n onFilterStateChanged,\n });\n\n useEffect(() => {\n const activeFilters = activeFilterIndex.map((i) => filters[i]);\n const applyFilter = (filter?: Filter) => {\n const query = filter ? filterAsQuery(filter, { columnsByName }) : \"\";\n onApplyFilter({ filter: query, filterStruct: filter });\n };\n if (activeFilters.length === 0) {\n applyFilter();\n } else if (activeFilters.length === 1) {\n const [filter] = activeFilters;\n applyFilter(filter);\n } else {\n applyFilter({ op: \"and\", filters: activeFilters });\n }\n }, [activeFilterIndex, columnsByName, filters, onApplyFilter]);\n\n const editPillLabel = useCallback((index: number, filter: Filter) => {\n setTimeout(() => {\n setInteractedFilterState({\n filter,\n index,\n state: \"rename\",\n });\n }, 100);\n }, []);\n\n const focusFilterPill = useCallback(\n (index = 0) => {\n requestAnimationFrame(() => {\n const target = containerRef.current?.querySelector(\n `.vuuFilterPill[data-index=\"${index}\"] button`,\n ) as undefined | HTMLInputElement;\n if (target) {\n target.focus();\n }\n });\n },\n [containerRef],\n );\n\n const deleteConfirmed = useCallback(\n (filter: Filter) => {\n onDeleteFilter(filter);\n\n // TODO move focus to next/previous filter\n requestAnimationFrame(() => {\n if (filters.length) {\n focusFilterPill(0);\n }\n });\n },\n [filters.length, focusFilterPill, onDeleteFilter],\n );\n\n const getDeletePrompt = useMemo(\n () => (filter: Filter) => {\n const close = () => {\n setPromptProps(null);\n focusFilterPill();\n };\n return {\n confirmButtonLabel: \"Remove\",\n icon: \"warn-triangle\",\n onCancel: close,\n onClose: close,\n onConfirm: () => {\n setPromptProps(null);\n deleteConfirmed(filter);\n },\n text: `Are you sure you want to delete ${filter.name}`,\n title: \"Remove Filter\",\n variant: \"warn\",\n } as PromptProps;\n },\n [deleteConfirmed, focusFilterPill],\n );\n\n const deleteFilter = useCallback(\n (filter: Filter, withPrompt: boolean) => {\n if (withPrompt) {\n setPromptProps(getDeletePrompt(filter));\n } else {\n deleteConfirmed(filter);\n }\n },\n [deleteConfirmed, getDeletePrompt],\n );\n\n // TODO handle cancel edit name\n const handleExitEditFilterName: EditableLabelProps[\"onExitEditMode\"] =\n useCallback(\n (_, editedValue = \"\") => {\n if (\n interactedFilterState?.state === \"rename\" &&\n interactedFilterState.filter\n ) {\n const { filter } = interactedFilterState;\n const indexOfEditedFilter = onRenameFilter(filter, editedValue);\n\n setInteractedFilterState(undefined);\n focusFilterPill(indexOfEditedFilter);\n }\n setInteractedFilterState(undefined);\n },\n [focusFilterPill, interactedFilterState, onRenameFilter],\n );\n\n const handlePillMenuAction = useCallback<MenuActionHandler>(\n ({ menuId, options }) => {\n switch (menuId) {\n case \"delete-filter\": {\n const { filter } = options as FilterMenuOptions;\n deleteFilter(filter, true);\n return true;\n }\n case \"rename-filter\": {\n const { filter } = options as FilterMenuOptions;\n const index = filters.indexOf(filter);\n editPillLabel(index, filter);\n return true;\n }\n case \"edit-filter\": {\n const { filter } = options as FilterMenuOptions;\n setInteractedFilterState({\n filter,\n index: filters.indexOf(filter),\n state: \"edit\",\n });\n return true;\n }\n default:\n return false;\n }\n },\n [deleteFilter, editPillLabel, filters],\n );\n\n const handlePillKeyDown = useCallback<KeyboardEventHandler>((e) => {\n if (e.key === \"ArrowRight\" || e.key === \"ArrowLeft\") {\n navigateToNextItem(e.target, e.key === \"ArrowLeft\" ? \"bwd\" : \"fwd\");\n }\n }, []);\n\n const addIfNewElseUpdate = useCallback(\n (newOrUpdatedFilter: Filter, existing: Filter | undefined) => {\n if (existing === undefined) {\n const idx = onAddFilter(newOrUpdatedFilter);\n focusFilterPill(idx);\n editPillLabel(idx, newOrUpdatedFilter);\n } else {\n const idx = onChangeFilter(existing, newOrUpdatedFilter);\n focusFilterPill(idx);\n }\n },\n [editPillLabel, focusFilterPill, onAddFilter, onChangeFilter],\n );\n\n const filterSaveHandler = useCallback<FilterEditSaveHandler>(\n (filter) => {\n if (interactedFilterState) {\n const { filter: existingFilter } = interactedFilterState;\n setInteractedFilterState(undefined);\n addIfNewElseUpdate(filter, existingFilter);\n }\n },\n [addIfNewElseUpdate, interactedFilterState],\n );\n\n const handlePillClick = useCallback<MouseEventHandler<HTMLButtonElement>>(\n (e) => {\n const isEditing = (e.target as HTMLElement).querySelector(\n \".vuuEditableLabel-editing\",\n );\n if (!isEditing) {\n const pill = queryClosest(e.target, \".vuuFilterPill\");\n if (pill) {\n const index = getElementDataIndex(pill);\n onToggleFilterActive(index, e.shiftKey);\n }\n }\n },\n [onToggleFilterActive],\n );\n\n const FilterPillProps: Omit<FilterPillProps, \"filter\" | \"selected\"> = {\n editLabelApiRef: editPillLabelAPI,\n // onBeginEdit: handleBeginEditFilterName,\n onClick: handlePillClick,\n onKeyDown: handlePillKeyDown,\n onMenuAction: handlePillMenuAction,\n onExitEditMode: handleExitEditFilterName,\n };\n\n const handleClickAddButton = useCallback(() => {\n setInteractedFilterState({\n index: -1,\n state: \"create\",\n });\n }, []);\n\n const handleKeyDownAddButton = useCallback<KeyboardEventHandler>((evt) => {\n if (evt.key === \"ArrowLeft\") {\n navigateToNextItem(evt.target, \"bwd\");\n }\n }, []);\n\n const handleCancelEdit = useCallback<FilterEditCancelHandler>(() => {\n if (interactedFilterState) {\n const { index } = interactedFilterState;\n if (index === -1) {\n addButtonRef.current?.focus();\n } else {\n focusFilterPill(index);\n }\n setInteractedFilterState(undefined);\n }\n }, [focusFilterPill, interactedFilterState]);\n\n const addButtonProps = {\n ref: addButtonRef,\n onClick: handleClickAddButton,\n onKeyDown: handleKeyDownAddButton,\n };\n\n return {\n FilterPillProps,\n activeFilterIndex,\n addButtonProps,\n columnsByName,\n filters,\n interactedFilterState,\n onCancelEdit: handleCancelEdit,\n onSave: filterSaveHandler,\n promptProps,\n };\n};\n\nfunction columnDescriptorsByName(\n columns: ColumnDescriptor[],\n): ColumnDescriptorsByName {\n return columns.reduce((m, col) => ({ ...m, [col.name]: col }), {});\n}\n"],"names":["useRef","useState","NullEditAPI","useMemo","useFilterState","useEffect","filterAsQuery","useCallback","navigateToNextItem","queryClosest","getElementDataIndex","FilterPillProps"],"mappings":"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"}
|
|
1
|
+
{"version":3,"file":"useCustomFilters.js","sources":["../../src/custom-filters/useCustomFilters.ts"],"sourcesContent":["import { MenuActionHandler } from \"@vuu-ui/vuu-data-types\";\nimport { ColumnDescriptorsByName, Filter } from \"@vuu-ui/vuu-filter-types\";\nimport { PromptProps } from \"@vuu-ui/vuu-popups\";\nimport { ColumnDescriptor } from \"@vuu-ui/vuu-table-types\";\nimport {\n EditableLabelProps,\n EditAPI,\n NullEditAPI,\n} from \"@vuu-ui/vuu-ui-controls\";\nimport {\n filterAsQuery,\n getElementDataIndex,\n queryClosest,\n} from \"@vuu-ui/vuu-utils\";\nimport {\n KeyboardEventHandler,\n MouseEventHandler,\n RefObject,\n useCallback,\n useEffect,\n useMemo,\n useRef,\n useState,\n} from \"react\";\nimport { FilterBarProps } from \"../filter-bar\";\nimport {\n FilterEditCancelHandler,\n FilterEditSaveHandler,\n} from \"../filter-editor\";\nimport { FilterPillProps } from \"../filter-pill\";\nimport { FilterMenuOptions } from \"../filter-pill-menu\";\nimport { navigateToNextItem } from \"./filterBarFocusManagement\";\nimport { useFilterState } from \"./useFilterState\";\n\nexport type EditFilterState = \"create\" | \"edit\";\nexport type FilterState = EditFilterState | \"rename\";\nexport const isEditFilterState = (\n filterState?: string,\n): filterState is EditFilterState =>\n filterState === \"edit\" || filterState === \"create\";\n\ntype InteractedFilterState = {\n filter?: Filter;\n index: number;\n state: FilterState;\n};\n\nexport interface CustomFilterHookProps\n extends Pick<\n FilterBarProps,\n | \"columnDescriptors\"\n | \"defaultFilterState\"\n | \"filterState\"\n | \"onApplyFilter\"\n | \"onFilterDeleted\"\n | \"onFilterRenamed\"\n | \"onFilterStateChanged\"\n > {\n containerRef: RefObject<HTMLDivElement>;\n}\n\nexport const useCustomFilters = ({\n columnDescriptors,\n containerRef,\n defaultFilterState,\n filterState,\n onApplyFilter,\n onFilterDeleted,\n onFilterRenamed,\n onFilterStateChanged,\n}: CustomFilterHookProps) => {\n const addButtonRef = useRef<HTMLButtonElement>(null);\n const [interactedFilterState, setInteractedFilterState] = useState<\n InteractedFilterState | undefined\n >();\n const [promptProps, setPromptProps] = useState<PromptProps | null>(null);\n const editPillLabelAPI = useRef<EditAPI>(NullEditAPI);\n\n const columnsByName = useMemo(\n () => columnDescriptorsByName(columnDescriptors),\n [columnDescriptors],\n );\n\n const {\n activeFilterIndex,\n filters,\n onAddFilter,\n onChangeFilter,\n onDeleteFilter,\n onRenameFilter,\n onToggleFilterActive,\n } = useFilterState({\n defaultFilterState,\n filterState,\n onFilterDeleted,\n onFilterRenamed,\n onFilterStateChanged,\n });\n\n useEffect(() => {\n const activeFilters = activeFilterIndex.map((i) => filters[i]);\n const applyFilter = (filter?: Filter) => {\n const query = filter ? filterAsQuery(filter, { columnsByName }) : \"\";\n onApplyFilter({ filter: query, filterStruct: filter });\n };\n if (activeFilters.length === 0) {\n applyFilter();\n } else if (activeFilters.length === 1) {\n const [filter] = activeFilters;\n applyFilter(filter);\n } else {\n applyFilter({ op: \"and\", filters: activeFilters });\n }\n }, [activeFilterIndex, columnsByName, filters, onApplyFilter]);\n\n const editPillLabel = useCallback((index: number, filter: Filter) => {\n setTimeout(() => {\n setInteractedFilterState({\n filter,\n index,\n state: \"rename\",\n });\n }, 100);\n }, []);\n\n const focusFilterPill = useCallback(\n (index = 0) => {\n requestAnimationFrame(() => {\n const target = containerRef.current?.querySelector(\n `.vuuFilterPill[data-index=\"${index}\"] button`,\n ) as undefined | HTMLInputElement;\n if (target) {\n target.focus();\n }\n });\n },\n [containerRef],\n );\n\n const deleteConfirmed = useCallback(\n (filter: Filter) => {\n onDeleteFilter(filter);\n\n // TODO move focus to next/previous filter\n requestAnimationFrame(() => {\n if (filters.length) {\n focusFilterPill(0);\n }\n });\n },\n [filters.length, focusFilterPill, onDeleteFilter],\n );\n\n const getDeletePrompt = useMemo(\n () => (filter: Filter) => {\n const close = () => {\n setPromptProps(null);\n focusFilterPill();\n };\n return {\n confirmButtonLabel: \"Remove\",\n icon: \"warn-triangle\",\n onCancel: close,\n onClose: close,\n onConfirm: () => {\n setPromptProps(null);\n deleteConfirmed(filter);\n },\n text: `Are you sure you want to delete ${filter.name}`,\n title: \"Remove Filter\",\n variant: \"warn\",\n } as PromptProps;\n },\n [deleteConfirmed, focusFilterPill],\n );\n\n const deleteFilter = useCallback(\n (filter: Filter, withPrompt: boolean) => {\n if (withPrompt) {\n setPromptProps(getDeletePrompt(filter));\n } else {\n deleteConfirmed(filter);\n }\n },\n [deleteConfirmed, getDeletePrompt],\n );\n\n // TODO handle cancel edit name\n const handleExitEditFilterName: EditableLabelProps[\"onExitEditMode\"] =\n useCallback(\n (_, editedValue = \"\") => {\n if (\n interactedFilterState?.state === \"rename\" &&\n interactedFilterState.filter\n ) {\n const { filter } = interactedFilterState;\n const indexOfEditedFilter = onRenameFilter(filter, editedValue);\n\n setInteractedFilterState(undefined);\n focusFilterPill(indexOfEditedFilter);\n }\n setInteractedFilterState(undefined);\n },\n [focusFilterPill, interactedFilterState, onRenameFilter],\n );\n\n const handlePillMenuAction = useCallback<MenuActionHandler>(\n ({ menuId, options }) => {\n switch (menuId) {\n case \"delete-filter\": {\n const { filter } = options as FilterMenuOptions;\n deleteFilter(filter, true);\n return true;\n }\n case \"rename-filter\": {\n const { filter } = options as FilterMenuOptions;\n const index = filters.indexOf(filter);\n editPillLabel(index, filter);\n return true;\n }\n case \"edit-filter\": {\n const { filter } = options as FilterMenuOptions;\n setInteractedFilterState({\n filter,\n index: filters.indexOf(filter),\n state: \"edit\",\n });\n return true;\n }\n default:\n return false;\n }\n },\n [deleteFilter, editPillLabel, filters],\n );\n\n const handlePillKeyDown = useCallback<KeyboardEventHandler>((e) => {\n if (e.key === \"ArrowRight\" || e.key === \"ArrowLeft\") {\n navigateToNextItem(e.target, e.key === \"ArrowLeft\" ? \"bwd\" : \"fwd\");\n }\n }, []);\n\n const addIfNewElseUpdate = useCallback(\n (newOrUpdatedFilter: Filter, existing: Filter | undefined) => {\n if (existing === undefined) {\n const idx = onAddFilter(newOrUpdatedFilter);\n focusFilterPill(idx);\n editPillLabel(idx, newOrUpdatedFilter);\n } else {\n const idx = onChangeFilter(existing, newOrUpdatedFilter);\n focusFilterPill(idx);\n }\n },\n [editPillLabel, focusFilterPill, onAddFilter, onChangeFilter],\n );\n\n const filterSaveHandler = useCallback<FilterEditSaveHandler>(\n (filter) => {\n if (interactedFilterState) {\n const { filter: existingFilter } = interactedFilterState;\n setInteractedFilterState(undefined);\n addIfNewElseUpdate(filter, existingFilter);\n }\n },\n [addIfNewElseUpdate, interactedFilterState],\n );\n\n const handlePillClick = useCallback<MouseEventHandler<HTMLButtonElement>>(\n (e) => {\n const isEditing = (e.target as HTMLElement).querySelector(\n \".vuuEditableLabel-editing\",\n );\n if (!isEditing) {\n const pill = queryClosest(e.target, \".vuuFilterPill\");\n if (pill) {\n const index = getElementDataIndex(pill);\n onToggleFilterActive(index, e.shiftKey);\n }\n }\n },\n [onToggleFilterActive],\n );\n\n const FilterPillProps: Omit<FilterPillProps, \"filter\" | \"selected\"> = {\n editLabelApiRef: editPillLabelAPI,\n // onBeginEdit: handleBeginEditFilterName,\n onClick: handlePillClick,\n onKeyDown: handlePillKeyDown,\n onMenuAction: handlePillMenuAction,\n onExitEditMode: handleExitEditFilterName,\n };\n\n const handleClickAddButton = useCallback(() => {\n setInteractedFilterState({\n index: -1,\n state: \"create\",\n });\n }, []);\n\n const handleKeyDownAddButton = useCallback<KeyboardEventHandler>((evt) => {\n if (evt.key === \"ArrowLeft\") {\n navigateToNextItem(evt.target, \"bwd\");\n }\n }, []);\n\n const handleCancelEdit = useCallback<FilterEditCancelHandler>(() => {\n if (interactedFilterState) {\n const { index } = interactedFilterState;\n if (index === -1) {\n addButtonRef.current?.focus();\n } else {\n focusFilterPill(index);\n }\n setInteractedFilterState(undefined);\n }\n }, [focusFilterPill, interactedFilterState]);\n\n const addButtonProps = {\n ref: addButtonRef,\n onClick: handleClickAddButton,\n onKeyDown: handleKeyDownAddButton,\n };\n\n return {\n FilterPillProps,\n activeFilterIndex,\n addButtonProps,\n columnsByName,\n filters,\n interactedFilterState,\n onCancelEdit: handleCancelEdit,\n onSave: filterSaveHandler,\n promptProps,\n };\n};\n\nfunction columnDescriptorsByName(\n columns: ColumnDescriptor[],\n): ColumnDescriptorsByName {\n return columns.reduce((m, col) => ({ ...m, [col.name]: col }), {});\n}\n"],"names":["useRef","useState","NullEditAPI","useMemo","useFilterState","useEffect","filterAsQuery","useCallback","navigateToNextItem","queryClosest","getElementDataIndex","FilterPillProps"],"mappings":"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"}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"useFilterState.js","sources":["../../src/custom-filters/useFilterState.ts"],"sourcesContent":["import { useCallback } from \"react\";\nimport { Filter, FilterState } from \"@vuu-ui/vuu-filter-types\";\nimport { useControlled } from \"@vuu-ui/vuu-ui-controls\";\n\nexport interface FiltersHookProps {\n defaultFilterState?: FilterState;\n filterState?: FilterState;\n onFilterDeleted?: (filter: Filter) => void;\n onFilterRenamed?: (filter: Filter, name: string) => void;\n onFilterStateChanged?: (s: FilterState) => void;\n}\n\nconst getActiveIndices = (\n indices: number[],\n toggledIndex: number,\n preserveExisting: boolean,\n) => {\n const isActive = indices.includes(toggledIndex);\n if (isActive) {\n if (preserveExisting) {\n return indices.filter((i) => i !== toggledIndex);\n } else {\n return [];\n }\n } else {\n if (preserveExisting) {\n return indices.concat(toggledIndex);\n } else {\n return [toggledIndex];\n }\n }\n};\n\nexport const useFilterState = ({\n defaultFilterState,\n onFilterDeleted,\n onFilterRenamed,\n onFilterStateChanged,\n filterState: filterStateProp,\n}: FiltersHookProps) => {\n const [filterState, setFilterState] = useControlled<FilterState>({\n controlled: filterStateProp,\n default: defaultFilterState ?? { filters: [], activeIndices: [] },\n name: \"useFilterState\",\n state: \"FilterState\",\n });\n\n const handleFilterStateChange = useCallback(\n (s: FilterState) => {\n setFilterState(s);\n onFilterStateChanged?.(s);\n },\n [onFilterStateChanged, setFilterState],\n );\n\n const handleAddFilter = useCallback(\n (filter: Filter) => {\n const index = filterState.filters.length;\n const newFilters = filterState.filters.concat(filter);\n const newIndices = appendIfNotPresent(filterState.activeIndices, index);\n handleFilterStateChange({\n filters: newFilters,\n activeIndices: newIndices,\n });\n return index;\n },\n [filterState, handleFilterStateChange],\n );\n\n const handleDeleteFilter = useCallback(\n (filter: Filter) => {\n let index = -1;\n const newFilters = filterState.filters.filter((f, i) => {\n if (f !== filter) {\n return true;\n } else {\n index = i;\n return false;\n }\n });\n\n const newIndices = removeIndexAndDecrementLarger(\n filterState.activeIndices,\n index,\n );\n\n handleFilterStateChange({\n filters: newFilters,\n activeIndices: newIndices,\n });\n onFilterDeleted?.(filter);\n return index;\n },\n [\n filterState.filters,\n filterState.activeIndices,\n handleFilterStateChange,\n onFilterDeleted,\n ],\n );\n\n const handleRenameFilter = useCallback(\n (filter: Filter, name: string) => {\n let index = -1;\n const newFilters = filterState.filters.map((f, i) => {\n if (f === filter) {\n index = i;\n return { ...filter, name };\n } else {\n return f;\n }\n });\n handleFilterStateChange({ ...filterState, filters: newFilters });\n onFilterRenamed?.(filter, name);\n\n return index;\n },\n [filterState, handleFilterStateChange, onFilterRenamed],\n );\n\n const handleChangeFilter = useCallback(\n (oldFilter: Filter, newFilter: Filter) => {\n let index = -1;\n const newFilters = filterState.filters.map((f, i) => {\n if (f === oldFilter) {\n index = i;\n return newFilter;\n } else {\n return f;\n }\n });\n handleFilterStateChange({ ...filterState, filters: newFilters });\n\n return index;\n },\n [filterState, handleFilterStateChange],\n );\n\n const handleToggleFilterActive = useCallback(\n (filterIndex: number, preserveRemainingFilters = false) => {\n handleFilterStateChange({\n ...filterState,\n activeIndices: getActiveIndices(\n filterState.activeIndices,\n filterIndex,\n preserveRemainingFilters,\n ),\n });\n },\n [filterState, handleFilterStateChange],\n );\n\n return {\n activeFilterIndex: filterState.activeIndices,\n filters: filterState.filters,\n onToggleFilterActive: handleToggleFilterActive,\n onAddFilter: handleAddFilter,\n onChangeFilter: handleChangeFilter,\n onDeleteFilter: handleDeleteFilter,\n onRenameFilter: handleRenameFilter,\n };\n};\n\nconst appendIfNotPresent = (ns: number[], n: number) =>\n ns.includes(n) ? ns : ns.concat(n);\n\nconst removeIndexAndDecrementLarger = (\n indices: number[],\n idxToRemove: number,\n) => {\n return indices.reduce<number[]>((res, i) => {\n if (i === idxToRemove) return res;\n return res.concat(i > idxToRemove ? i - 1 : i);\n }, []);\n};\n"],"names":["useControlled","useCallback"],"mappings":";;;;;AAYA,MAAM,gBAAmB,GAAA,CACvB,OACA,EAAA,YAAA,EACA,gBACG,KAAA;AACH,EAAM,MAAA,QAAA,GAAW,OAAQ,CAAA,QAAA,CAAS,YAAY,CAAA
|
|
1
|
+
{"version":3,"file":"useFilterState.js","sources":["../../src/custom-filters/useFilterState.ts"],"sourcesContent":["import { useCallback } from \"react\";\nimport { Filter, FilterState } from \"@vuu-ui/vuu-filter-types\";\nimport { useControlled } from \"@vuu-ui/vuu-ui-controls\";\n\nexport interface FiltersHookProps {\n defaultFilterState?: FilterState;\n filterState?: FilterState;\n onFilterDeleted?: (filter: Filter) => void;\n onFilterRenamed?: (filter: Filter, name: string) => void;\n onFilterStateChanged?: (s: FilterState) => void;\n}\n\nconst getActiveIndices = (\n indices: number[],\n toggledIndex: number,\n preserveExisting: boolean,\n) => {\n const isActive = indices.includes(toggledIndex);\n if (isActive) {\n if (preserveExisting) {\n return indices.filter((i) => i !== toggledIndex);\n } else {\n return [];\n }\n } else {\n if (preserveExisting) {\n return indices.concat(toggledIndex);\n } else {\n return [toggledIndex];\n }\n }\n};\n\nexport const useFilterState = ({\n defaultFilterState,\n onFilterDeleted,\n onFilterRenamed,\n onFilterStateChanged,\n filterState: filterStateProp,\n}: FiltersHookProps) => {\n const [filterState, setFilterState] = useControlled<FilterState>({\n controlled: filterStateProp,\n default: defaultFilterState ?? { filters: [], activeIndices: [] },\n name: \"useFilterState\",\n state: \"FilterState\",\n });\n\n const handleFilterStateChange = useCallback(\n (s: FilterState) => {\n setFilterState(s);\n onFilterStateChanged?.(s);\n },\n [onFilterStateChanged, setFilterState],\n );\n\n const handleAddFilter = useCallback(\n (filter: Filter) => {\n const index = filterState.filters.length;\n const newFilters = filterState.filters.concat(filter);\n const newIndices = appendIfNotPresent(filterState.activeIndices, index);\n handleFilterStateChange({\n filters: newFilters,\n activeIndices: newIndices,\n });\n return index;\n },\n [filterState, handleFilterStateChange],\n );\n\n const handleDeleteFilter = useCallback(\n (filter: Filter) => {\n let index = -1;\n const newFilters = filterState.filters.filter((f, i) => {\n if (f !== filter) {\n return true;\n } else {\n index = i;\n return false;\n }\n });\n\n const newIndices = removeIndexAndDecrementLarger(\n filterState.activeIndices,\n index,\n );\n\n handleFilterStateChange({\n filters: newFilters,\n activeIndices: newIndices,\n });\n onFilterDeleted?.(filter);\n return index;\n },\n [\n filterState.filters,\n filterState.activeIndices,\n handleFilterStateChange,\n onFilterDeleted,\n ],\n );\n\n const handleRenameFilter = useCallback(\n (filter: Filter, name: string) => {\n let index = -1;\n const newFilters = filterState.filters.map((f, i) => {\n if (f === filter) {\n index = i;\n return { ...filter, name };\n } else {\n return f;\n }\n });\n handleFilterStateChange({ ...filterState, filters: newFilters });\n onFilterRenamed?.(filter, name);\n\n return index;\n },\n [filterState, handleFilterStateChange, onFilterRenamed],\n );\n\n const handleChangeFilter = useCallback(\n (oldFilter: Filter, newFilter: Filter) => {\n let index = -1;\n const newFilters = filterState.filters.map((f, i) => {\n if (f === oldFilter) {\n index = i;\n return newFilter;\n } else {\n return f;\n }\n });\n handleFilterStateChange({ ...filterState, filters: newFilters });\n\n return index;\n },\n [filterState, handleFilterStateChange],\n );\n\n const handleToggleFilterActive = useCallback(\n (filterIndex: number, preserveRemainingFilters = false) => {\n handleFilterStateChange({\n ...filterState,\n activeIndices: getActiveIndices(\n filterState.activeIndices,\n filterIndex,\n preserveRemainingFilters,\n ),\n });\n },\n [filterState, handleFilterStateChange],\n );\n\n return {\n activeFilterIndex: filterState.activeIndices,\n filters: filterState.filters,\n onToggleFilterActive: handleToggleFilterActive,\n onAddFilter: handleAddFilter,\n onChangeFilter: handleChangeFilter,\n onDeleteFilter: handleDeleteFilter,\n onRenameFilter: handleRenameFilter,\n };\n};\n\nconst appendIfNotPresent = (ns: number[], n: number) =>\n ns.includes(n) ? ns : ns.concat(n);\n\nconst removeIndexAndDecrementLarger = (\n indices: number[],\n idxToRemove: number,\n) => {\n return indices.reduce<number[]>((res, i) => {\n if (i === idxToRemove) return res;\n return res.concat(i > idxToRemove ? i - 1 : i);\n }, []);\n};\n"],"names":["useControlled","useCallback"],"mappings":"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"}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"FilterBar.js","sources":["../../src/filter-bar/FilterBar.tsx"],"sourcesContent":["import {\n DataSourceFilter,\n SuggestionProvider,\n TableSchema,\n} from \"@vuu-ui/vuu-data-types\";\nimport { Filter, FilterState } from \"@vuu-ui/vuu-filter-types\";\nimport { ColumnDescriptor } from \"@vuu-ui/vuu-table-types\";\nimport { Icon } from \"@vuu-ui/vuu-ui-controls\";\nimport { ToggleButton, ToggleButtonGroup } from \"@salt-ds/core\";\nimport { useComponentCssInjection } from \"@salt-ds/styles\";\nimport { useWindow } from \"@salt-ds/window\";\nimport cx from \"clsx\";\nimport { HTMLAttributes, useMemo } from \"react\";\nimport { CustomFilters } from \"../custom-filters\";\nimport { QuickFilterProps, QuickFilters } from \"../quick-filters\";\nimport { FilterMode, useFilterBar } from \"./useFilterBar\";\n\nimport filterBarCss from \"./FilterBar.css\";\n\nexport type FilterBarVariant =\n | \"custom-filters-only\"\n | \"quick-filters-only\"\n | \"full-filters\";\n\nexport interface FilterBarProps extends HTMLAttributes<HTMLDivElement> {\n QuickFilterProps?: Pick<\n QuickFilterProps,\n \"quickFilterColumns\" | \"onChangeQuickFilterColumns\"\n >;\n /**\n * This is used to apply tailored filters based on column types and other attributes.\n * NOTE: Always make sure that these are passed with proper re-render optimization, otherwise,\n * might end up with infinite state updates.\n */\n columnDescriptors: ColumnDescriptor[];\n defaultFilterMode?: FilterMode;\n defaultFilterState?: FilterState;\n filterMode?: FilterMode;\n filterState?: FilterState;\n onApplyFilter: (filter: DataSourceFilter) => void;\n onChangeFilterMode?: (filterMode: FilterMode) => void;\n onFilterDeleted?: (filter: Filter) => void;\n onFilterRenamed?: (filter: Filter, name: string) => void;\n onFilterStateChanged?: (state: FilterState) => void;\n suggestionProvider?: SuggestionProvider;\n /**\n * TableSchema is used both to populate list of available columns and to\n * provide table in call to Typeahead service\n */\n tableSchema?: TableSchema;\n variant?: FilterBarVariant;\n}\n\nconst classBase = \"vuuFilterBar\";\n\nexport const FilterBar = ({\n QuickFilterProps,\n className: classNameProp,\n columnDescriptors,\n defaultFilterMode,\n defaultFilterState,\n filterMode: filterModeProp,\n filterState,\n onApplyFilter,\n onChangeFilterMode: onChangeFilterModeProp,\n onFilterDeleted,\n onFilterRenamed,\n onFilterStateChanged,\n suggestionProvider,\n tableSchema,\n variant = \"custom-filters-only\",\n ...htmlAttributes\n}: FilterBarProps) => {\n const targetWindow = useWindow();\n useComponentCssInjection({\n testId: \"vuu-filter-bar\",\n css: filterBarCss,\n window: targetWindow,\n });\n\n const allowCustomFilters = variant !== \"quick-filters-only\";\n const allowQuickFilters = variant !== \"custom-filters-only\";\n\n const controlledFilterMode: FilterMode | undefined = !allowCustomFilters\n ? \"quick-filter\"\n : !allowQuickFilters\n ? \"custom-filter\"\n : filterModeProp;\n\n const { filterMode, onChangeFilterMode } = useFilterBar({\n defaultFilterMode,\n filterMode: controlledFilterMode,\n onChangeFilterMode: onChangeFilterModeProp,\n });\n\n const className = cx(classBase, classNameProp);\n\n const startAdornment = useMemo(() => {\n if (!allowQuickFilters) {\n return <Icon name=\"filter\" size={16} style={{ top: 4 }} />;\n } else {\n return (\n <ToggleButtonGroup\n data-variant=\"secondary\"\n onChange={onChangeFilterMode}\n value={filterMode}\n >\n <ToggleButton\n className=\"vuuIconToggleButton\"\n key=\"custom-filter\"\n value=\"custom-filter\"\n aria-label=\"Custom filters\"\n tabIndex={-1}\n >\n <Icon name=\"grid\" size={16} />\n </ToggleButton>\n <ToggleButton\n className=\"vuuIconToggleButton\"\n key=\"quick-filter\"\n value=\"quick-filter\"\n aria-label=\"Quick filters\"\n tabIndex={-1}\n >\n <Icon name=\"tune\" size={16} />\n </ToggleButton>\n </ToggleButtonGroup>\n );\n }\n }, [allowQuickFilters, filterMode, onChangeFilterMode]);\n\n return (\n <div\n {...htmlAttributes}\n className={cx(className, `${classBase}-${filterMode}-mode`)}\n >\n {variant === \"quick-filters-only\" ? null : (\n <div className={`${classBase}-iconContainer`}>{startAdornment}</div>\n )}\n {filterMode === \"custom-filter\" ? (\n <CustomFilters\n columnDescriptors={columnDescriptors}\n defaultFilterState={defaultFilterState}\n filterState={filterState}\n onApplyFilter={onApplyFilter}\n onFilterDeleted={onFilterDeleted}\n onFilterRenamed={onFilterRenamed}\n onFilterStateChanged={onFilterStateChanged}\n tableSchema={tableSchema}\n />\n ) : (\n <QuickFilters\n {...QuickFilterProps}\n availableColumns={columnDescriptors}\n onApplyFilter={onApplyFilter}\n tableSchema={tableSchema}\n />\n )}\n </div>\n );\n};\n"],"names":["QuickFilterProps","useWindow","useComponentCssInjection","filterBarCss","useFilterBar","useMemo","jsx","Icon","jsxs","ToggleButtonGroup","ToggleButton","CustomFilters","QuickFilters"],"mappings":";;;;;;;;;;;;;;AAqDA,MAAM,SAAY,GAAA,cAAA
|
|
1
|
+
{"version":3,"file":"FilterBar.js","sources":["../../src/filter-bar/FilterBar.tsx"],"sourcesContent":["import {\n DataSourceFilter,\n SuggestionProvider,\n TableSchema,\n} from \"@vuu-ui/vuu-data-types\";\nimport { Filter, FilterState } from \"@vuu-ui/vuu-filter-types\";\nimport { ColumnDescriptor } from \"@vuu-ui/vuu-table-types\";\nimport { Icon } from \"@vuu-ui/vuu-ui-controls\";\nimport { ToggleButton, ToggleButtonGroup } from \"@salt-ds/core\";\nimport { useComponentCssInjection } from \"@salt-ds/styles\";\nimport { useWindow } from \"@salt-ds/window\";\nimport cx from \"clsx\";\nimport { HTMLAttributes, useMemo } from \"react\";\nimport { CustomFilters } from \"../custom-filters\";\nimport { QuickFilterProps, QuickFilters } from \"../quick-filters\";\nimport { FilterMode, useFilterBar } from \"./useFilterBar\";\n\nimport filterBarCss from \"./FilterBar.css\";\n\nexport type FilterBarVariant =\n | \"custom-filters-only\"\n | \"quick-filters-only\"\n | \"full-filters\";\n\nexport interface FilterBarProps extends HTMLAttributes<HTMLDivElement> {\n QuickFilterProps?: Pick<\n QuickFilterProps,\n \"quickFilterColumns\" | \"onChangeQuickFilterColumns\"\n >;\n /**\n * This is used to apply tailored filters based on column types and other attributes.\n * NOTE: Always make sure that these are passed with proper re-render optimization, otherwise,\n * might end up with infinite state updates.\n */\n columnDescriptors: ColumnDescriptor[];\n defaultFilterMode?: FilterMode;\n defaultFilterState?: FilterState;\n filterMode?: FilterMode;\n filterState?: FilterState;\n onApplyFilter: (filter: DataSourceFilter) => void;\n onChangeFilterMode?: (filterMode: FilterMode) => void;\n onFilterDeleted?: (filter: Filter) => void;\n onFilterRenamed?: (filter: Filter, name: string) => void;\n onFilterStateChanged?: (state: FilterState) => void;\n suggestionProvider?: SuggestionProvider;\n /**\n * TableSchema is used both to populate list of available columns and to\n * provide table in call to Typeahead service\n */\n tableSchema?: TableSchema;\n variant?: FilterBarVariant;\n}\n\nconst classBase = \"vuuFilterBar\";\n\nexport const FilterBar = ({\n QuickFilterProps,\n className: classNameProp,\n columnDescriptors,\n defaultFilterMode,\n defaultFilterState,\n filterMode: filterModeProp,\n filterState,\n onApplyFilter,\n onChangeFilterMode: onChangeFilterModeProp,\n onFilterDeleted,\n onFilterRenamed,\n onFilterStateChanged,\n suggestionProvider,\n tableSchema,\n variant = \"custom-filters-only\",\n ...htmlAttributes\n}: FilterBarProps) => {\n const targetWindow = useWindow();\n useComponentCssInjection({\n testId: \"vuu-filter-bar\",\n css: filterBarCss,\n window: targetWindow,\n });\n\n const allowCustomFilters = variant !== \"quick-filters-only\";\n const allowQuickFilters = variant !== \"custom-filters-only\";\n\n const controlledFilterMode: FilterMode | undefined = !allowCustomFilters\n ? \"quick-filter\"\n : !allowQuickFilters\n ? \"custom-filter\"\n : filterModeProp;\n\n const { filterMode, onChangeFilterMode } = useFilterBar({\n defaultFilterMode,\n filterMode: controlledFilterMode,\n onChangeFilterMode: onChangeFilterModeProp,\n });\n\n const className = cx(classBase, classNameProp);\n\n const startAdornment = useMemo(() => {\n if (!allowQuickFilters) {\n return <Icon name=\"filter\" size={16} style={{ top: 4 }} />;\n } else {\n return (\n <ToggleButtonGroup\n data-variant=\"secondary\"\n onChange={onChangeFilterMode}\n value={filterMode}\n >\n <ToggleButton\n className=\"vuuIconToggleButton\"\n key=\"custom-filter\"\n value=\"custom-filter\"\n aria-label=\"Custom filters\"\n tabIndex={-1}\n >\n <Icon name=\"grid\" size={16} />\n </ToggleButton>\n <ToggleButton\n className=\"vuuIconToggleButton\"\n key=\"quick-filter\"\n value=\"quick-filter\"\n aria-label=\"Quick filters\"\n tabIndex={-1}\n >\n <Icon name=\"tune\" size={16} />\n </ToggleButton>\n </ToggleButtonGroup>\n );\n }\n }, [allowQuickFilters, filterMode, onChangeFilterMode]);\n\n return (\n <div\n {...htmlAttributes}\n className={cx(className, `${classBase}-${filterMode}-mode`)}\n >\n {variant === \"quick-filters-only\" ? null : (\n <div className={`${classBase}-iconContainer`}>{startAdornment}</div>\n )}\n {filterMode === \"custom-filter\" ? (\n <CustomFilters\n columnDescriptors={columnDescriptors}\n defaultFilterState={defaultFilterState}\n filterState={filterState}\n onApplyFilter={onApplyFilter}\n onFilterDeleted={onFilterDeleted}\n onFilterRenamed={onFilterRenamed}\n onFilterStateChanged={onFilterStateChanged}\n tableSchema={tableSchema}\n />\n ) : (\n <QuickFilters\n {...QuickFilterProps}\n availableColumns={columnDescriptors}\n onApplyFilter={onApplyFilter}\n tableSchema={tableSchema}\n />\n )}\n </div>\n );\n};\n"],"names":["QuickFilterProps","useWindow","useComponentCssInjection","filterBarCss","useFilterBar","useMemo","jsx","Icon","jsxs","ToggleButtonGroup","ToggleButton","CustomFilters","QuickFilters"],"mappings":"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"}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"useFilterBar.js","sources":["../../src/filter-bar/useFilterBar.ts"],"sourcesContent":["import { queryClosest } from \"@vuu-ui/vuu-utils\";\nimport { useControlled } from \"@salt-ds/core\";\nimport { SyntheticEvent, useCallback } from \"react\";\nimport { FilterBarProps } from \"./FilterBar\";\n\nexport type FilterMode = \"custom-filter\" | \"quick-filter\";\n\nconst isFilterMode = (value?: string | null): value is FilterMode =>\n value === \"custom-filter\" || value === \"quick-filter\";\n\nexport const useFilterBar = ({\n defaultFilterMode,\n filterMode: filterModeProp,\n onChangeFilterMode,\n}: Pick<\n FilterBarProps,\n \"defaultFilterMode\" | \"filterMode\" | \"onChangeFilterMode\"\n>) => {\n const [filterMode, setFilterMode] = useControlled<FilterMode>({\n controlled: filterModeProp,\n default: defaultFilterMode ?? \"custom-filter\",\n name: \"useFilterBar\",\n state: \"filterMode\",\n });\n\n const handleChangeFilterMode = useCallback(\n (e: SyntheticEvent<HTMLButtonElement>) => {\n const button = queryClosest<HTMLButtonElement>(e.target, \"button\");\n const newFilterMode = button?.value;\n if (isFilterMode(newFilterMode)) {\n setFilterMode(newFilterMode);\n onChangeFilterMode?.(newFilterMode);\n }\n },\n [onChangeFilterMode, setFilterMode],\n );\n\n return {\n filterMode,\n onChangeFilterMode: handleChangeFilterMode,\n };\n};\n"],"names":["useControlled","useCallback","queryClosest"],"mappings":";;;;;;AAOA,MAAM,YAAe,GAAA,CAAC,KACpB,KAAA,KAAA,KAAU,mBAAmB,KAAU,KAAA,cAAA
|
|
1
|
+
{"version":3,"file":"useFilterBar.js","sources":["../../src/filter-bar/useFilterBar.ts"],"sourcesContent":["import { queryClosest } from \"@vuu-ui/vuu-utils\";\nimport { useControlled } from \"@salt-ds/core\";\nimport { SyntheticEvent, useCallback } from \"react\";\nimport { FilterBarProps } from \"./FilterBar\";\n\nexport type FilterMode = \"custom-filter\" | \"quick-filter\";\n\nconst isFilterMode = (value?: string | null): value is FilterMode =>\n value === \"custom-filter\" || value === \"quick-filter\";\n\nexport const useFilterBar = ({\n defaultFilterMode,\n filterMode: filterModeProp,\n onChangeFilterMode,\n}: Pick<\n FilterBarProps,\n \"defaultFilterMode\" | \"filterMode\" | \"onChangeFilterMode\"\n>) => {\n const [filterMode, setFilterMode] = useControlled<FilterMode>({\n controlled: filterModeProp,\n default: defaultFilterMode ?? \"custom-filter\",\n name: \"useFilterBar\",\n state: \"filterMode\",\n });\n\n const handleChangeFilterMode = useCallback(\n (e: SyntheticEvent<HTMLButtonElement>) => {\n const button = queryClosest<HTMLButtonElement>(e.target, \"button\");\n const newFilterMode = button?.value;\n if (isFilterMode(newFilterMode)) {\n setFilterMode(newFilterMode);\n onChangeFilterMode?.(newFilterMode);\n }\n },\n [onChangeFilterMode, setFilterMode],\n );\n\n return {\n filterMode,\n onChangeFilterMode: handleChangeFilterMode,\n };\n};\n"],"names":["useControlled","useCallback","queryClosest"],"mappings":";;;;;;AAOA,MAAM,YAAe,GAAA,CAAC,KACpB,KAAA,KAAA,KAAU,mBAAmB,KAAU,KAAA,cAAA;AAElC,MAAM,eAAe,CAAC;AAAA,EAC3B,iBAAA;AAAA,EACA,UAAY,EAAA,cAAA;AAAA,EACZ;AACF,CAGM,KAAA;AACJ,EAAA,MAAM,CAAC,UAAA,EAAY,aAAa,CAAA,GAAIA,kBAA0B,CAAA;AAAA,IAC5D,UAAY,EAAA,cAAA;AAAA,IACZ,SAAS,iBAAqB,IAAA,eAAA;AAAA,IAC9B,IAAM,EAAA,cAAA;AAAA,IACN,KAAO,EAAA;AAAA,GACR,CAAA;AAED,EAAA,MAAM,sBAAyB,GAAAC,iBAAA;AAAA,IAC7B,CAAC,CAAyC,KAAA;AACxC,MAAA,MAAM,MAAS,GAAAC,qBAAA,CAAgC,CAAE,CAAA,MAAA,EAAQ,QAAQ,CAAA;AACjE,MAAA,MAAM,gBAAgB,MAAQ,EAAA,KAAA;AAC9B,MAAI,IAAA,YAAA,CAAa,aAAa,CAAG,EAAA;AAC/B,QAAA,aAAA,CAAc,aAAa,CAAA;AAC3B,QAAA,kBAAA,GAAqB,aAAa,CAAA;AAAA;AACpC,KACF;AAAA,IACA,CAAC,oBAAoB,aAAa;AAAA,GACpC;AAEA,EAAO,OAAA;AAAA,IACL,UAAA;AAAA,IACA,kBAAoB,EAAA;AAAA,GACtB;AACF;;;;"}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"ColumnPicker.js","sources":["../../src/filter-clause/ColumnPicker.tsx"],"sourcesContent":["import type { ColumnDescriptor } from \"@vuu-ui/vuu-table-types\";\nimport { ExpandoCombobox } from \"./ExpandoCombobox\";\nimport { ComboBoxProps, Option } from \"@salt-ds/core\";\nimport { ForwardedRef, SyntheticEvent, forwardRef } from \"react\";\n\nexport type ColumnPickerProps = Pick<\n ComboBoxProps,\n \"className\" | \"inputProps\" | \"value\"\n> & {\n columns: ColumnDescriptor[];\n onSelect: (evt: SyntheticEvent, columnName: string) => void;\n};\n\nexport const ColumnPicker = forwardRef(function ColumnPicker(\n { className, columns, inputProps, onSelect, value }: ColumnPickerProps,\n forwardedRef: ForwardedRef<HTMLDivElement>,\n) {\n const handleSelectionChange = (\n evt: SyntheticEvent,\n newSelected: string[],\n ) => {\n onSelect(evt, newSelected[0]);\n };\n\n return (\n <ExpandoCombobox\n inputProps={inputProps}\n className={className}\n data-field=\"column\"\n onSelectionChange={handleSelectionChange}\n ref={forwardedRef}\n title=\"column\"\n value={value}\n >\n {columns.map(({ name }) => (\n <Option value={name} key={name} />\n ))}\n </ExpandoCombobox>\n );\n});\n"],"names":["forwardRef","ColumnPicker","jsx","ExpandoCombobox","Option"],"mappings":";;;;;;;AAaa,MAAA,YAAA,GAAeA,gBAAW,CAAA,SAASC,aAC9C,CAAA,EAAE,SAAW,EAAA,OAAA,EAAS,UAAY,EAAA,QAAA,EAAU,KAAM,EAAA,EAClD,YACA,EAAA;AACA,EAAM,MAAA,qBAAA,GAAwB,CAC5B,GAAA,EACA,WACG,KAAA;AACH,IAAS,QAAA,CAAA,GAAA,EAAK,WAAY,CAAA,CAAC,CAAC,CAAA
|
|
1
|
+
{"version":3,"file":"ColumnPicker.js","sources":["../../src/filter-clause/ColumnPicker.tsx"],"sourcesContent":["import type { ColumnDescriptor } from \"@vuu-ui/vuu-table-types\";\nimport { ExpandoCombobox } from \"./ExpandoCombobox\";\nimport { ComboBoxProps, Option } from \"@salt-ds/core\";\nimport { ForwardedRef, SyntheticEvent, forwardRef } from \"react\";\n\nexport type ColumnPickerProps = Pick<\n ComboBoxProps,\n \"className\" | \"inputProps\" | \"value\"\n> & {\n columns: ColumnDescriptor[];\n onSelect: (evt: SyntheticEvent, columnName: string) => void;\n};\n\nexport const ColumnPicker = forwardRef(function ColumnPicker(\n { className, columns, inputProps, onSelect, value }: ColumnPickerProps,\n forwardedRef: ForwardedRef<HTMLDivElement>,\n) {\n const handleSelectionChange = (\n evt: SyntheticEvent,\n newSelected: string[],\n ) => {\n onSelect(evt, newSelected[0]);\n };\n\n return (\n <ExpandoCombobox\n inputProps={inputProps}\n className={className}\n data-field=\"column\"\n onSelectionChange={handleSelectionChange}\n ref={forwardedRef}\n title=\"column\"\n value={value}\n >\n {columns.map(({ name }) => (\n <Option value={name} key={name} />\n ))}\n </ExpandoCombobox>\n );\n});\n"],"names":["forwardRef","ColumnPicker","jsx","ExpandoCombobox","Option"],"mappings":";;;;;;;AAaa,MAAA,YAAA,GAAeA,gBAAW,CAAA,SAASC,aAC9C,CAAA,EAAE,SAAW,EAAA,OAAA,EAAS,UAAY,EAAA,QAAA,EAAU,KAAM,EAAA,EAClD,YACA,EAAA;AACA,EAAM,MAAA,qBAAA,GAAwB,CAC5B,GAAA,EACA,WACG,KAAA;AACH,IAAS,QAAA,CAAA,GAAA,EAAK,WAAY,CAAA,CAAC,CAAC,CAAA;AAAA,GAC9B;AAEA,EACE,uBAAAC,cAAA;AAAA,IAACC,+BAAA;AAAA,IAAA;AAAA,MACC,UAAA;AAAA,MACA,SAAA;AAAA,MACA,YAAW,EAAA,QAAA;AAAA,MACX,iBAAmB,EAAA,qBAAA;AAAA,MACnB,GAAK,EAAA,YAAA;AAAA,MACL,KAAM,EAAA,QAAA;AAAA,MACN,KAAA;AAAA,MAEC,QAAA,EAAA,OAAA,CAAQ,GAAI,CAAA,CAAC,EAAE,IAAA,EACd,qBAAAD,cAAA,CAACE,WAAO,EAAA,EAAA,KAAA,EAAO,IAAW,EAAA,EAAA,IAAM,CACjC;AAAA;AAAA,GACH;AAEJ,CAAC;;;;"}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"ExpandoCombobox.js","sources":["../../src/filter-clause/ExpandoCombobox.tsx"],"sourcesContent":["import cx from \"clsx\";\nimport { ComboBox, ComboBoxProps } from \"@salt-ds/core\";\nimport {\n ChangeEvent,\n ForwardedRef,\n Ref,\n SyntheticEvent,\n forwardRef,\n useMemo,\n useState,\n} from \"react\";\nimport { useComponentCssInjection } from \"@salt-ds/styles\";\nimport { useWindow } from \"@salt-ds/window\";\n\nimport expandoComboboxCss from \"./ExpandoCombobox.css\";\n\nconst classBase = \"vuuExpandoCombobox\";\n\nexport interface ExpandoComboboxProps<Item = string>\n extends ComboBoxProps<Item> {\n itemToString?: (item: Item) => string;\n}\n\nconst defaultItemToString = (item: unknown) => {\n if (typeof item === \"string\") {\n return item;\n } else {\n return item?.toString() ?? \"\";\n }\n};\nexport const ExpandoCombobox = forwardRef(function ExpandoCombobox<\n Item = string\n>(\n {\n children,\n className,\n inputProps: inputPropsProp,\n itemToString = defaultItemToString,\n multiselect,\n onChange,\n onSelectionChange,\n value: valueProp,\n ...props\n }: ExpandoComboboxProps<Item>,\n forwardedRef: ForwardedRef<HTMLDivElement>\n) {\n const targetWindow = useWindow();\n useComponentCssInjection({\n testId: \"vuu-expando-combobox\",\n css: expandoComboboxCss,\n window: targetWindow,\n });\n\n const [open, setOpen] = useState(false);\n const [value, setValue] = useState(\n valueProp === undefined ? \"\" : valueProp.toString()\n );\n\n const handleChange = (evt: ChangeEvent<HTMLInputElement>) => {\n const value = evt.target.value;\n onChange?.(evt);\n setValue(value);\n };\n\n const handleSelectionChange = (evt: SyntheticEvent, newSelected: Item[]) => {\n if (multiselect) {\n onSelectionChange?.(evt, newSelected);\n } else {\n const [selectedValue] = newSelected;\n setTimeout(() => {\n onSelectionChange?.(evt, newSelected);\n setValue(itemToString(selectedValue));\n }, 100);\n }\n };\n\n const inputProps = useMemo<ComboBoxProps<Item>[\"inputProps\"]>(() => {\n return {\n autoComplete: \"off\",\n ...inputPropsProp,\n onFocus: (evt) => {\n inputPropsProp?.onFocus?.(evt);\n setTimeout(() => {\n setOpen(true);\n }, 100);\n },\n };\n }, [inputPropsProp]);\n\n // const matchingValues = values.filter((val) =>\n // val.toLowerCase().startsWith(value.trim().toLowerCase())\n // );\n\n return (\n <div\n className={cx(classBase, className)}\n data-text={value}\n ref={forwardedRef}\n >\n <ComboBox<Item>\n {...props}\n inputProps={inputProps}\n multiselect={multiselect}\n onChange={handleChange}\n onOpenChange={setOpen}\n onSelectionChange={handleSelectionChange}\n open={open}\n value={value}\n >\n {children}\n </ComboBox>\n </div>\n );\n}) as <Item = string>(\n props: ExpandoComboboxProps<Item> & { ref?: Ref<HTMLDivElement> }\n) => JSX.Element;\n"],"names":["forwardRef","ExpandoCombobox","useWindow","useComponentCssInjection","expandoComboboxCss","useState","value","useMemo","jsx","ComboBox"],"mappings":";;;;;;;;;;AAgBA,MAAM,SAAY,GAAA,oBAAA
|
|
1
|
+
{"version":3,"file":"ExpandoCombobox.js","sources":["../../src/filter-clause/ExpandoCombobox.tsx"],"sourcesContent":["import cx from \"clsx\";\nimport { ComboBox, ComboBoxProps } from \"@salt-ds/core\";\nimport {\n ChangeEvent,\n ForwardedRef,\n Ref,\n SyntheticEvent,\n forwardRef,\n useMemo,\n useState,\n} from \"react\";\nimport { useComponentCssInjection } from \"@salt-ds/styles\";\nimport { useWindow } from \"@salt-ds/window\";\n\nimport expandoComboboxCss from \"./ExpandoCombobox.css\";\n\nconst classBase = \"vuuExpandoCombobox\";\n\nexport interface ExpandoComboboxProps<Item = string>\n extends ComboBoxProps<Item> {\n itemToString?: (item: Item) => string;\n}\n\nconst defaultItemToString = (item: unknown) => {\n if (typeof item === \"string\") {\n return item;\n } else {\n return item?.toString() ?? \"\";\n }\n};\nexport const ExpandoCombobox = forwardRef(function ExpandoCombobox<\n Item = string\n>(\n {\n children,\n className,\n inputProps: inputPropsProp,\n itemToString = defaultItemToString,\n multiselect,\n onChange,\n onSelectionChange,\n value: valueProp,\n ...props\n }: ExpandoComboboxProps<Item>,\n forwardedRef: ForwardedRef<HTMLDivElement>\n) {\n const targetWindow = useWindow();\n useComponentCssInjection({\n testId: \"vuu-expando-combobox\",\n css: expandoComboboxCss,\n window: targetWindow,\n });\n\n const [open, setOpen] = useState(false);\n const [value, setValue] = useState(\n valueProp === undefined ? \"\" : valueProp.toString()\n );\n\n const handleChange = (evt: ChangeEvent<HTMLInputElement>) => {\n const value = evt.target.value;\n onChange?.(evt);\n setValue(value);\n };\n\n const handleSelectionChange = (evt: SyntheticEvent, newSelected: Item[]) => {\n if (multiselect) {\n onSelectionChange?.(evt, newSelected);\n } else {\n const [selectedValue] = newSelected;\n setTimeout(() => {\n onSelectionChange?.(evt, newSelected);\n setValue(itemToString(selectedValue));\n }, 100);\n }\n };\n\n const inputProps = useMemo<ComboBoxProps<Item>[\"inputProps\"]>(() => {\n return {\n autoComplete: \"off\",\n ...inputPropsProp,\n onFocus: (evt) => {\n inputPropsProp?.onFocus?.(evt);\n setTimeout(() => {\n setOpen(true);\n }, 100);\n },\n };\n }, [inputPropsProp]);\n\n // const matchingValues = values.filter((val) =>\n // val.toLowerCase().startsWith(value.trim().toLowerCase())\n // );\n\n return (\n <div\n className={cx(classBase, className)}\n data-text={value}\n ref={forwardedRef}\n >\n <ComboBox<Item>\n {...props}\n inputProps={inputProps}\n multiselect={multiselect}\n onChange={handleChange}\n onOpenChange={setOpen}\n onSelectionChange={handleSelectionChange}\n open={open}\n value={value}\n >\n {children}\n </ComboBox>\n </div>\n );\n}) as <Item = string>(\n props: ExpandoComboboxProps<Item> & { ref?: Ref<HTMLDivElement> }\n) => JSX.Element;\n"],"names":["forwardRef","ExpandoCombobox","useWindow","useComponentCssInjection","expandoComboboxCss","useState","value","useMemo","jsx","ComboBox"],"mappings":";;;;;;;;;;AAgBA,MAAM,SAAY,GAAA,oBAAA;AAOlB,MAAM,mBAAA,GAAsB,CAAC,IAAkB,KAAA;AAC7C,EAAI,IAAA,OAAO,SAAS,QAAU,EAAA;AAC5B,IAAO,OAAA,IAAA;AAAA,GACF,MAAA;AACL,IAAO,OAAA,IAAA,EAAM,UAAc,IAAA,EAAA;AAAA;AAE/B,CAAA;AACa,MAAA,eAAA,GAAkBA,gBAAW,CAAA,SAASC,gBAGjD,CAAA;AAAA,EACE,QAAA;AAAA,EACA,SAAA;AAAA,EACA,UAAY,EAAA,cAAA;AAAA,EACZ,YAAe,GAAA,mBAAA;AAAA,EACf,WAAA;AAAA,EACA,QAAA;AAAA,EACA,iBAAA;AAAA,EACA,KAAO,EAAA,SAAA;AAAA,EACP,GAAG;AACL,CAAA,EACA,YACA,EAAA;AACA,EAAA,MAAM,eAAeC,gBAAU,EAAA;AAC/B,EAAyBC,+BAAA,CAAA;AAAA,IACvB,MAAQ,EAAA,sBAAA;AAAA,IACR,GAAK,EAAAC,iBAAA;AAAA,IACL,MAAQ,EAAA;AAAA,GACT,CAAA;AAED,EAAA,MAAM,CAAC,IAAA,EAAM,OAAO,CAAA,GAAIC,eAAS,KAAK,CAAA;AACtC,EAAM,MAAA,CAAC,KAAO,EAAA,QAAQ,CAAI,GAAAA,cAAA;AAAA,IACxB,SAAc,KAAA,KAAA,CAAA,GAAY,EAAK,GAAA,SAAA,CAAU,QAAS;AAAA,GACpD;AAEA,EAAM,MAAA,YAAA,GAAe,CAAC,GAAuC,KAAA;AAC3D,IAAMC,MAAAA,MAAAA,GAAQ,IAAI,MAAO,CAAA,KAAA;AACzB,IAAA,QAAA,GAAW,GAAG,CAAA;AACd,IAAA,QAAA,CAASA,MAAK,CAAA;AAAA,GAChB;AAEA,EAAM,MAAA,qBAAA,GAAwB,CAAC,GAAA,EAAqB,WAAwB,KAAA;AAC1E,IAAA,IAAI,WAAa,EAAA;AACf,MAAA,iBAAA,GAAoB,KAAK,WAAW,CAAA;AAAA,KAC/B,MAAA;AACL,MAAM,MAAA,CAAC,aAAa,CAAI,GAAA,WAAA;AACxB,MAAA,UAAA,CAAW,MAAM;AACf,QAAA,iBAAA,GAAoB,KAAK,WAAW,CAAA;AACpC,QAAS,QAAA,CAAA,YAAA,CAAa,aAAa,CAAC,CAAA;AAAA,SACnC,GAAG,CAAA;AAAA;AACR,GACF;AAEA,EAAM,MAAA,UAAA,GAAaC,cAA2C,MAAM;AAClE,IAAO,OAAA;AAAA,MACL,YAAc,EAAA,KAAA;AAAA,MACd,GAAG,cAAA;AAAA,MACH,OAAA,EAAS,CAAC,GAAQ,KAAA;AAChB,QAAA,cAAA,EAAgB,UAAU,GAAG,CAAA;AAC7B,QAAA,UAAA,CAAW,MAAM;AACf,UAAA,OAAA,CAAQ,IAAI,CAAA;AAAA,WACX,GAAG,CAAA;AAAA;AACR,KACF;AAAA,GACF,EAAG,CAAC,cAAc,CAAC,CAAA;AAMnB,EACE,uBAAAC,cAAA;AAAA,IAAC,KAAA;AAAA,IAAA;AAAA,MACC,SAAA,EAAW,EAAG,CAAA,SAAA,EAAW,SAAS,CAAA;AAAA,MAClC,WAAW,EAAA,KAAA;AAAA,MACX,GAAK,EAAA,YAAA;AAAA,MAEL,QAAA,kBAAAA,cAAA;AAAA,QAACC,aAAA;AAAA,QAAA;AAAA,UACE,GAAG,KAAA;AAAA,UACJ,UAAA;AAAA,UACA,WAAA;AAAA,UACA,QAAU,EAAA,YAAA;AAAA,UACV,YAAc,EAAA,OAAA;AAAA,UACd,iBAAmB,EAAA,qBAAA;AAAA,UACnB,IAAA;AAAA,UACA,KAAA;AAAA,UAEC;AAAA;AAAA;AACH;AAAA,GACF;AAEJ,CAAC;;;;"}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"FilterClause.js","sources":["../../src/filter-clause/FilterClause.tsx"],"sourcesContent":["import type { TableSchema } from \"@vuu-ui/vuu-data-types\";\nimport {\n ColumnDescriptorsByName,\n MultiValueFilterClause,\n SingleValueFilterClause,\n} from \"@vuu-ui/vuu-filter-types\";\nimport { CloseReason } from \"@vuu-ui/vuu-ui-controls\";\nimport { useComponentCssInjection } from \"@salt-ds/styles\";\nimport { useWindow } from \"@salt-ds/window\";\nimport cx from \"clsx\";\nimport { HTMLAttributes, useMemo } from \"react\";\nimport { FilterClauseModel } from \"../FilterModel\";\nimport { useFilterClause } from \"./useFilterClause\";\nimport { FilterClauseValueEditor } from \"./value-editors/FilterClauseValueEditor\";\nimport { ColumnPicker } from \"./ColumnPicker\";\n\nimport filterClauseCss from \"./FilterClause.css\";\nimport { OperatorPicker } from \"./OperatorPicker\";\n\nexport type FilterClauseCancelType = \"Backspace\" | \"Escape\";\nexport type FilterClauseCancelHandler = (\n filterClause: FilterClauseModel,\n reason: FilterClauseCancelType,\n) => void;\n\nexport interface FilterClauseProps\n extends Omit<HTMLAttributes<HTMLDivElement>, \"onChange\"> {\n columnsByName: ColumnDescriptorsByName;\n filterClauseModel: FilterClauseModel;\n onCancel?: FilterClauseCancelHandler;\n onDropdownClose?: (closeReason: CloseReason) => void;\n onDropdownOpen?: () => void;\n onFocusSave?: () => void;\n tableSchema: TableSchema;\n}\n\nconst classBase = \"vuuFilterClause\";\n\nexport const FilterClause = ({\n className,\n columnsByName,\n onCancel,\n onDropdownClose,\n onDropdownOpen,\n onFocusSave,\n filterClauseModel,\n tableSchema,\n ...htmlAttributes\n}: FilterClauseProps) => {\n const {\n inputProps,\n columnRef,\n filterClause,\n onChangeValue,\n onSelectColumn,\n onSelectOperator,\n onDeselectValue,\n operatorRef,\n selectedColumn,\n valueRef,\n } = useFilterClause({\n filterClauseModel,\n onCancel,\n onFocusSave,\n columnsByName,\n });\n\n const targetWindow = useWindow();\n useComponentCssInjection({\n testId: \"vuu-filter-clause\",\n css: filterClauseCss,\n window: targetWindow,\n });\n\n const columns = useMemo(() => Object.values(columnsByName), [columnsByName]);\n\n return (\n <div className={cx(classBase, className)} {...htmlAttributes} tabIndex={0}>\n <ColumnPicker\n inputProps={inputProps}\n className={cx(`${classBase}Field`, `${classBase}Column`)}\n columns={columns}\n key=\"column-field\"\n onSelect={onSelectColumn}\n ref={columnRef}\n value={filterClauseModel.column ?? \"\"}\n />\n {selectedColumn?.name ? (\n <OperatorPicker\n column={selectedColumn}\n inputProps={inputProps}\n className={cx(`${classBase}Field`, `${classBase}Operator`, {\n [`${classBase}Operator-hidden`]: selectedColumn === null,\n })}\n key=\"operator-field\"\n onSelect={onSelectOperator}\n ref={operatorRef}\n value={filterClauseModel.op ?? \"\"}\n />\n ) : null}\n {filterClauseModel.op ? (\n <FilterClauseValueEditor\n inputProps={inputProps}\n key=\"value-field\"\n onChangeValue={onChangeValue}\n onDeselectValue={onDeselectValue}\n operator={filterClauseModel.op}\n ref={valueRef}\n selectedColumn={selectedColumn}\n table={tableSchema.table}\n value={\n (filterClause as MultiValueFilterClause)?.values ??\n (filterClause as SingleValueFilterClause)?.value\n }\n />\n ) : null}\n </div>\n );\n};\n"],"names":["useFilterClause","useWindow","useComponentCssInjection","filterClauseCss","useMemo","jsxs","jsx","ColumnPicker","OperatorPicker","FilterClauseValueEditor"],"mappings":";;;;;;;;;;;;;AAoCA,MAAM,SAAY,GAAA,iBAAA
|
|
1
|
+
{"version":3,"file":"FilterClause.js","sources":["../../src/filter-clause/FilterClause.tsx"],"sourcesContent":["import type { TableSchema } from \"@vuu-ui/vuu-data-types\";\nimport {\n ColumnDescriptorsByName,\n MultiValueFilterClause,\n SingleValueFilterClause,\n} from \"@vuu-ui/vuu-filter-types\";\nimport { CloseReason } from \"@vuu-ui/vuu-ui-controls\";\nimport { useComponentCssInjection } from \"@salt-ds/styles\";\nimport { useWindow } from \"@salt-ds/window\";\nimport cx from \"clsx\";\nimport { HTMLAttributes, useMemo } from \"react\";\nimport { FilterClauseModel } from \"../FilterModel\";\nimport { useFilterClause } from \"./useFilterClause\";\nimport { FilterClauseValueEditor } from \"./value-editors/FilterClauseValueEditor\";\nimport { ColumnPicker } from \"./ColumnPicker\";\n\nimport filterClauseCss from \"./FilterClause.css\";\nimport { OperatorPicker } from \"./OperatorPicker\";\n\nexport type FilterClauseCancelType = \"Backspace\" | \"Escape\";\nexport type FilterClauseCancelHandler = (\n filterClause: FilterClauseModel,\n reason: FilterClauseCancelType,\n) => void;\n\nexport interface FilterClauseProps\n extends Omit<HTMLAttributes<HTMLDivElement>, \"onChange\"> {\n columnsByName: ColumnDescriptorsByName;\n filterClauseModel: FilterClauseModel;\n onCancel?: FilterClauseCancelHandler;\n onDropdownClose?: (closeReason: CloseReason) => void;\n onDropdownOpen?: () => void;\n onFocusSave?: () => void;\n tableSchema: TableSchema;\n}\n\nconst classBase = \"vuuFilterClause\";\n\nexport const FilterClause = ({\n className,\n columnsByName,\n onCancel,\n onDropdownClose,\n onDropdownOpen,\n onFocusSave,\n filterClauseModel,\n tableSchema,\n ...htmlAttributes\n}: FilterClauseProps) => {\n const {\n inputProps,\n columnRef,\n filterClause,\n onChangeValue,\n onSelectColumn,\n onSelectOperator,\n onDeselectValue,\n operatorRef,\n selectedColumn,\n valueRef,\n } = useFilterClause({\n filterClauseModel,\n onCancel,\n onFocusSave,\n columnsByName,\n });\n\n const targetWindow = useWindow();\n useComponentCssInjection({\n testId: \"vuu-filter-clause\",\n css: filterClauseCss,\n window: targetWindow,\n });\n\n const columns = useMemo(() => Object.values(columnsByName), [columnsByName]);\n\n return (\n <div className={cx(classBase, className)} {...htmlAttributes} tabIndex={0}>\n <ColumnPicker\n inputProps={inputProps}\n className={cx(`${classBase}Field`, `${classBase}Column`)}\n columns={columns}\n key=\"column-field\"\n onSelect={onSelectColumn}\n ref={columnRef}\n value={filterClauseModel.column ?? \"\"}\n />\n {selectedColumn?.name ? (\n <OperatorPicker\n column={selectedColumn}\n inputProps={inputProps}\n className={cx(`${classBase}Field`, `${classBase}Operator`, {\n [`${classBase}Operator-hidden`]: selectedColumn === null,\n })}\n key=\"operator-field\"\n onSelect={onSelectOperator}\n ref={operatorRef}\n value={filterClauseModel.op ?? \"\"}\n />\n ) : null}\n {filterClauseModel.op ? (\n <FilterClauseValueEditor\n inputProps={inputProps}\n key=\"value-field\"\n onChangeValue={onChangeValue}\n onDeselectValue={onDeselectValue}\n operator={filterClauseModel.op}\n ref={valueRef}\n selectedColumn={selectedColumn}\n table={tableSchema.table}\n value={\n (filterClause as MultiValueFilterClause)?.values ??\n (filterClause as SingleValueFilterClause)?.value\n }\n />\n ) : null}\n </div>\n );\n};\n"],"names":["useFilterClause","useWindow","useComponentCssInjection","filterClauseCss","useMemo","jsxs","jsx","ColumnPicker","OperatorPicker","FilterClauseValueEditor"],"mappings":";;;;;;;;;;;;;AAoCA,MAAM,SAAY,GAAA,iBAAA;AAEX,MAAM,eAAe,CAAC;AAAA,EAC3B,SAAA;AAAA,EACA,aAAA;AAAA,EACA,QAAA;AAAA,EACA,eAAA;AAAA,EACA,cAAA;AAAA,EACA,WAAA;AAAA,EACA,iBAAA;AAAA,EACA,WAAA;AAAA,EACA,GAAG;AACL,CAAyB,KAAA;AACvB,EAAM,MAAA;AAAA,IACJ,UAAA;AAAA,IACA,SAAA;AAAA,IACA,YAAA;AAAA,IACA,aAAA;AAAA,IACA,cAAA;AAAA,IACA,gBAAA;AAAA,IACA,eAAA;AAAA,IACA,WAAA;AAAA,IACA,cAAA;AAAA,IACA;AAAA,MACEA,+BAAgB,CAAA;AAAA,IAClB,iBAAA;AAAA,IACA,QAAA;AAAA,IACA,WAAA;AAAA,IACA;AAAA,GACD,CAAA;AAED,EAAA,MAAM,eAAeC,gBAAU,EAAA;AAC/B,EAAyBC,+BAAA,CAAA;AAAA,IACvB,MAAQ,EAAA,mBAAA;AAAA,IACR,GAAK,EAAAC,cAAA;AAAA,IACL,MAAQ,EAAA;AAAA,GACT,CAAA;AAED,EAAM,MAAA,OAAA,GAAUC,cAAQ,MAAM,MAAA,CAAO,OAAO,aAAa,CAAA,EAAG,CAAC,aAAa,CAAC,CAAA;AAE3E,EACE,uBAAAC,eAAA,CAAC,KAAI,EAAA,EAAA,SAAA,EAAW,EAAG,CAAA,SAAA,EAAW,SAAS,CAAI,EAAA,GAAG,cAAgB,EAAA,QAAA,EAAU,CACtE,EAAA,QAAA,EAAA;AAAA,oBAAAC,cAAA;AAAA,MAACC,yBAAA;AAAA,MAAA;AAAA,QACC,UAAA;AAAA,QACA,WAAW,EAAG,CAAA,CAAA,EAAG,SAAS,CAAS,KAAA,CAAA,EAAA,CAAA,EAAG,SAAS,CAAQ,MAAA,CAAA,CAAA;AAAA,QACvD,OAAA;AAAA,QAEA,QAAU,EAAA,cAAA;AAAA,QACV,GAAK,EAAA,SAAA;AAAA,QACL,KAAA,EAAO,kBAAkB,MAAU,IAAA;AAAA,OAAA;AAAA,MAH/B;AAAA,KAIN;AAAA,IACC,gBAAgB,IACf,mBAAAD,cAAA;AAAA,MAACE,6BAAA;AAAA,MAAA;AAAA,QACC,MAAQ,EAAA,cAAA;AAAA,QACR,UAAA;AAAA,QACA,WAAW,EAAG,CAAA,CAAA,EAAG,SAAS,CAAS,KAAA,CAAA,EAAA,CAAA,EAAG,SAAS,CAAY,QAAA,CAAA,EAAA;AAAA,UACzD,CAAC,CAAA,EAAG,SAAS,CAAA,eAAA,CAAiB,GAAG,cAAmB,KAAA;AAAA,SACrD,CAAA;AAAA,QAED,QAAU,EAAA,gBAAA;AAAA,QACV,GAAK,EAAA,WAAA;AAAA,QACL,KAAA,EAAO,kBAAkB,EAAM,IAAA;AAAA,OAAA;AAAA,MAH3B;AAAA,KAKJ,GAAA,IAAA;AAAA,IACH,kBAAkB,EACjB,mBAAAF,cAAA;AAAA,MAACG,+CAAA;AAAA,MAAA;AAAA,QACC,UAAA;AAAA,QAEA,aAAA;AAAA,QACA,eAAA;AAAA,QACA,UAAU,iBAAkB,CAAA,EAAA;AAAA,QAC5B,GAAK,EAAA,QAAA;AAAA,QACL,cAAA;AAAA,QACA,OAAO,WAAY,CAAA,KAAA;AAAA,QACnB,KAAA,EACG,YAAyC,EAAA,MAAA,IACzC,YAA0C,EAAA;AAAA,OAAA;AAAA,MATzC;AAAA,KAYJ,GAAA;AAAA,GACN,EAAA,CAAA;AAEJ;;;;"}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"OperatorPicker.js","sources":["../../src/filter-clause/OperatorPicker.tsx"],"sourcesContent":["import type { FilterClauseOp } from \"@vuu-ui/vuu-filter-types\";\nimport type { ColumnDescriptor } from \"@vuu-ui/vuu-table-types\";\nimport { isValidFilterClauseOp } from \"@vuu-ui/vuu-utils\";\nimport { ComboBoxProps, Option } from \"@salt-ds/core\";\nimport { ForwardedRef, SyntheticEvent, forwardRef } from \"react\";\nimport { ExpandoCombobox } from \"./ExpandoCombobox\";\nimport { getOperators } from \"./operator-utils\";\n\nexport type OperatorPickerProps = Pick<\n ComboBoxProps,\n \"className\" | \"inputProps\" | \"value\"\n> & {\n column: ColumnDescriptor;\n onSelect: (evt: SyntheticEvent, operator: FilterClauseOp) => void;\n};\n\nexport const OperatorPicker = forwardRef(function ColumnPicker(\n { className, column, inputProps, onSelect, value }: OperatorPickerProps,\n forwardedRef: ForwardedRef<HTMLDivElement>,\n) {\n const handleSelectionChange = (\n evt: SyntheticEvent,\n newSelected: string[],\n ) => {\n const [selectedValue] = newSelected;\n if (isValidFilterClauseOp(selectedValue)) {\n onSelect(evt, selectedValue);\n }\n };\n\n return (\n <ExpandoCombobox\n inputProps={inputProps}\n className={className}\n data-field=\"operator\"\n onSelectionChange={handleSelectionChange}\n ref={forwardedRef}\n title=\"operator\"\n value={value}\n >\n {getOperators(column).map((op) => (\n <Option value={op} key={op} />\n ))}\n </ExpandoCombobox>\n );\n});\n"],"names":["forwardRef","isValidFilterClauseOp","jsx","ExpandoCombobox","getOperators","Option"],"mappings":";;;;;;;;;AAgBa,MAAA,cAAA,GAAiBA,gBAAW,CAAA,SAAS,YAChD,CAAA,EAAE,SAAW,EAAA,MAAA,EAAQ,UAAY,EAAA,QAAA,EAAU,KAAM,EAAA,EACjD,YACA,EAAA;AACA,EAAM,MAAA,qBAAA,GAAwB,CAC5B,GAAA,EACA,WACG,KAAA;AACH,IAAM,MAAA,CAAC,aAAa,CAAI,GAAA,WAAA
|
|
1
|
+
{"version":3,"file":"OperatorPicker.js","sources":["../../src/filter-clause/OperatorPicker.tsx"],"sourcesContent":["import type { FilterClauseOp } from \"@vuu-ui/vuu-filter-types\";\nimport type { ColumnDescriptor } from \"@vuu-ui/vuu-table-types\";\nimport { isValidFilterClauseOp } from \"@vuu-ui/vuu-utils\";\nimport { ComboBoxProps, Option } from \"@salt-ds/core\";\nimport { ForwardedRef, SyntheticEvent, forwardRef } from \"react\";\nimport { ExpandoCombobox } from \"./ExpandoCombobox\";\nimport { getOperators } from \"./operator-utils\";\n\nexport type OperatorPickerProps = Pick<\n ComboBoxProps,\n \"className\" | \"inputProps\" | \"value\"\n> & {\n column: ColumnDescriptor;\n onSelect: (evt: SyntheticEvent, operator: FilterClauseOp) => void;\n};\n\nexport const OperatorPicker = forwardRef(function ColumnPicker(\n { className, column, inputProps, onSelect, value }: OperatorPickerProps,\n forwardedRef: ForwardedRef<HTMLDivElement>,\n) {\n const handleSelectionChange = (\n evt: SyntheticEvent,\n newSelected: string[],\n ) => {\n const [selectedValue] = newSelected;\n if (isValidFilterClauseOp(selectedValue)) {\n onSelect(evt, selectedValue);\n }\n };\n\n return (\n <ExpandoCombobox\n inputProps={inputProps}\n className={className}\n data-field=\"operator\"\n onSelectionChange={handleSelectionChange}\n ref={forwardedRef}\n title=\"operator\"\n value={value}\n >\n {getOperators(column).map((op) => (\n <Option value={op} key={op} />\n ))}\n </ExpandoCombobox>\n );\n});\n"],"names":["forwardRef","isValidFilterClauseOp","jsx","ExpandoCombobox","getOperators","Option"],"mappings":";;;;;;;;;AAgBa,MAAA,cAAA,GAAiBA,gBAAW,CAAA,SAAS,YAChD,CAAA,EAAE,SAAW,EAAA,MAAA,EAAQ,UAAY,EAAA,QAAA,EAAU,KAAM,EAAA,EACjD,YACA,EAAA;AACA,EAAM,MAAA,qBAAA,GAAwB,CAC5B,GAAA,EACA,WACG,KAAA;AACH,IAAM,MAAA,CAAC,aAAa,CAAI,GAAA,WAAA;AACxB,IAAI,IAAAC,8BAAA,CAAsB,aAAa,CAAG,EAAA;AACxC,MAAA,QAAA,CAAS,KAAK,aAAa,CAAA;AAAA;AAC7B,GACF;AAEA,EACE,uBAAAC,cAAA;AAAA,IAACC,+BAAA;AAAA,IAAA;AAAA,MACC,UAAA;AAAA,MACA,SAAA;AAAA,MACA,YAAW,EAAA,UAAA;AAAA,MACX,iBAAmB,EAAA,qBAAA;AAAA,MACnB,GAAK,EAAA,YAAA;AAAA,MACL,KAAM,EAAA,UAAA;AAAA,MACN,KAAA;AAAA,MAEC,QAAA,EAAAC,0BAAA,CAAa,MAAM,CAAA,CAAE,GAAI,CAAA,CAAC,EACzB,qBAAAF,cAAA,CAACG,WAAO,EAAA,EAAA,KAAA,EAAO,EAAS,EAAA,EAAA,EAAI,CAC7B;AAAA;AAAA,GACH;AAEJ,CAAC;;;;"}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"filterClauseFocusManagement.js","sources":["../../src/filter-clause/filterClauseFocusManagement.ts"],"sourcesContent":["import { getElementDataIndex, queryClosest } from \"@vuu-ui/vuu-utils\";\nimport { KeyboardEvent } from \"react\";\n\nconst getFilterClauseElement = (possiblyDescendant?: HTMLElement) =>\n possiblyDescendant?.closest(\".vuuFilterClause\") as HTMLElement;\n\nconst getFilterClauseFieldElement = (possiblyDescendant?: HTMLElement) =>\n possiblyDescendant?.closest(\".vuuFilterClauseField\") as HTMLElement;\n\ntype FilterClauseFieldName = \"column\" | \"operator\" | \"value\";\nconst mapFilterFieldToClassName: Record<FilterClauseFieldName, string> = {\n column: \"vuuFilterClauseColumn\",\n operator: \"vuuFilterClauseOperator\",\n value: \"vuuFilterClauseValue\",\n};\n\nconst getFilterClauseDetails = ({ classList }: HTMLElement) => {\n if (classList.contains(\"vuuFilterClauseColumn\")) {\n return \"column\";\n } else if (classList.contains(\"vuuFilterClauseOperator\")) {\n return \"operator\";\n } else if (classList.contains(\"vuuFilterClauseValue\")) {\n return \"value\";\n } else {\n throw Error(\n \"getFilterClauseField, filterClauseElemnent is missing required class name\",\n );\n }\n};\n\nexport const getFocusedFieldDetails = (): [number, string] | [] => {\n const el = document.activeElement as HTMLElement;\n const field = queryClosest(el, \".vuuFilterClauseField,.saltCalendar\");\n if (field?.matches(\".vuuFilterClauseField\")) {\n const filterClause = queryClosest(field, \".vuuFilterClause\");\n if (filterClause && field) {\n return [getElementDataIndex(filterClause), getFilterClauseDetails(field)];\n }\n } else if (field?.matches(\".saltCalendar\")) {\n console.log(\"muthafucker is ins a calendar\");\n }\n // const filterClause = queryClosest(field, \".vuuFilterClause\");\n // if (filterClause && field) {\n // return [getElementDataIndex(filterClause), getFilterClauseDetails(field)];\n // } else {\n return [];\n // }\n};\n\n// Focus the input control within field. If clause passed, will\n// focus first field within clause\nconst focusField = (fieldOrClause: HTMLElement | null) => {\n const input = fieldOrClause?.querySelector(\"input\");\n if (input) {\n input.focus();\n requestAnimationFrame(() => {\n input?.select();\n });\n }\n};\n\nexport const elementIsFilterCombinator = (\n element: Element | null,\n): element is HTMLElement =>\n element !== null && element.classList.contains(\"vuuFilterClauseCombinator\");\n\nexport const elementIsFilterClause = (\n element: Element | null,\n): element is HTMLElement =>\n element !== null && element.classList.contains(\"vuuFilterClause\");\n\nexport const focusFilterClauseField = (\n filterEditor: HTMLElement,\n filterClauseIndex: number,\n fieldName: FilterClauseFieldName = \"value\",\n) => {\n if (filterEditor) {\n const fieldClassName = mapFilterFieldToClassName[fieldName];\n const field = filterEditor.querySelector(\n `.vuuFilterClause[data-index=\"${filterClauseIndex}\"] .${fieldClassName}`,\n ) as HTMLElement;\n focusField(field);\n }\n};\n\nexport const focusLastClauseValue = (filterEditor: HTMLElement) => {\n console.log(\"focusLastClauseValue\");\n const field = Array.from(\n filterEditor?.querySelectorAll(\".vuuFilterClauseField\"),\n ).at(-1) as HTMLElement;\n focusField(field);\n};\n\nexport const focusNextFocusableElement = (direction: \"fwd\" | \"bwd\" = \"fwd\") => {\n const activeField = getFocusedField() as HTMLElement;\n const filterClause = getFilterClauseElement(activeField);\n if (direction === \"fwd\" && filterClause?.lastChild === activeField) {\n requestAnimationFrame(() => {\n focusNextFocusableElement();\n });\n } else {\n const nextField =\n direction === \"fwd\"\n ? (activeField?.nextElementSibling as HTMLElement)\n : (activeField?.previousElementSibling as HTMLElement);\n\n nextField?.querySelector(\"input\")?.focus();\n }\n};\n\nconst getFocusedField = () => {\n const activeElement = document.activeElement as HTMLElement;\n if (activeElement?.classList.contains(\"vuuFilterClause-clearButton\")) {\n return activeElement as HTMLElement;\n } else {\n return getFilterClauseFieldElement(activeElement);\n }\n};\n\nexport const focusNextElement = () => {\n const filterClauseField = getFocusedField();\n const filterClause = getFilterClauseElement(filterClauseField);\n if (filterClause && filterClauseField) {\n if (filterClauseField.classList.contains(\"vuuFilterClauseValue\")) {\n const clearButton = filterClause.querySelector(\n \".vuuFilterClause-clearButton\",\n ) as HTMLButtonElement;\n clearButton?.focus();\n } else {\n focusNextFocusableElement();\n }\n }\n};\n\nconst cursorAtTextStart = (input: HTMLInputElement) =>\n input.selectionStart === 0;\n\nconst cursorAtTextEnd = (input: HTMLInputElement) =>\n input.selectionStart === input.value.length;\n\nconst getFieldName = (field: HTMLElement) =>\n field?.classList.contains(\"vuuFilterClauseColumn\")\n ? \"column\"\n : field?.classList.contains(\"vuuFilterClauseOperator\")\n ? \"operator\"\n : \"value\";\n\nexport const clauseIsNotFirst = (el: HTMLElement) => {\n const clause = getFilterClauseElement(el);\n if (clause) {\n const index = getElementDataIndex(clause);\n return index > 0;\n }\n};\n\nconst clauseIsNotLast = (el: HTMLElement) => {\n const clause = getFilterClauseElement(el);\n const nextClause = clause?.nextElementSibling as HTMLElement;\n return nextClause?.classList.contains(\"vuuFilterClauseCombinator\");\n};\n\nexport const tabToPreviousFilterCombinator = (currentElement: HTMLElement) => {\n const filterClause = getFilterClauseElement(currentElement);\n const nextItem = filterClause.previousSibling as HTMLElement;\n console.log(`tab to previous combinator`);\n nextItem?.focus();\n};\n\nexport const navigateToNextFilterClause = (\n currentElement: HTMLElement,\n direction: \"bwd\" | \"fwd\" = \"fwd\",\n) => {\n if (direction === \"bwd\") {\n if (elementIsFilterCombinator(currentElement)) {\n const nextClause = currentElement.previousElementSibling;\n if (elementIsFilterClause(nextClause)) {\n const nextField = nextClause.querySelector(\n \".vuuFilterClauseValue\",\n ) as HTMLElement;\n console.log(`focus field Value ${nextField?.classList}`);\n focusField(nextField);\n }\n } else {\n const filterClause = getFilterClauseElement(currentElement);\n const nextClause = filterClause.previousSibling as HTMLElement;\n const nextField = nextClause.querySelector(\n \".vuuFilterClauseValue\",\n ) as HTMLElement;\n focusField(nextField);\n }\n } else {\n const nextClause = currentElement.nextSibling as HTMLElement;\n focusField(nextClause);\n }\n};\n\n// The logic around preventDefault/stopPropagation is important\n// in this function\nexport const navigateToNextItemIfAtBoundary = (\n evt: KeyboardEvent<HTMLInputElement>,\n) => {\n const input = evt.target as HTMLInputElement;\n const field = getFilterClauseFieldElement(input);\n if (evt.key === \"ArrowLeft\") {\n if (cursorAtTextStart(input)) {\n const fieldName = getFieldName(field);\n if (fieldName === \"column\") {\n if (clauseIsNotFirst(input)) {\n const filterClause = getFilterClauseElement(field);\n const combinator = filterClause.previousElementSibling as HTMLElement;\n combinator?.focus();\n }\n } else {\n evt.preventDefault();\n focusField(field.previousSibling as HTMLElement);\n }\n }\n // stopPropagation, even if cursor is not at start. We want the arrowLeft to move the cursor\n evt.stopPropagation();\n } else if (evt.key === \"ArrowRight\") {\n if (cursorAtTextEnd(input as HTMLInputElement)) {\n const fieldName = getFieldName(field);\n if (fieldName === \"value\") {\n if (clauseIsNotLast(input)) {\n const filterClause = getFilterClauseElement(field);\n const combinator = filterClause.nextElementSibling as HTMLElement;\n combinator?.focus();\n }\n // Do not preventDefault, stopPropagation\n return;\n } else {\n evt.preventDefault();\n focusField(field.nextSibling as HTMLElement);\n }\n }\n // stopPropagation, even if cursor is not at end. We want the arrowRight to move the cursor\n evt.stopPropagation();\n }\n};\n\nexport const focusFirstClauseIfAllClausesValid = (\n filterEditor: HTMLElement,\n) => {\n const columInput = Array.from(\n filterEditor.querySelectorAll(\".vuuFilterClauseColumn input\"),\n ) as HTMLInputElement[];\n if (columInput.every((input) => input.value.length > 0)) {\n setTimeout(() => {\n const input = columInput.at(0);\n input?.select();\n input?.focus();\n }, 100);\n }\n};\n"],"names":["queryClosest","getElementDataIndex"],"mappings":"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"}
|
|
1
|
+
{"version":3,"file":"filterClauseFocusManagement.js","sources":["../../src/filter-clause/filterClauseFocusManagement.ts"],"sourcesContent":["import { getElementDataIndex, queryClosest } from \"@vuu-ui/vuu-utils\";\nimport { KeyboardEvent } from \"react\";\n\nconst getFilterClauseElement = (possiblyDescendant?: HTMLElement) =>\n possiblyDescendant?.closest(\".vuuFilterClause\") as HTMLElement;\n\nconst getFilterClauseFieldElement = (possiblyDescendant?: HTMLElement) =>\n possiblyDescendant?.closest(\".vuuFilterClauseField\") as HTMLElement;\n\ntype FilterClauseFieldName = \"column\" | \"operator\" | \"value\";\nconst mapFilterFieldToClassName: Record<FilterClauseFieldName, string> = {\n column: \"vuuFilterClauseColumn\",\n operator: \"vuuFilterClauseOperator\",\n value: \"vuuFilterClauseValue\",\n};\n\nconst getFilterClauseDetails = ({ classList }: HTMLElement) => {\n if (classList.contains(\"vuuFilterClauseColumn\")) {\n return \"column\";\n } else if (classList.contains(\"vuuFilterClauseOperator\")) {\n return \"operator\";\n } else if (classList.contains(\"vuuFilterClauseValue\")) {\n return \"value\";\n } else {\n throw Error(\n \"getFilterClauseField, filterClauseElemnent is missing required class name\",\n );\n }\n};\n\nexport const getFocusedFieldDetails = (): [number, string] | [] => {\n const el = document.activeElement as HTMLElement;\n const field = queryClosest(el, \".vuuFilterClauseField,.saltCalendar\");\n if (field?.matches(\".vuuFilterClauseField\")) {\n const filterClause = queryClosest(field, \".vuuFilterClause\");\n if (filterClause && field) {\n return [getElementDataIndex(filterClause), getFilterClauseDetails(field)];\n }\n } else if (field?.matches(\".saltCalendar\")) {\n console.log(\"muthafucker is ins a calendar\");\n }\n // const filterClause = queryClosest(field, \".vuuFilterClause\");\n // if (filterClause && field) {\n // return [getElementDataIndex(filterClause), getFilterClauseDetails(field)];\n // } else {\n return [];\n // }\n};\n\n// Focus the input control within field. If clause passed, will\n// focus first field within clause\nconst focusField = (fieldOrClause: HTMLElement | null) => {\n const input = fieldOrClause?.querySelector(\"input\");\n if (input) {\n input.focus();\n requestAnimationFrame(() => {\n input?.select();\n });\n }\n};\n\nexport const elementIsFilterCombinator = (\n element: Element | null,\n): element is HTMLElement =>\n element !== null && element.classList.contains(\"vuuFilterClauseCombinator\");\n\nexport const elementIsFilterClause = (\n element: Element | null,\n): element is HTMLElement =>\n element !== null && element.classList.contains(\"vuuFilterClause\");\n\nexport const focusFilterClauseField = (\n filterEditor: HTMLElement,\n filterClauseIndex: number,\n fieldName: FilterClauseFieldName = \"value\",\n) => {\n if (filterEditor) {\n const fieldClassName = mapFilterFieldToClassName[fieldName];\n const field = filterEditor.querySelector(\n `.vuuFilterClause[data-index=\"${filterClauseIndex}\"] .${fieldClassName}`,\n ) as HTMLElement;\n focusField(field);\n }\n};\n\nexport const focusLastClauseValue = (filterEditor: HTMLElement) => {\n console.log(\"focusLastClauseValue\");\n const field = Array.from(\n filterEditor?.querySelectorAll(\".vuuFilterClauseField\"),\n ).at(-1) as HTMLElement;\n focusField(field);\n};\n\nexport const focusNextFocusableElement = (direction: \"fwd\" | \"bwd\" = \"fwd\") => {\n const activeField = getFocusedField() as HTMLElement;\n const filterClause = getFilterClauseElement(activeField);\n if (direction === \"fwd\" && filterClause?.lastChild === activeField) {\n requestAnimationFrame(() => {\n focusNextFocusableElement();\n });\n } else {\n const nextField =\n direction === \"fwd\"\n ? (activeField?.nextElementSibling as HTMLElement)\n : (activeField?.previousElementSibling as HTMLElement);\n\n nextField?.querySelector(\"input\")?.focus();\n }\n};\n\nconst getFocusedField = () => {\n const activeElement = document.activeElement as HTMLElement;\n if (activeElement?.classList.contains(\"vuuFilterClause-clearButton\")) {\n return activeElement as HTMLElement;\n } else {\n return getFilterClauseFieldElement(activeElement);\n }\n};\n\nexport const focusNextElement = () => {\n const filterClauseField = getFocusedField();\n const filterClause = getFilterClauseElement(filterClauseField);\n if (filterClause && filterClauseField) {\n if (filterClauseField.classList.contains(\"vuuFilterClauseValue\")) {\n const clearButton = filterClause.querySelector(\n \".vuuFilterClause-clearButton\",\n ) as HTMLButtonElement;\n clearButton?.focus();\n } else {\n focusNextFocusableElement();\n }\n }\n};\n\nconst cursorAtTextStart = (input: HTMLInputElement) =>\n input.selectionStart === 0;\n\nconst cursorAtTextEnd = (input: HTMLInputElement) =>\n input.selectionStart === input.value.length;\n\nconst getFieldName = (field: HTMLElement) =>\n field?.classList.contains(\"vuuFilterClauseColumn\")\n ? \"column\"\n : field?.classList.contains(\"vuuFilterClauseOperator\")\n ? \"operator\"\n : \"value\";\n\nexport const clauseIsNotFirst = (el: HTMLElement) => {\n const clause = getFilterClauseElement(el);\n if (clause) {\n const index = getElementDataIndex(clause);\n return index > 0;\n }\n};\n\nconst clauseIsNotLast = (el: HTMLElement) => {\n const clause = getFilterClauseElement(el);\n const nextClause = clause?.nextElementSibling as HTMLElement;\n return nextClause?.classList.contains(\"vuuFilterClauseCombinator\");\n};\n\nexport const tabToPreviousFilterCombinator = (currentElement: HTMLElement) => {\n const filterClause = getFilterClauseElement(currentElement);\n const nextItem = filterClause.previousSibling as HTMLElement;\n console.log(`tab to previous combinator`);\n nextItem?.focus();\n};\n\nexport const navigateToNextFilterClause = (\n currentElement: HTMLElement,\n direction: \"bwd\" | \"fwd\" = \"fwd\",\n) => {\n if (direction === \"bwd\") {\n if (elementIsFilterCombinator(currentElement)) {\n const nextClause = currentElement.previousElementSibling;\n if (elementIsFilterClause(nextClause)) {\n const nextField = nextClause.querySelector(\n \".vuuFilterClauseValue\",\n ) as HTMLElement;\n console.log(`focus field Value ${nextField?.classList}`);\n focusField(nextField);\n }\n } else {\n const filterClause = getFilterClauseElement(currentElement);\n const nextClause = filterClause.previousSibling as HTMLElement;\n const nextField = nextClause.querySelector(\n \".vuuFilterClauseValue\",\n ) as HTMLElement;\n focusField(nextField);\n }\n } else {\n const nextClause = currentElement.nextSibling as HTMLElement;\n focusField(nextClause);\n }\n};\n\n// The logic around preventDefault/stopPropagation is important\n// in this function\nexport const navigateToNextItemIfAtBoundary = (\n evt: KeyboardEvent<HTMLInputElement>,\n) => {\n const input = evt.target as HTMLInputElement;\n const field = getFilterClauseFieldElement(input);\n if (evt.key === \"ArrowLeft\") {\n if (cursorAtTextStart(input)) {\n const fieldName = getFieldName(field);\n if (fieldName === \"column\") {\n if (clauseIsNotFirst(input)) {\n const filterClause = getFilterClauseElement(field);\n const combinator = filterClause.previousElementSibling as HTMLElement;\n combinator?.focus();\n }\n } else {\n evt.preventDefault();\n focusField(field.previousSibling as HTMLElement);\n }\n }\n // stopPropagation, even if cursor is not at start. We want the arrowLeft to move the cursor\n evt.stopPropagation();\n } else if (evt.key === \"ArrowRight\") {\n if (cursorAtTextEnd(input as HTMLInputElement)) {\n const fieldName = getFieldName(field);\n if (fieldName === \"value\") {\n if (clauseIsNotLast(input)) {\n const filterClause = getFilterClauseElement(field);\n const combinator = filterClause.nextElementSibling as HTMLElement;\n combinator?.focus();\n }\n // Do not preventDefault, stopPropagation\n return;\n } else {\n evt.preventDefault();\n focusField(field.nextSibling as HTMLElement);\n }\n }\n // stopPropagation, even if cursor is not at end. We want the arrowRight to move the cursor\n evt.stopPropagation();\n }\n};\n\nexport const focusFirstClauseIfAllClausesValid = (\n filterEditor: HTMLElement,\n) => {\n const columInput = Array.from(\n filterEditor.querySelectorAll(\".vuuFilterClauseColumn input\"),\n ) as HTMLInputElement[];\n if (columInput.every((input) => input.value.length > 0)) {\n setTimeout(() => {\n const input = columInput.at(0);\n input?.select();\n input?.focus();\n }, 100);\n }\n};\n"],"names":["queryClosest","getElementDataIndex"],"mappings":"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"}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"operator-utils.js","sources":["../../src/filter-clause/operator-utils.ts"],"sourcesContent":["import type { ColumnDescriptor } from \"@vuu-ui/vuu-table-types\";\nimport { isNumericColumn, isTextColumn } from \"@vuu-ui/vuu-utils\";\nimport type {\n FilterClauseOp,\n NumericFilterClauseOp,\n} from \"@vuu-ui/vuu-filter-types\";\n\nexport const textOperators: FilterClauseOp[] = [\n \"=\",\n \"in\",\n \"!=\",\n \"starts\",\n \"ends\",\n \"contains\",\n];\nexport const numericOperators: NumericFilterClauseOp[] = [\n \"=\",\n \"!=\",\n \">\",\n \">=\",\n \"<\",\n \"<=\",\n];\n\nexport const getOperators = (column: ColumnDescriptor): FilterClauseOp[] => {\n if (isTextColumn(column)) {\n return textOperators;\n } else if (isNumericColumn(column)) {\n return numericOperators;\n } else {\n throw Error(\"getOperators only supports text and numeric columns\");\n }\n};\n"],"names":["isTextColumn","isNumericColumn"],"mappings":";;;;AAOO,MAAM,aAAkC,GAAA;AAAA,EAC7C,GAAA;AAAA,EACA,IAAA;AAAA,EACA,IAAA;AAAA,EACA,QAAA;AAAA,EACA,MAAA;AAAA,EACA
|
|
1
|
+
{"version":3,"file":"operator-utils.js","sources":["../../src/filter-clause/operator-utils.ts"],"sourcesContent":["import type { ColumnDescriptor } from \"@vuu-ui/vuu-table-types\";\nimport { isNumericColumn, isTextColumn } from \"@vuu-ui/vuu-utils\";\nimport type {\n FilterClauseOp,\n NumericFilterClauseOp,\n} from \"@vuu-ui/vuu-filter-types\";\n\nexport const textOperators: FilterClauseOp[] = [\n \"=\",\n \"in\",\n \"!=\",\n \"starts\",\n \"ends\",\n \"contains\",\n];\nexport const numericOperators: NumericFilterClauseOp[] = [\n \"=\",\n \"!=\",\n \">\",\n \">=\",\n \"<\",\n \"<=\",\n];\n\nexport const getOperators = (column: ColumnDescriptor): FilterClauseOp[] => {\n if (isTextColumn(column)) {\n return textOperators;\n } else if (isNumericColumn(column)) {\n return numericOperators;\n } else {\n throw Error(\"getOperators only supports text and numeric columns\");\n }\n};\n"],"names":["isTextColumn","isNumericColumn"],"mappings":";;;;AAOO,MAAM,aAAkC,GAAA;AAAA,EAC7C,GAAA;AAAA,EACA,IAAA;AAAA,EACA,IAAA;AAAA,EACA,QAAA;AAAA,EACA,MAAA;AAAA,EACA;AACF;AACO,MAAM,gBAA4C,GAAA;AAAA,EACvD,GAAA;AAAA,EACA,IAAA;AAAA,EACA,GAAA;AAAA,EACA,IAAA;AAAA,EACA,GAAA;AAAA,EACA;AACF;AAEa,MAAA,YAAA,GAAe,CAAC,MAA+C,KAAA;AAC1E,EAAI,IAAAA,qBAAA,CAAa,MAAM,CAAG,EAAA;AACxB,IAAO,OAAA,aAAA;AAAA,GACT,MAAA,IAAWC,wBAAgB,CAAA,MAAM,CAAG,EAAA;AAClC,IAAO,OAAA,gBAAA;AAAA,GACF,MAAA;AACL,IAAA,MAAM,MAAM,qDAAqD,CAAA;AAAA;AAErE;;;;;;"}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"useFilterClause.js","sources":["../../src/filter-clause/useFilterClause.ts"],"sourcesContent":["import { FilterClause, FilterClauseOp } from \"@vuu-ui/vuu-filter-types\";\nimport { hasOpenOptionList } from \"@vuu-ui/vuu-utils\";\nimport {\n KeyboardEvent,\n RefCallback,\n SyntheticEvent,\n useCallback,\n useEffect,\n useMemo,\n useRef,\n useState,\n} from \"react\";\nimport { FilterClauseProps } from \"./FilterClause\";\nimport {\n clauseIsNotFirst,\n focusNextElement,\n focusNextFocusableElement,\n navigateToNextItemIfAtBoundary,\n tabToPreviousFilterCombinator,\n} from \"./filterClauseFocusManagement\";\nexport type FilterClauseEditorHookProps = Pick<\n FilterClauseProps,\n \"columnsByName\" | \"filterClauseModel\" | \"onCancel\" | \"onFocusSave\"\n>;\n\nexport type FilterClauseValueChangeHandler = (\n value: string | string[] | number | number[],\n isFinal?: boolean,\n) => void;\n\nexport const useFilterClause = ({\n filterClauseModel,\n onCancel,\n columnsByName,\n onFocusSave,\n}: FilterClauseEditorHookProps) => {\n const [filterClause, setFilterClause] = useState<Partial<FilterClause>>(\n filterClauseModel.isValid ? filterClauseModel.asFilter() : {},\n );\n\n useMemo(() => {\n filterClauseModel.on(\"filterClause\", (filterClause) => {\n setFilterClause(filterClause);\n });\n }, [filterClauseModel]);\n\n const columnRef = useRef<HTMLDivElement>(null);\n const operatorRef = useRef<HTMLDivElement>(null);\n const valueRef = useRef<HTMLDivElement | null>(null);\n\n const setValueRef = useCallback<RefCallback<HTMLDivElement>>(\n (el) => {\n valueRef.current = el;\n if (!filterClauseModel.isValid) {\n el?.querySelector(\"input\")?.focus();\n }\n },\n [filterClauseModel.isValid],\n );\n\n const removeAndNavigateToNextInputIfAtBoundary = useCallback(\n (evt: KeyboardEvent) => {\n const input = evt.target as HTMLInputElement;\n if (input.value === \"\") {\n const field = input.closest(\"[data-field]\") as HTMLElement;\n switch (field?.dataset?.field) {\n case \"operator\": {\n filterClauseModel.column = undefined;\n focusNextFocusableElement(\"bwd\");\n break;\n }\n case \"value\": {\n filterClauseModel.setOp(undefined);\n focusNextFocusableElement(\"bwd\");\n break;\n }\n case \"column\": {\n if (clauseIsNotFirst(input)) {\n // When we backspace from an empty clause, the clause will be removed.filterClause\n // In this case, we will reposition focus on previous clause, but we\n // don't want the backspace to be effect an edit on that clause.\n evt.preventDefault();\n onCancel?.(filterClauseModel, \"Backspace\");\n }\n }\n }\n }\n },\n [filterClauseModel, onCancel],\n );\n\n const onSelectColumn = (evt: SyntheticEvent, selectedColumn: string) => {\n if (selectedColumn) {\n if (evt?.type === \"keydown\") {\n const { key } = evt as KeyboardEvent;\n if (key === \"Tab\") {\n if (filterClauseModel.column === selectedColumn) {\n // No selection change, allow normal Tab navigation (to Save button)\n return;\n } else {\n // Tab is being used to change selection, keep focus within the clause\n evt.preventDefault();\n }\n }\n }\n }\n filterClauseModel.column = selectedColumn;\n setTimeout(() => {\n focusNextElement();\n }, 100);\n };\n\n const onSelectOperator = useCallback(\n (_, selectedOp: FilterClauseOp) => {\n filterClauseModel.setOp(selectedOp);\n focusNextElement();\n },\n [filterClauseModel],\n );\n\n const handleChangeValue = useCallback<FilterClauseValueChangeHandler>(\n (value, isFinal) => filterClauseModel.setValue(value, isFinal),\n [filterClauseModel],\n );\n\n const handleDeselectValue = useCallback(\n () => filterClauseModel.setValue(undefined),\n [filterClauseModel],\n );\n\n const handleKeyDownCaptureNavigation = useCallback(\n (evt: KeyboardEvent<HTMLInputElement>) => {\n if ([\"ArrowLeft\", \"ArrowRight\"].includes(evt.key)) {\n navigateToNextItemIfAtBoundary(evt);\n } else if (evt.key === \"Backspace\") {\n removeAndNavigateToNextInputIfAtBoundary(evt);\n } else if (evt.key === \"Escape\") {\n // ignore when optionlist is open, the optionList will be collapsed\n if (!hasOpenOptionList(evt.target)) {\n onCancel?.(filterClauseModel, \"Escape\");\n }\n } else if (evt.key === \"Tab\" && evt.shiftKey) {\n evt.preventDefault();\n tabToPreviousFilterCombinator(evt.target as HTMLElement);\n } else if (evt.key === \"Tab\") {\n // if the clause is valid, skip to save\n if (filterClauseModel.isValid) {\n evt.preventDefault();\n evt.stopPropagation();\n // TODO focus cancel if not changed\n onFocusSave?.();\n }\n }\n },\n [\n filterClauseModel,\n onCancel,\n onFocusSave,\n removeAndNavigateToNextInputIfAtBoundary,\n ],\n );\n\n const inputProps = useMemo(\n () => ({\n onKeyDownCapture: handleKeyDownCaptureNavigation,\n tabIndex: -1,\n }),\n [handleKeyDownCaptureNavigation],\n );\n\n // Do we need this or can we leave it to the filterEditor\n useEffect(() => {\n // leave the valueInput to callbackRef handler above, may\n // fire after the requestAnimationFrame\n if (!filterClauseModel.isValid) {\n const inputRef =\n filterClauseModel.column === undefined\n ? columnRef\n : filterClauseModel.op === undefined\n ? operatorRef\n : null;\n\n requestAnimationFrame(() => {\n inputRef?.current?.querySelector(\"input\")?.focus();\n });\n }\n }, [filterClauseModel]);\n\n return {\n inputProps,\n columnRef,\n filterClause,\n onChangeValue: handleChangeValue,\n onDeselectValue: handleDeselectValue,\n onSelectColumn,\n onSelectOperator,\n operatorRef,\n selectedColumn: columnsByName[filterClauseModel.column ?? \"\"],\n valueRef: setValueRef,\n };\n};\n"],"names":["useState","useMemo","filterClause","useRef","useCallback","focusNextFocusableElement","clauseIsNotFirst","focusNextElement","navigateToNextItemIfAtBoundary","hasOpenOptionList","tabToPreviousFilterCombinator","useEffect"],"mappings":"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"}
|
|
1
|
+
{"version":3,"file":"useFilterClause.js","sources":["../../src/filter-clause/useFilterClause.ts"],"sourcesContent":["import { FilterClause, FilterClauseOp } from \"@vuu-ui/vuu-filter-types\";\nimport { hasOpenOptionList } from \"@vuu-ui/vuu-utils\";\nimport {\n KeyboardEvent,\n RefCallback,\n SyntheticEvent,\n useCallback,\n useEffect,\n useMemo,\n useRef,\n useState,\n} from \"react\";\nimport { FilterClauseProps } from \"./FilterClause\";\nimport {\n clauseIsNotFirst,\n focusNextElement,\n focusNextFocusableElement,\n navigateToNextItemIfAtBoundary,\n tabToPreviousFilterCombinator,\n} from \"./filterClauseFocusManagement\";\nexport type FilterClauseEditorHookProps = Pick<\n FilterClauseProps,\n \"columnsByName\" | \"filterClauseModel\" | \"onCancel\" | \"onFocusSave\"\n>;\n\nexport type FilterClauseValueChangeHandler = (\n value: string | string[] | number | number[],\n isFinal?: boolean,\n) => void;\n\nexport const useFilterClause = ({\n filterClauseModel,\n onCancel,\n columnsByName,\n onFocusSave,\n}: FilterClauseEditorHookProps) => {\n const [filterClause, setFilterClause] = useState<Partial<FilterClause>>(\n filterClauseModel.isValid ? filterClauseModel.asFilter() : {},\n );\n\n useMemo(() => {\n filterClauseModel.on(\"filterClause\", (filterClause) => {\n setFilterClause(filterClause);\n });\n }, [filterClauseModel]);\n\n const columnRef = useRef<HTMLDivElement>(null);\n const operatorRef = useRef<HTMLDivElement>(null);\n const valueRef = useRef<HTMLDivElement | null>(null);\n\n const setValueRef = useCallback<RefCallback<HTMLDivElement>>(\n (el) => {\n valueRef.current = el;\n if (!filterClauseModel.isValid) {\n el?.querySelector(\"input\")?.focus();\n }\n },\n [filterClauseModel.isValid],\n );\n\n const removeAndNavigateToNextInputIfAtBoundary = useCallback(\n (evt: KeyboardEvent) => {\n const input = evt.target as HTMLInputElement;\n if (input.value === \"\") {\n const field = input.closest(\"[data-field]\") as HTMLElement;\n switch (field?.dataset?.field) {\n case \"operator\": {\n filterClauseModel.column = undefined;\n focusNextFocusableElement(\"bwd\");\n break;\n }\n case \"value\": {\n filterClauseModel.setOp(undefined);\n focusNextFocusableElement(\"bwd\");\n break;\n }\n case \"column\": {\n if (clauseIsNotFirst(input)) {\n // When we backspace from an empty clause, the clause will be removed.filterClause\n // In this case, we will reposition focus on previous clause, but we\n // don't want the backspace to be effect an edit on that clause.\n evt.preventDefault();\n onCancel?.(filterClauseModel, \"Backspace\");\n }\n }\n }\n }\n },\n [filterClauseModel, onCancel],\n );\n\n const onSelectColumn = (evt: SyntheticEvent, selectedColumn: string) => {\n if (selectedColumn) {\n if (evt?.type === \"keydown\") {\n const { key } = evt as KeyboardEvent;\n if (key === \"Tab\") {\n if (filterClauseModel.column === selectedColumn) {\n // No selection change, allow normal Tab navigation (to Save button)\n return;\n } else {\n // Tab is being used to change selection, keep focus within the clause\n evt.preventDefault();\n }\n }\n }\n }\n filterClauseModel.column = selectedColumn;\n setTimeout(() => {\n focusNextElement();\n }, 100);\n };\n\n const onSelectOperator = useCallback(\n (_, selectedOp: FilterClauseOp) => {\n filterClauseModel.setOp(selectedOp);\n focusNextElement();\n },\n [filterClauseModel],\n );\n\n const handleChangeValue = useCallback<FilterClauseValueChangeHandler>(\n (value, isFinal) => filterClauseModel.setValue(value, isFinal),\n [filterClauseModel],\n );\n\n const handleDeselectValue = useCallback(\n () => filterClauseModel.setValue(undefined),\n [filterClauseModel],\n );\n\n const handleKeyDownCaptureNavigation = useCallback(\n (evt: KeyboardEvent<HTMLInputElement>) => {\n if ([\"ArrowLeft\", \"ArrowRight\"].includes(evt.key)) {\n navigateToNextItemIfAtBoundary(evt);\n } else if (evt.key === \"Backspace\") {\n removeAndNavigateToNextInputIfAtBoundary(evt);\n } else if (evt.key === \"Escape\") {\n // ignore when optionlist is open, the optionList will be collapsed\n if (!hasOpenOptionList(evt.target)) {\n onCancel?.(filterClauseModel, \"Escape\");\n }\n } else if (evt.key === \"Tab\" && evt.shiftKey) {\n evt.preventDefault();\n tabToPreviousFilterCombinator(evt.target as HTMLElement);\n } else if (evt.key === \"Tab\") {\n // if the clause is valid, skip to save\n if (filterClauseModel.isValid) {\n evt.preventDefault();\n evt.stopPropagation();\n // TODO focus cancel if not changed\n onFocusSave?.();\n }\n }\n },\n [\n filterClauseModel,\n onCancel,\n onFocusSave,\n removeAndNavigateToNextInputIfAtBoundary,\n ],\n );\n\n const inputProps = useMemo(\n () => ({\n onKeyDownCapture: handleKeyDownCaptureNavigation,\n tabIndex: -1,\n }),\n [handleKeyDownCaptureNavigation],\n );\n\n // Do we need this or can we leave it to the filterEditor\n useEffect(() => {\n // leave the valueInput to callbackRef handler above, may\n // fire after the requestAnimationFrame\n if (!filterClauseModel.isValid) {\n const inputRef =\n filterClauseModel.column === undefined\n ? columnRef\n : filterClauseModel.op === undefined\n ? operatorRef\n : null;\n\n requestAnimationFrame(() => {\n inputRef?.current?.querySelector(\"input\")?.focus();\n });\n }\n }, [filterClauseModel]);\n\n return {\n inputProps,\n columnRef,\n filterClause,\n onChangeValue: handleChangeValue,\n onDeselectValue: handleDeselectValue,\n onSelectColumn,\n onSelectOperator,\n operatorRef,\n selectedColumn: columnsByName[filterClauseModel.column ?? \"\"],\n valueRef: setValueRef,\n };\n};\n"],"names":["useState","useMemo","filterClause","useRef","useCallback","focusNextFocusableElement","clauseIsNotFirst","focusNextElement","navigateToNextItemIfAtBoundary","hasOpenOptionList","tabToPreviousFilterCombinator","useEffect"],"mappings":"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"}
|