@fluentui/react-combobox 9.0.0-beta.8 → 9.0.0-beta.9
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/CHANGELOG.json +117 -4
- package/CHANGELOG.md +28 -5
- package/Spec.md +4 -4
- package/dist/index.d.ts +25 -16
- package/lib/components/Combobox/Combobox.types.js.map +1 -1
- package/lib/components/Combobox/renderCombobox.js +3 -4
- package/lib/components/Combobox/renderCombobox.js.map +1 -1
- package/lib/components/Combobox/useCombobox.js +153 -15
- package/lib/components/Combobox/useCombobox.js.map +1 -1
- package/lib/components/Combobox/useComboboxStyles.js +56 -25
- package/lib/components/Combobox/useComboboxStyles.js.map +1 -1
- package/lib/components/Dropdown/Dropdown.types.js.map +1 -1
- package/lib/components/Dropdown/renderDropdown.js +3 -4
- package/lib/components/Dropdown/renderDropdown.js.map +1 -1
- package/lib/components/Dropdown/useDropdown.js +100 -8
- package/lib/components/Dropdown/useDropdown.js.map +1 -1
- package/lib/components/Dropdown/useDropdownStyles.js +41 -19
- package/lib/components/Dropdown/useDropdownStyles.js.map +1 -1
- package/lib/components/Listbox/Listbox.types.js.map +1 -1
- package/lib/components/Listbox/useListbox.js +25 -17
- package/lib/components/Listbox/useListbox.js.map +1 -1
- package/lib/components/Option/Option.types.js.map +1 -1
- package/lib/components/Option/useOption.js +29 -21
- package/lib/components/Option/useOption.js.map +1 -1
- package/lib/components/Option/useOptionStyles.js +2 -1
- package/lib/components/Option/useOptionStyles.js.map +1 -1
- package/lib/contexts/ComboboxContext.js +11 -4
- package/lib/contexts/ComboboxContext.js.map +1 -1
- package/lib/contexts/ListboxContext.js +9 -4
- package/lib/contexts/ListboxContext.js.map +1 -1
- package/lib/contexts/useComboboxContextValues.js +8 -2
- package/lib/contexts/useComboboxContextValues.js.map +1 -1
- package/lib/contexts/useListboxContextValues.js +8 -4
- package/lib/contexts/useListboxContextValues.js.map +1 -1
- package/lib/utils/ComboboxBase.types.js.map +1 -1
- package/lib/utils/Selection.types.js.map +1 -1
- package/lib/utils/dropdownKeyActions.js +2 -9
- package/lib/utils/dropdownKeyActions.js.map +1 -1
- package/lib/utils/useComboboxBaseState.js +29 -24
- package/lib/utils/useComboboxBaseState.js.map +1 -1
- package/lib/utils/useComboboxPopup.js +5 -3
- package/lib/utils/useComboboxPopup.js.map +1 -1
- package/lib/utils/useSelection.js +13 -4
- package/lib/utils/useSelection.js.map +1 -1
- package/lib/utils/useTriggerListboxSlots.js +45 -50
- package/lib/utils/useTriggerListboxSlots.js.map +1 -1
- package/lib-commonjs/components/Combobox/renderCombobox.js +3 -4
- package/lib-commonjs/components/Combobox/renderCombobox.js.map +1 -1
- package/lib-commonjs/components/Combobox/useCombobox.js +152 -14
- package/lib-commonjs/components/Combobox/useCombobox.js.map +1 -1
- package/lib-commonjs/components/Combobox/useComboboxStyles.js +56 -25
- package/lib-commonjs/components/Combobox/useComboboxStyles.js.map +1 -1
- package/lib-commonjs/components/Dropdown/renderDropdown.js +3 -4
- package/lib-commonjs/components/Dropdown/renderDropdown.js.map +1 -1
- package/lib-commonjs/components/Dropdown/useDropdown.js +101 -7
- package/lib-commonjs/components/Dropdown/useDropdown.js.map +1 -1
- package/lib-commonjs/components/Dropdown/useDropdownStyles.js +41 -19
- package/lib-commonjs/components/Dropdown/useDropdownStyles.js.map +1 -1
- package/lib-commonjs/components/Listbox/useListbox.js +24 -16
- package/lib-commonjs/components/Listbox/useListbox.js.map +1 -1
- package/lib-commonjs/components/Option/useOption.js +29 -21
- package/lib-commonjs/components/Option/useOption.js.map +1 -1
- package/lib-commonjs/components/Option/useOptionStyles.js +2 -1
- package/lib-commonjs/components/Option/useOptionStyles.js.map +1 -1
- package/lib-commonjs/contexts/ComboboxContext.js +11 -4
- package/lib-commonjs/contexts/ComboboxContext.js.map +1 -1
- package/lib-commonjs/contexts/ListboxContext.js +9 -4
- package/lib-commonjs/contexts/ListboxContext.js.map +1 -1
- package/lib-commonjs/contexts/useComboboxContextValues.js +8 -2
- package/lib-commonjs/contexts/useComboboxContextValues.js.map +1 -1
- package/lib-commonjs/contexts/useListboxContextValues.js +8 -4
- package/lib-commonjs/contexts/useListboxContextValues.js.map +1 -1
- package/lib-commonjs/utils/dropdownKeyActions.js +2 -9
- package/lib-commonjs/utils/dropdownKeyActions.js.map +1 -1
- package/lib-commonjs/utils/useComboboxBaseState.js +29 -24
- package/lib-commonjs/utils/useComboboxBaseState.js.map +1 -1
- package/lib-commonjs/utils/useComboboxPopup.js +5 -3
- package/lib-commonjs/utils/useComboboxPopup.js.map +1 -1
- package/lib-commonjs/utils/useSelection.js +13 -4
- package/lib-commonjs/utils/useSelection.js.map +1 -1
- package/lib-commonjs/utils/useTriggerListboxSlots.js +44 -49
- package/lib-commonjs/utils/useTriggerListboxSlots.js.map +1 -1
- package/package.json +9 -9
- package/dist/tsdoc-metadata.json +0 -11
|
@@ -13,8 +13,9 @@ const react_context_selector_1 = /*#__PURE__*/require("@fluentui/react-context-s
|
|
|
13
13
|
|
|
14
14
|
const react_icons_1 = /*#__PURE__*/require("@fluentui/react-icons");
|
|
15
15
|
|
|
16
|
-
const
|
|
16
|
+
const ComboboxContext_1 = /*#__PURE__*/require("../../contexts/ComboboxContext");
|
|
17
17
|
|
|
18
|
+
const ListboxContext_1 = /*#__PURE__*/require("../../contexts/ListboxContext");
|
|
18
19
|
|
|
19
20
|
function getValueString(value, children) {
|
|
20
21
|
if (value) {
|
|
@@ -46,20 +47,26 @@ const useOption_unstable = (props, ref) => {
|
|
|
46
47
|
value
|
|
47
48
|
} = props;
|
|
48
49
|
const optionRef = React.useRef(null);
|
|
49
|
-
const optionValue = getValueString(value, props.children); //
|
|
50
|
+
const optionValue = getValueString(value, props.children); // use the id if provided, otherwise use a generated id
|
|
50
51
|
|
|
52
|
+
const id = react_utilities_1.useId('fluent-option', props.id); // data used for context registration & events
|
|
53
|
+
|
|
54
|
+
const optionData = React.useMemo(() => ({
|
|
55
|
+
id,
|
|
56
|
+
disabled,
|
|
57
|
+
value: optionValue
|
|
58
|
+
}), [id, disabled, optionValue]); // context values
|
|
59
|
+
|
|
60
|
+
const focusVisible = react_context_selector_1.useContextSelector(ListboxContext_1.ListboxContext, ctx => ctx.focusVisible);
|
|
51
61
|
const multiselect = react_context_selector_1.useContextSelector(ListboxContext_1.ListboxContext, ctx => ctx.multiselect);
|
|
52
|
-
const onOptionClick = react_context_selector_1.useContextSelector(ListboxContext_1.ListboxContext, ctx => ctx.onOptionClick);
|
|
53
62
|
const registerOption = react_context_selector_1.useContextSelector(ListboxContext_1.ListboxContext, ctx => ctx.registerOption);
|
|
54
63
|
const selected = react_context_selector_1.useContextSelector(ListboxContext_1.ListboxContext, ctx => {
|
|
55
64
|
const selectedOptions = ctx.selectedOptions;
|
|
56
65
|
return !!optionValue && !!selectedOptions.find(o => o === optionValue);
|
|
57
|
-
});
|
|
58
|
-
|
|
59
|
-
const
|
|
60
|
-
const
|
|
61
|
-
return props.id || defaultId;
|
|
62
|
-
}, [props.id, defaultId]); // current active option?
|
|
66
|
+
});
|
|
67
|
+
const selectOption = react_context_selector_1.useContextSelector(ListboxContext_1.ListboxContext, ctx => ctx.selectOption);
|
|
68
|
+
const setActiveOption = react_context_selector_1.useContextSelector(ListboxContext_1.ListboxContext, ctx => ctx.setActiveOption);
|
|
69
|
+
const setOpen = react_context_selector_1.useContextSelector(ComboboxContext_1.ComboboxContext, ctx => ctx.setOpen); // current active option?
|
|
63
70
|
|
|
64
71
|
const active = react_context_selector_1.useContextSelector(ListboxContext_1.ListboxContext, ctx => {
|
|
65
72
|
var _a, _b;
|
|
@@ -79,26 +86,26 @@ const useOption_unstable = (props, ref) => {
|
|
|
79
86
|
if (disabled) {
|
|
80
87
|
event.preventDefault();
|
|
81
88
|
return;
|
|
82
|
-
}
|
|
89
|
+
} // clicked option should always become active option
|
|
83
90
|
|
|
84
|
-
|
|
85
|
-
|
|
86
|
-
|
|
87
|
-
|
|
88
|
-
|
|
91
|
+
|
|
92
|
+
setActiveOption(optionData); // close on option click for single-select options in a combobox
|
|
93
|
+
|
|
94
|
+
if (!multiselect) {
|
|
95
|
+
setOpen === null || setOpen === void 0 ? void 0 : setOpen(event, false);
|
|
96
|
+
} // handle selection change
|
|
97
|
+
|
|
98
|
+
|
|
99
|
+
selectOption(event, optionData);
|
|
89
100
|
(_a = props.onClick) === null || _a === void 0 ? void 0 : _a.call(props, event);
|
|
90
101
|
}; // register option data with context
|
|
91
102
|
|
|
92
103
|
|
|
93
104
|
React.useEffect(() => {
|
|
94
105
|
if (id && optionRef.current) {
|
|
95
|
-
return registerOption(
|
|
96
|
-
id,
|
|
97
|
-
disabled,
|
|
98
|
-
value: optionValue
|
|
99
|
-
}, optionRef.current);
|
|
106
|
+
return registerOption(optionData, optionRef.current);
|
|
100
107
|
}
|
|
101
|
-
}, [
|
|
108
|
+
}, [id, optionData, registerOption]);
|
|
102
109
|
return {
|
|
103
110
|
components: {
|
|
104
111
|
root: 'div',
|
|
@@ -122,6 +129,7 @@ const useOption_unstable = (props, ref) => {
|
|
|
122
129
|
}),
|
|
123
130
|
active,
|
|
124
131
|
disabled,
|
|
132
|
+
focusVisible,
|
|
125
133
|
multiselect,
|
|
126
134
|
selected
|
|
127
135
|
};
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"sources":["components/Option/useOption.tsx"],"names":[],"mappings":";;;;;;;AAAA,MAAA,KAAA,gBAAA,OAAA,CAAA,OAAA,CAAA;;AACA,MAAA,iBAAA,gBAAA,OAAA,CAAA,2BAAA,CAAA;;AACA,MAAA,wBAAA,gBAAA,OAAA,CAAA,kCAAA,CAAA;;AACA,MAAA,aAAA,gBAAA,OAAA,CAAA,uBAAA,CAAA;;AACA,MAAA,gBAAA,gBAAA,OAAA,CAAA,+BAAA,CAAA,
|
|
1
|
+
{"version":3,"sources":["components/Option/useOption.tsx"],"names":[],"mappings":"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","sourcesContent":["import * as React from 'react';\nimport { getNativeElementProps, resolveShorthand, useId, useMergedRefs } from '@fluentui/react-utilities';\nimport { useContextSelector } from '@fluentui/react-context-selector';\nimport { CheckmarkFilled, CheckboxUncheckedFilled, CheckboxCheckedFilled } from '@fluentui/react-icons';\nimport { ComboboxContext } from '../../contexts/ComboboxContext';\nimport { ListboxContext } from '../../contexts/ListboxContext';\nimport type { OptionValue } from '../../utils/OptionCollection.types';\nimport type { OptionProps, OptionState } from './Option.types';\n\nfunction getValueString(value: string | undefined, children: React.ReactNode) {\n if (value) {\n return value;\n }\n\n let valueString = '';\n React.Children.forEach(children, child => {\n if (typeof child === 'string') {\n valueString += child;\n }\n });\n return valueString;\n}\n\n/**\n * Create the state required to render Option.\n *\n * The returned state can be modified with hooks such as useOptionStyles_unstable,\n * before being passed to renderOption_unstable.\n *\n * @param props - props from this instance of Option\n * @param ref - reference to root HTMLElement of Option\n */\nexport const useOption_unstable = (props: OptionProps, ref: React.Ref<HTMLElement>): OptionState => {\n const { disabled, value } = props;\n const optionRef = React.useRef<HTMLElement>(null);\n const optionValue = getValueString(value, props.children);\n\n // use the id if provided, otherwise use a generated id\n const id = useId('fluent-option', props.id);\n\n // data used for context registration & events\n const optionData = React.useMemo<OptionValue>(() => ({ id, disabled, value: optionValue }), [\n id,\n disabled,\n optionValue,\n ]);\n\n // context values\n const focusVisible = useContextSelector(ListboxContext, ctx => ctx.focusVisible);\n const multiselect = useContextSelector(ListboxContext, ctx => ctx.multiselect);\n const registerOption = useContextSelector(ListboxContext, ctx => ctx.registerOption);\n const selected = useContextSelector(ListboxContext, ctx => {\n const selectedOptions = ctx.selectedOptions;\n\n return !!optionValue && !!selectedOptions.find(o => o === optionValue);\n });\n const selectOption = useContextSelector(ListboxContext, ctx => ctx.selectOption);\n const setActiveOption = useContextSelector(ListboxContext, ctx => ctx.setActiveOption);\n const setOpen = useContextSelector(ComboboxContext, ctx => ctx.setOpen);\n\n // current active option?\n const active = useContextSelector(ListboxContext, ctx => {\n return ctx.activeOption?.id !== undefined && ctx.activeOption?.id === id;\n });\n\n // check icon\n let CheckIcon = <CheckmarkFilled />;\n if (multiselect) {\n CheckIcon = selected ? <CheckboxCheckedFilled /> : <CheckboxUncheckedFilled />;\n }\n\n const onClick = (event: React.MouseEvent<HTMLDivElement>) => {\n if (disabled) {\n event.preventDefault();\n return;\n }\n\n // clicked option should always become active option\n setActiveOption(optionData);\n\n // close on option click for single-select options in a combobox\n if (!multiselect) {\n setOpen?.(event, false);\n }\n\n // handle selection change\n selectOption(event, optionData);\n\n props.onClick?.(event);\n };\n\n // register option data with context\n React.useEffect(() => {\n if (id && optionRef.current) {\n return registerOption(optionData, optionRef.current);\n }\n }, [id, optionData, registerOption]);\n\n return {\n components: {\n root: 'div',\n checkIcon: 'span',\n },\n root: getNativeElementProps('div', {\n ref: useMergedRefs(ref, optionRef),\n role: 'option',\n 'aria-disabled': disabled ? 'true' : undefined,\n 'aria-selected': `${selected}`,\n id,\n ...props,\n onClick,\n }),\n checkIcon: resolveShorthand(props.checkIcon, {\n required: true,\n defaultProps: {\n 'aria-hidden': 'true',\n children: CheckIcon,\n },\n }),\n active,\n disabled,\n focusVisible,\n multiselect,\n selected,\n };\n};\n"],"sourceRoot":"../src/"}
|
|
@@ -113,11 +113,12 @@ const useOptionStyles_unstable = state => {
|
|
|
113
113
|
const {
|
|
114
114
|
active,
|
|
115
115
|
disabled,
|
|
116
|
+
focusVisible,
|
|
116
117
|
multiselect,
|
|
117
118
|
selected
|
|
118
119
|
} = state;
|
|
119
120
|
const styles = useStyles();
|
|
120
|
-
state.root.className = react_1.mergeClasses(exports.optionClassNames.root, styles.root, active && styles.active, disabled && styles.disabled, selected && styles.selected, state.root.className);
|
|
121
|
+
state.root.className = react_1.mergeClasses(exports.optionClassNames.root, styles.root, active && focusVisible && styles.active, disabled && styles.disabled, selected && styles.selected, state.root.className);
|
|
121
122
|
|
|
122
123
|
if (state.checkIcon) {
|
|
123
124
|
state.checkIcon.className = react_1.mergeClasses(exports.optionClassNames.checkIcon, styles.checkIcon, state.checkIcon.className, multiselect && styles.multiselectCheck, selected && styles.selectedCheck, selected && multiselect && styles.selectedMultiselectCheck, disabled && styles.checkDisabled);
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"sources":["components/Option/useOptionStyles.ts"],"names":[],"mappings":";;;;;;;AAAA,MAAA,aAAA,gBAAA,OAAA,CAAA,uBAAA,CAAA;;AAEA,MAAA,OAAA,gBAAA,OAAA,CAAA,gBAAA,CAAA;;AAGa,OAAA,CAAA,gBAAA,GAAgD;EAC3D,IAAI,EAAE,YADqD;EAE3D,SAAS,EAAE;AAFgD,CAAhD;AAKb;;AAEG;;AACH,MAAM,SAAS,gBAAG,OAAA,SAAA;EAAA;IAAA;IAAA;IAAA;IAAA;IAAA;IAAA;IAAA;IAAA;IAAA;IAAA;IAAA;IAAA;IAAA;IAAA;IAAA;IAAA;IAAA;IAAA;IAAA;EAAA;EAAA;IAAA;IAAA;IAAA;IAAA;IAAA;IAAA;IAAA;IAAA;IAAA;IAAA;IAAA;IAAA;IAAA;IAAA;IAAA;IAAA;IAAA;IAAA;IAAA;IAAA;IAAA;IAAA;IAAA;IAAA;EAAA;EAAA;IAAA;IAAA;IAAA;IAAA;EAAA;EAAA;EAAA;IAAA;IAAA;IAAA;IAAA;IAAA;EAAA;EAAA;IAAA;IAAA;IAAA;EAAA;EAAA;IAAA;EAAA;EAAA;IAAA;EAAA;EAAA;IAAA;IAAA;EAAA;AAAA;EAAA;EAAA;EAAA;EAAA;IAAA;EAAA;IAAA;EAAA;AAAA,EAAlB;AAkGA;;AAEG;;;AACI,MAAM,wBAAwB,GAAI,KAAD,IAAoC;EAC1E,MAAM;IAAE,MAAF;IAAU,QAAV;IAAoB,
|
|
1
|
+
{"version":3,"sources":["components/Option/useOptionStyles.ts"],"names":[],"mappings":";;;;;;;AAAA,MAAA,aAAA,gBAAA,OAAA,CAAA,uBAAA,CAAA;;AAEA,MAAA,OAAA,gBAAA,OAAA,CAAA,gBAAA,CAAA;;AAGa,OAAA,CAAA,gBAAA,GAAgD;EAC3D,IAAI,EAAE,YADqD;EAE3D,SAAS,EAAE;AAFgD,CAAhD;AAKb;;AAEG;;AACH,MAAM,SAAS,gBAAG,OAAA,SAAA;EAAA;IAAA;IAAA;IAAA;IAAA;IAAA;IAAA;IAAA;IAAA;IAAA;IAAA;IAAA;IAAA;IAAA;IAAA;IAAA;IAAA;IAAA;IAAA;IAAA;EAAA;EAAA;IAAA;IAAA;IAAA;IAAA;IAAA;IAAA;IAAA;IAAA;IAAA;IAAA;IAAA;IAAA;IAAA;IAAA;IAAA;IAAA;IAAA;IAAA;IAAA;IAAA;IAAA;IAAA;IAAA;IAAA;EAAA;EAAA;IAAA;IAAA;IAAA;IAAA;EAAA;EAAA;EAAA;IAAA;IAAA;IAAA;IAAA;IAAA;EAAA;EAAA;IAAA;IAAA;IAAA;EAAA;EAAA;IAAA;EAAA;EAAA;IAAA;EAAA;EAAA;IAAA;IAAA;EAAA;AAAA;EAAA;EAAA;EAAA;EAAA;IAAA;EAAA;IAAA;EAAA;AAAA,EAAlB;AAkGA;;AAEG;;;AACI,MAAM,wBAAwB,GAAI,KAAD,IAAoC;EAC1E,MAAM;IAAE,MAAF;IAAU,QAAV;IAAoB,YAApB;IAAkC,WAAlC;IAA+C;EAA/C,IAA4D,KAAlE;EACA,MAAM,MAAM,GAAG,SAAS,EAAxB;EACA,KAAK,CAAC,IAAN,CAAW,SAAX,GAAuB,OAAA,CAAA,YAAA,CACrB,OAAA,CAAA,gBAAA,CAAiB,IADI,EAErB,MAAM,CAAC,IAFc,EAGrB,MAAM,IAAI,YAAV,IAA0B,MAAM,CAAC,MAHZ,EAIrB,QAAQ,IAAI,MAAM,CAAC,QAJE,EAKrB,QAAQ,IAAI,MAAM,CAAC,QALE,EAMrB,KAAK,CAAC,IAAN,CAAW,SANU,CAAvB;;EASA,IAAI,KAAK,CAAC,SAAV,EAAqB;IACnB,KAAK,CAAC,SAAN,CAAgB,SAAhB,GAA4B,OAAA,CAAA,YAAA,CAC1B,OAAA,CAAA,gBAAA,CAAiB,SADS,EAE1B,MAAM,CAAC,SAFmB,EAG1B,KAAK,CAAC,SAAN,CAAgB,SAHU,EAI1B,WAAW,IAAI,MAAM,CAAC,gBAJI,EAK1B,QAAQ,IAAI,MAAM,CAAC,aALO,EAM1B,QAAQ,IAAI,WAAZ,IAA2B,MAAM,CAAC,wBANR,EAO1B,QAAQ,IAAI,MAAM,CAAC,aAPO,CAA5B;EASD;;EAED,OAAO,KAAP;AACD,CAzBM;;AAAM,OAAA,CAAA,wBAAA,GAAwB,wBAAxB","sourcesContent":["import { tokens } from '@fluentui/react-theme';\nimport { SlotClassNames } from '@fluentui/react-utilities';\nimport { makeStyles, mergeClasses, shorthands } from '@griffel/react';\nimport type { OptionSlots, OptionState } from './Option.types';\n\nexport const optionClassNames: SlotClassNames<OptionSlots> = {\n root: 'fui-Option',\n checkIcon: 'fui-Option__checkIcon',\n};\n\n/**\n * Styles for the root slot\n */\nconst useStyles = makeStyles({\n root: {\n alignItems: 'center',\n ...shorthands.borderRadius(tokens.borderRadiusMedium),\n color: tokens.colorNeutralForeground1,\n columnGap: tokens.spacingHorizontalXS,\n cursor: 'pointer',\n display: 'flex',\n fontFamily: tokens.fontFamilyBase,\n fontSize: tokens.fontSizeBase300,\n lineHeight: tokens.lineHeightBase300,\n ...shorthands.padding(tokens.spacingVerticalSNudge, tokens.spacingHorizontalS),\n position: 'relative',\n\n '&:hover': {\n backgroundColor: tokens.colorNeutralBackground1Hover,\n },\n\n '&:active': {\n backgroundColor: tokens.colorNeutralBackground1Pressed,\n },\n },\n\n active: {\n // taken from @fluentui/react-tabster\n // cannot use createFocusIndicatorStyle() directly, since we aren't using the :focus selector\n '::after': {\n content: '\"\"',\n position: 'absolute',\n pointerEvents: 'none',\n zIndex: 1,\n\n ...shorthands.borderStyle('solid'),\n ...shorthands.borderWidth('2px'),\n ...shorthands.borderRadius(tokens.borderRadiusMedium),\n ...shorthands.borderColor(tokens.colorStrokeFocus2),\n\n top: '-2px',\n bottom: '-2px',\n left: '-2px',\n right: '-2px',\n },\n },\n\n disabled: {\n color: tokens.colorNeutralForegroundDisabled,\n\n '&:hover': {\n backgroundColor: tokens.colorTransparentBackground,\n },\n\n '&:active': {\n backgroundColor: tokens.colorTransparentBackground,\n },\n\n '@media (forced-colors: active)': {\n color: 'GrayText',\n },\n },\n\n selected: {},\n\n checkIcon: {\n fontSize: tokens.fontSizeBase400,\n // Shift icon(s) to the left to give text content extra spacing without needing an extra node\n // This is done instead of gap since the extra space only exists between icon > content, not icon > icon\n marginLeft: `calc(${tokens.spacingHorizontalXXS} * -1)`,\n marginRight: tokens.spacingHorizontalXXS,\n visibility: 'hidden',\n\n '& svg': {\n display: 'block',\n },\n },\n\n multiselectCheck: {\n color: tokens.colorNeutralForeground3,\n fontSize: tokens.fontSizeBase500,\n visibility: 'visible',\n },\n\n selectedCheck: {\n visibility: 'visible',\n },\n\n selectedMultiselectCheck: {\n color: tokens.colorBrandBackground,\n },\n\n checkDisabled: {\n color: tokens.colorNeutralForegroundDisabled,\n\n '@media (forced-colors: active)': {\n color: 'GrayText',\n },\n },\n});\n\n/**\n * Apply styling to the Option slots based on the state\n */\nexport const useOptionStyles_unstable = (state: OptionState): OptionState => {\n const { active, disabled, focusVisible, multiselect, selected } = state;\n const styles = useStyles();\n state.root.className = mergeClasses(\n optionClassNames.root,\n styles.root,\n active && focusVisible && styles.active,\n disabled && styles.disabled,\n selected && styles.selected,\n state.root.className,\n );\n\n if (state.checkIcon) {\n state.checkIcon.className = mergeClasses(\n optionClassNames.checkIcon,\n styles.checkIcon,\n state.checkIcon.className,\n multiselect && styles.multiselectCheck,\n selected && styles.selectedCheck,\n selected && multiselect && styles.selectedMultiselectCheck,\n disabled && styles.checkDisabled,\n );\n }\n\n return state;\n};\n"],"sourceRoot":"../src/"}
|
|
@@ -11,15 +11,22 @@ const react_context_selector_1 = /*#__PURE__*/require("@fluentui/react-context-s
|
|
|
11
11
|
exports.ComboboxContext = /*#__PURE__*/react_context_selector_1.createContext({
|
|
12
12
|
activeOption: undefined,
|
|
13
13
|
appearance: 'outline',
|
|
14
|
+
focusVisible: false,
|
|
15
|
+
open: false,
|
|
14
16
|
|
|
15
|
-
|
|
17
|
+
registerOption() {
|
|
18
|
+
return () => undefined;
|
|
16
19
|
},
|
|
17
20
|
|
|
18
|
-
open: false,
|
|
19
21
|
selectedOptions: [],
|
|
20
22
|
|
|
21
|
-
|
|
22
|
-
|
|
23
|
+
selectOption() {// noop
|
|
24
|
+
},
|
|
25
|
+
|
|
26
|
+
setActiveOption() {// noop
|
|
27
|
+
},
|
|
28
|
+
|
|
29
|
+
setOpen() {// noop
|
|
23
30
|
},
|
|
24
31
|
|
|
25
32
|
size: 'medium'
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"sources":["contexts/ComboboxContext.ts"],"names":[],"mappings":";;;;;;;AAAA,MAAA,wBAAA,gBAAA,OAAA,CAAA,kCAAA,CAAA,C,
|
|
1
|
+
{"version":3,"sources":["contexts/ComboboxContext.ts"],"names":[],"mappings":";;;;;;;AAAA,MAAA,wBAAA,gBAAA,OAAA,CAAA,kCAAA,CAAA,C,CAoBA;;;AACa,OAAA,CAAA,eAAA,gBAAkB,wBAAA,CAAA,aAAA,CAAoC;EACjE,YAAY,EAAE,SADmD;EAEjE,UAAU,EAAE,SAFqD;EAGjE,YAAY,EAAE,KAHmD;EAIjE,IAAI,EAAE,KAJ2D;;EAKjE,cAAc,GAAA;IACZ,OAAO,MAAM,SAAb;EACD,CAPgE;;EAQjE,eAAe,EAAE,EARgD;;EASjE,YAAY,GAAA,CACV;EACD,CAXgE;;EAYjE,eAAe,GAAA,CACb;EACD,CAdgE;;EAejE,OAAO,GAAA,CACL;EACD,CAjBgE;;EAkBjE,IAAI,EAAE;AAlB2D,CAApC,CAAlB","sourcesContent":["import { createContext } from '@fluentui/react-context-selector';\nimport { ComboboxState } from '../components/Combobox/Combobox.types';\n\n/**\n * Context shared with Combobox, Listbox, & Options\n */\nexport type ComboboxContextValue = Pick<\n ComboboxState,\n | 'activeOption'\n | 'appearance'\n | 'focusVisible'\n | 'open'\n | 'registerOption'\n | 'selectedOptions'\n | 'selectOption'\n | 'setActiveOption'\n | 'setOpen'\n | 'size'\n>;\n\n// eslint-disable-next-line @fluentui/no-context-default-value\nexport const ComboboxContext = createContext<ComboboxContextValue>({\n activeOption: undefined,\n appearance: 'outline',\n focusVisible: false,\n open: false,\n registerOption() {\n return () => undefined;\n },\n selectedOptions: [],\n selectOption() {\n // noop\n },\n setActiveOption() {\n // noop\n },\n setOpen() {\n // noop\n },\n size: 'medium',\n});\n"],"sourceRoot":"../src/"}
|
|
@@ -10,15 +10,20 @@ const react_context_selector_1 = /*#__PURE__*/require("@fluentui/react-context-s
|
|
|
10
10
|
|
|
11
11
|
exports.ListboxContext = /*#__PURE__*/react_context_selector_1.createContext({
|
|
12
12
|
activeOption: undefined,
|
|
13
|
+
focusVisible: false,
|
|
13
14
|
multiselect: false,
|
|
14
15
|
|
|
15
|
-
onOptionClick() {// noop
|
|
16
|
-
},
|
|
17
|
-
|
|
18
16
|
registerOption() {
|
|
19
17
|
return () => undefined;
|
|
20
18
|
},
|
|
21
19
|
|
|
22
|
-
selectedOptions: []
|
|
20
|
+
selectedOptions: [],
|
|
21
|
+
|
|
22
|
+
selectOption() {// noop
|
|
23
|
+
},
|
|
24
|
+
|
|
25
|
+
setActiveOption() {// noop
|
|
26
|
+
}
|
|
27
|
+
|
|
23
28
|
});
|
|
24
29
|
//# sourceMappingURL=ListboxContext.js.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"sources":["contexts/ListboxContext.ts"],"names":[],"mappings":";;;;;;;AAAA,MAAA,wBAAA,gBAAA,OAAA,CAAA,kCAAA,CAAA,C,
|
|
1
|
+
{"version":3,"sources":["contexts/ListboxContext.ts"],"names":[],"mappings":";;;;;;;AAAA,MAAA,wBAAA,gBAAA,OAAA,CAAA,kCAAA,CAAA,C,CAiBA;;;AACa,OAAA,CAAA,cAAA,gBAAiB,wBAAA,CAAA,aAAA,CAAmC;EAC/D,YAAY,EAAE,SADiD;EAE/D,YAAY,EAAE,KAFiD;EAG/D,WAAW,EAAE,KAHkD;;EAI/D,cAAc,GAAA;IACZ,OAAO,MAAM,SAAb;EACD,CAN8D;;EAO/D,eAAe,EAAE,EAP8C;;EAQ/D,YAAY,GAAA,CACV;EACD,CAV8D;;EAW/D,eAAe,GAAA,CACb;EACD;;AAb8D,CAAnC,CAAjB","sourcesContent":["import { createContext } from '@fluentui/react-context-selector';\nimport { ListboxState } from '../components/Listbox/Listbox.types';\n\n/**\n * Context shared with all Listbox Options\n */\nexport type ListboxContextValue = Pick<\n ListboxState,\n | 'activeOption'\n | 'focusVisible'\n | 'multiselect'\n | 'registerOption'\n | 'selectedOptions'\n | 'selectOption'\n | 'setActiveOption'\n>;\n\n// eslint-disable-next-line @fluentui/no-context-default-value\nexport const ListboxContext = createContext<ListboxContextValue>({\n activeOption: undefined,\n focusVisible: false,\n multiselect: false,\n registerOption() {\n return () => undefined;\n },\n selectedOptions: [],\n selectOption() {\n // noop\n },\n setActiveOption() {\n // noop\n },\n});\n"],"sourceRoot":"../src/"}
|
|
@@ -9,19 +9,25 @@ function useComboboxContextValues(state) {
|
|
|
9
9
|
const {
|
|
10
10
|
activeOption,
|
|
11
11
|
appearance,
|
|
12
|
-
|
|
12
|
+
focusVisible,
|
|
13
13
|
open,
|
|
14
14
|
registerOption,
|
|
15
15
|
selectedOptions,
|
|
16
|
+
selectOption,
|
|
17
|
+
setActiveOption,
|
|
18
|
+
setOpen,
|
|
16
19
|
size
|
|
17
20
|
} = state;
|
|
18
21
|
const combobox = {
|
|
19
22
|
activeOption,
|
|
20
23
|
appearance,
|
|
24
|
+
focusVisible,
|
|
21
25
|
open,
|
|
22
|
-
onOptionClick,
|
|
23
26
|
registerOption,
|
|
24
27
|
selectedOptions,
|
|
28
|
+
selectOption,
|
|
29
|
+
setActiveOption,
|
|
30
|
+
setOpen,
|
|
25
31
|
size
|
|
26
32
|
};
|
|
27
33
|
return {
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"sources":["contexts/useComboboxContextValues.ts"],"names":[],"mappings":";;;;;;;AAEA,SAAgB,wBAAhB,CAAyC,KAAzC,EAAiE;EAC/D,MAAM;
|
|
1
|
+
{"version":3,"sources":["contexts/useComboboxContextValues.ts"],"names":[],"mappings":";;;;;;;AAEA,SAAgB,wBAAhB,CAAyC,KAAzC,EAAiE;EAC/D,MAAM;IACJ,YADI;IAEJ,UAFI;IAGJ,YAHI;IAIJ,IAJI;IAKJ,cALI;IAMJ,eANI;IAOJ,YAPI;IAQJ,eARI;IASJ,OATI;IAUJ;EAVI,IAWF,KAXJ;EAaA,MAAM,QAAQ,GAAG;IACf,YADe;IAEf,UAFe;IAGf,YAHe;IAIf,IAJe;IAKf,cALe;IAMf,eANe;IAOf,YAPe;IAQf,eARe;IASf,OATe;IAUf;EAVe,CAAjB;EAaA,OAAO;IAAE;EAAF,CAAP;AACD;;AA5BD,OAAA,CAAA,wBAAA,GAAA,wBAAA","sourcesContent":["import { ComboboxBaseContextValues, ComboboxBaseState } from '../utils/ComboboxBase.types';\n\nexport function useComboboxContextValues(state: ComboboxBaseState): ComboboxBaseContextValues {\n const {\n activeOption,\n appearance,\n focusVisible,\n open,\n registerOption,\n selectedOptions,\n selectOption,\n setActiveOption,\n setOpen,\n size,\n } = state;\n\n const combobox = {\n activeOption,\n appearance,\n focusVisible,\n open,\n registerOption,\n selectedOptions,\n selectOption,\n setActiveOption,\n setOpen,\n size,\n };\n\n return { combobox };\n}\n"],"sourceRoot":"../src/"}
|
|
@@ -13,20 +13,24 @@ function useListboxContextValues(state) {
|
|
|
13
13
|
const hasComboboxContext = react_context_selector_1.useHasParentContext(ComboboxContext_1.ComboboxContext);
|
|
14
14
|
const {
|
|
15
15
|
activeOption,
|
|
16
|
+
focusVisible,
|
|
16
17
|
multiselect,
|
|
17
|
-
onOptionClick,
|
|
18
18
|
registerOption,
|
|
19
|
-
selectedOptions
|
|
19
|
+
selectedOptions,
|
|
20
|
+
selectOption,
|
|
21
|
+
setActiveOption
|
|
20
22
|
} = state; // get register/unregister functions from parent combobox context
|
|
21
23
|
|
|
22
24
|
const comboboxRegisterOption = react_context_selector_1.useContextSelector(ComboboxContext_1.ComboboxContext, ctx => ctx.registerOption);
|
|
23
25
|
const registerOptionValue = hasComboboxContext ? comboboxRegisterOption : registerOption;
|
|
24
26
|
const listbox = {
|
|
25
27
|
activeOption,
|
|
28
|
+
focusVisible,
|
|
26
29
|
multiselect,
|
|
27
|
-
|
|
30
|
+
registerOption: registerOptionValue,
|
|
28
31
|
selectedOptions,
|
|
29
|
-
|
|
32
|
+
selectOption,
|
|
33
|
+
setActiveOption
|
|
30
34
|
};
|
|
31
35
|
return {
|
|
32
36
|
listbox
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"sources":["contexts/useListboxContextValues.ts"],"names":[],"mappings":";;;;;;;AAAA,MAAA,wBAAA,gBAAA,OAAA,CAAA,kCAAA,CAAA;;AAEA,MAAA,iBAAA,gBAAA,OAAA,CAAA,mBAAA,CAAA;;AAEA,SAAgB,uBAAhB,CAAwC,KAAxC,EAA2D;EACzD,MAAM,kBAAkB,GAAG,wBAAA,CAAA,mBAAA,CAAoB,iBAAA,CAAA,eAApB,CAA3B;EACA,MAAM;
|
|
1
|
+
{"version":3,"sources":["contexts/useListboxContextValues.ts"],"names":[],"mappings":";;;;;;;AAAA,MAAA,wBAAA,gBAAA,OAAA,CAAA,kCAAA,CAAA;;AAEA,MAAA,iBAAA,gBAAA,OAAA,CAAA,mBAAA,CAAA;;AAEA,SAAgB,uBAAhB,CAAwC,KAAxC,EAA2D;EACzD,MAAM,kBAAkB,GAAG,wBAAA,CAAA,mBAAA,CAAoB,iBAAA,CAAA,eAApB,CAA3B;EACA,MAAM;IACJ,YADI;IAEJ,YAFI;IAGJ,WAHI;IAIJ,cAJI;IAKJ,eALI;IAMJ,YANI;IAOJ;EAPI,IAQF,KARJ,CAFyD,CAYzD;;EACA,MAAM,sBAAsB,GAAG,wBAAA,CAAA,kBAAA,CAAmB,iBAAA,CAAA,eAAnB,EAAoC,GAAG,IAAI,GAAG,CAAC,cAA/C,CAA/B;EAEA,MAAM,mBAAmB,GAAG,kBAAkB,GAAG,sBAAH,GAA4B,cAA1E;EAEA,MAAM,OAAO,GAAG;IACd,YADc;IAEd,YAFc;IAGd,WAHc;IAId,cAAc,EAAE,mBAJF;IAKd,eALc;IAMd,YANc;IAOd;EAPc,CAAhB;EAUA,OAAO;IAAE;EAAF,CAAP;AACD;;AA5BD,OAAA,CAAA,uBAAA,GAAA,uBAAA","sourcesContent":["import { useContextSelector, useHasParentContext } from '@fluentui/react-context-selector';\nimport { ListboxContextValues, ListboxState } from '../components/Listbox/Listbox.types';\nimport { ComboboxContext } from './ComboboxContext';\n\nexport function useListboxContextValues(state: ListboxState): ListboxContextValues {\n const hasComboboxContext = useHasParentContext(ComboboxContext);\n const {\n activeOption,\n focusVisible,\n multiselect,\n registerOption,\n selectedOptions,\n selectOption,\n setActiveOption,\n } = state;\n\n // get register/unregister functions from parent combobox context\n const comboboxRegisterOption = useContextSelector(ComboboxContext, ctx => ctx.registerOption);\n\n const registerOptionValue = hasComboboxContext ? comboboxRegisterOption : registerOption;\n\n const listbox = {\n activeOption,\n focusVisible,\n multiselect,\n registerOption: registerOptionValue,\n selectedOptions,\n selectOption,\n setActiveOption,\n };\n\n return { listbox };\n}\n"],"sourceRoot":"../src/"}
|
|
@@ -52,11 +52,11 @@ function getDropdownActionFromKey(e, options = {}) {
|
|
|
52
52
|
} // navigation interactions
|
|
53
53
|
|
|
54
54
|
|
|
55
|
-
if (code === keys.
|
|
55
|
+
if (code === keys.ArrowDown) {
|
|
56
56
|
return 'Next';
|
|
57
57
|
}
|
|
58
58
|
|
|
59
|
-
if (code === keys.
|
|
59
|
+
if (code === keys.ArrowUp) {
|
|
60
60
|
return 'Previous';
|
|
61
61
|
}
|
|
62
62
|
|
|
@@ -109,13 +109,6 @@ function getIndexFromAction(action, currentIndex, maxIndex) {
|
|
|
109
109
|
|
|
110
110
|
case 'PageUp':
|
|
111
111
|
return Math.max(0, currentIndex - 10);
|
|
112
|
-
// case 'Type':
|
|
113
|
-
// // always prevent default and stop propagation when typing
|
|
114
|
-
// e.preventDefault();
|
|
115
|
-
// e.stopPropagation();
|
|
116
|
-
// const matchingIndex = findByCharacter(e.key);
|
|
117
|
-
// return matchingIndex > -1 ? matchingIndex : activeIndex;
|
|
118
|
-
// break;
|
|
119
112
|
|
|
120
113
|
default:
|
|
121
114
|
return currentIndex;
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"sources":["utils/dropdownKeyActions.ts"],"names":[],"mappings":";;;;;;;AAAA,MAAA,IAAA,gBAAA,OAAA,CAAA,yBAAA,CAAA;AA2BA;;AAEG;;;AACH,SAAgB,wBAAhB,CACE,CADF,EAEE,OAAA,GAAiC,EAFnC,EAEqC;EAEnC,MAAM;IAAE,IAAI,GAAG,IAAT;IAAe,WAAW,GAAG;EAA7B,IAAuC,OAA7C;EACA,MAAM,IAAI,GAAG,CAAC,CAAC,GAAf;EACA,MAAM;IAAE,MAAF;IAAU,OAAV;IAAmB,GAAnB;IAAwB;EAAxB,IAAoC,CAA1C,CAJmC,CAMnC;;EACA,IAAI,GAAG,CAAC,MAAJ,KAAe,CAAf,IAAoB,IAAI,KAAK,IAAI,CAAC,KAAlC,IAA2C,CAAC,MAA5C,IAAsD,CAAC,OAAvD,IAAkE,CAAC,OAAvE,EAAgF;IAC9E,OAAO,MAAP;EACD,CATkC,CAWnC;;;EACA,IAAI,CAAC,IAAL,EAAW;IACT,IAAI,IAAI,KAAK,IAAI,CAAC,SAAd,IAA2B,IAAI,KAAK,IAAI,CAAC,OAAzC,IAAoD,IAAI,KAAK,IAAI,CAAC,KAAlE,IAA2E,IAAI,KAAK,IAAI,CAAC,KAA7F,EAAoG;MAClG,OAAO,MAAP;IACD,CAHQ,CAKT;;;IACA,OAAO,MAAP;EACD,CAnBkC,CAqBnC;;;EACA,IAAK,IAAI,KAAK,IAAI,CAAC,OAAd,IAAyB,MAA1B,IAAqC,IAAI,KAAK,IAAI,CAAC,KAAnD,IAA6D,CAAC,WAAD,IAAgB,IAAI,KAAK,IAAI,CAAC,KAA/F,EAAuG;IACrG,OAAO,aAAP;EACD;;EACD,IAAI,WAAW,IAAI,IAAI,KAAK,IAAI,CAAC,KAAjC,EAAwC;IACtC,OAAO,QAAP;EACD;;EACD,IAAI,IAAI,KAAK,IAAI,CAAC,MAAlB,EAA0B;IACxB,OAAO,OAAP;EACD,CA9BkC,CAgCnC;;;EACA,IAAI,IAAI,KAAK,IAAI,CAAC,
|
|
1
|
+
{"version":3,"sources":["utils/dropdownKeyActions.ts"],"names":[],"mappings":"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","sourcesContent":["import * as keys from '@fluentui/keyboard-keys';\nimport * as React from 'react';\n\n/**\n * enum of actions available in any type of managed dropdown control\n * e.g. combobox, select, datepicker, menu\n */\nexport type DropdownActions =\n | 'Close'\n | 'CloseSelect'\n | 'First'\n | 'Last'\n | 'Next'\n | 'None'\n | 'Open'\n | 'PageDown'\n | 'PageUp'\n | 'Previous'\n | 'Select'\n | 'Tab'\n | 'Type';\n\nexport interface DropdownActionOptions {\n open?: boolean;\n multiselect?: boolean;\n}\n\n/**\n * Converts a keyboard interaction into a defined action\n */\nexport function getDropdownActionFromKey(\n e: KeyboardEvent | React.KeyboardEvent,\n options: DropdownActionOptions = {},\n): DropdownActions {\n const { open = true, multiselect = false } = options;\n const code = e.key;\n const { altKey, ctrlKey, key, metaKey } = e;\n\n // typing action occurs whether open or closed\n if (key.length === 1 && code !== keys.Space && !altKey && !ctrlKey && !metaKey) {\n return 'Type';\n }\n\n // handle opening the dropdown if closed\n if (!open) {\n if (code === keys.ArrowDown || code === keys.ArrowUp || code === keys.Enter || code === keys.Space) {\n return 'Open';\n }\n\n // if the dropdown is closed and an action did not match the above, do nothing\n return 'None';\n }\n\n // select or close actions\n if ((code === keys.ArrowUp && altKey) || code === keys.Enter || (!multiselect && code === keys.Space)) {\n return 'CloseSelect';\n }\n if (multiselect && code === keys.Space) {\n return 'Select';\n }\n if (code === keys.Escape) {\n return 'Close';\n }\n\n // navigation interactions\n if (code === keys.ArrowDown) {\n return 'Next';\n }\n if (code === keys.ArrowUp) {\n return 'Previous';\n }\n if (code === keys.Home) {\n return 'First';\n }\n if (code === keys.End) {\n return 'Last';\n }\n if (code === keys.PageUp) {\n return 'PageUp';\n }\n if (code === keys.PageDown) {\n return 'PageDown';\n }\n if (code === keys.Tab) {\n return 'Tab';\n }\n\n // if nothing matched, return none\n return 'None';\n}\n\n/**\n * Returns the requested option index from an action\n */\nexport function getIndexFromAction(action: DropdownActions, currentIndex: number, maxIndex: number): number {\n switch (action) {\n case 'Next':\n return Math.min(maxIndex, currentIndex + 1);\n break;\n case 'Previous':\n return Math.max(0, currentIndex - 1);\n case 'First':\n return 0;\n case 'Last':\n return maxIndex;\n case 'PageDown':\n return Math.min(maxIndex, currentIndex + 10);\n case 'PageUp':\n return Math.max(0, currentIndex - 10);\n default:\n return currentIndex;\n }\n}\n"],"sourceRoot":"../src/"}
|
|
@@ -28,21 +28,31 @@ const useComboboxBaseState = props => {
|
|
|
28
28
|
const optionCollection = useOptionCollection_1.useOptionCollection();
|
|
29
29
|
const {
|
|
30
30
|
getOptionAtIndex,
|
|
31
|
-
getOptionById,
|
|
32
31
|
getOptionsMatchingValue
|
|
33
32
|
} = optionCollection;
|
|
34
|
-
const [activeOption, setActiveOption] = React.useState();
|
|
33
|
+
const [activeOption, setActiveOption] = React.useState(); // track whether keyboard focus outline should be shown
|
|
34
|
+
// tabster/keyborg doesn't work here, since the actual keyboard focus target doesn't move
|
|
35
|
+
|
|
36
|
+
const [focusVisible, setFocusVisible] = React.useState(false); // track focused state to conditionally render collapsed listbox
|
|
37
|
+
|
|
38
|
+
const [hasFocus, setHasFocus] = React.useState(false);
|
|
39
|
+
const ignoreNextBlur = React.useRef(false);
|
|
40
|
+
const selectionState = useSelection_1.useSelection(props);
|
|
35
41
|
const {
|
|
36
|
-
selectedOptions
|
|
37
|
-
|
|
38
|
-
} = useSelection_1.useSelection(props); // update value based on selectedOptions
|
|
42
|
+
selectedOptions
|
|
43
|
+
} = selectionState; // calculate value based on props, internal value changes, and selected options
|
|
39
44
|
|
|
40
45
|
const isFirstMount = react_utilities_1.useFirstMount();
|
|
46
|
+
const [controllableValue, setValue] = react_utilities_1.useControllableState({
|
|
47
|
+
state: props.value,
|
|
48
|
+
initialState: undefined
|
|
49
|
+
});
|
|
41
50
|
const value = React.useMemo(() => {
|
|
42
|
-
// don't compute value if it is defined through props,
|
|
43
|
-
if (
|
|
44
|
-
return
|
|
45
|
-
}
|
|
51
|
+
// don't compute the value if it is defined through props or setValue,
|
|
52
|
+
if (controllableValue !== undefined) {
|
|
53
|
+
return controllableValue;
|
|
54
|
+
} // handle defaultValue here, so it is overridden by selection
|
|
55
|
+
|
|
46
56
|
|
|
47
57
|
if (isFirstMount && props.defaultValue !== undefined) {
|
|
48
58
|
return props.defaultValue;
|
|
@@ -53,7 +63,7 @@ const useComboboxBaseState = props => {
|
|
|
53
63
|
}
|
|
54
64
|
|
|
55
65
|
return selectedOptions[0];
|
|
56
|
-
}, [isFirstMount, multiselect, props.defaultValue,
|
|
66
|
+
}, [controllableValue, isFirstMount, multiselect, props.defaultValue, selectedOptions]); // Handle open state, which is shared with options in context
|
|
57
67
|
|
|
58
68
|
const [open, setOpenState] = react_utilities_1.useControllableState({
|
|
59
69
|
state: props.open,
|
|
@@ -66,20 +76,11 @@ const useComboboxBaseState = props => {
|
|
|
66
76
|
open: newState
|
|
67
77
|
});
|
|
68
78
|
setOpenState(newState);
|
|
69
|
-
};
|
|
70
|
-
|
|
71
|
-
const onOptionClick = (event, option) => {
|
|
72
|
-
// clicked option should always become active option
|
|
73
|
-
setActiveOption(getOptionById(option.id)); // close on option click for single-select
|
|
74
|
-
|
|
75
|
-
!multiselect && setOpen(event, false); // handle selection change
|
|
76
|
-
|
|
77
|
-
selectOption(event, option);
|
|
78
79
|
}; // update active option based on change in open state
|
|
79
80
|
|
|
80
81
|
|
|
81
82
|
React.useEffect(() => {
|
|
82
|
-
if (open) {
|
|
83
|
+
if (open && !activeOption) {
|
|
83
84
|
// if there is a selection, start at the most recently selected item
|
|
84
85
|
if (selectedOptions.length > 0) {
|
|
85
86
|
const lastSelectedOption = getOptionsMatchingValue(v => v === selectedOptions[selectedOptions.length - 1]).pop();
|
|
@@ -88,7 +89,7 @@ const useComboboxBaseState = props => {
|
|
|
88
89
|
else {
|
|
89
90
|
setActiveOption(getOptionAtIndex(0));
|
|
90
91
|
}
|
|
91
|
-
} else {
|
|
92
|
+
} else if (!open) {
|
|
92
93
|
// reset the active option when closing
|
|
93
94
|
setActiveOption(undefined);
|
|
94
95
|
} // this should only be run in response to changes in the open state
|
|
@@ -96,15 +97,19 @@ const useComboboxBaseState = props => {
|
|
|
96
97
|
|
|
97
98
|
}, [open]);
|
|
98
99
|
return { ...optionCollection,
|
|
100
|
+
...selectionState,
|
|
99
101
|
activeOption,
|
|
100
102
|
appearance,
|
|
103
|
+
focusVisible,
|
|
104
|
+
hasFocus,
|
|
105
|
+
ignoreNextBlur,
|
|
101
106
|
inlinePopup,
|
|
102
|
-
onOptionClick,
|
|
103
107
|
open,
|
|
104
|
-
selectedOptions,
|
|
105
|
-
selectOption,
|
|
106
108
|
setActiveOption,
|
|
109
|
+
setFocusVisible,
|
|
110
|
+
setHasFocus,
|
|
107
111
|
setOpen,
|
|
112
|
+
setValue,
|
|
108
113
|
size,
|
|
109
114
|
value
|
|
110
115
|
};
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"sources":["utils/useComboboxBaseState.ts"],"names":[],"mappings":";;;;;;;AAAA,MAAA,KAAA,gBAAA,OAAA,CAAA,OAAA,CAAA;;AACA,MAAA,iBAAA,gBAAA,OAAA,CAAA,2BAAA,CAAA;;AACA,MAAA,qBAAA,gBAAA,OAAA,CAAA,8BAAA,CAAA;;AAEA,MAAA,cAAA,gBAAA,OAAA,CAAA,uBAAA,CAAA;AAGA;;AAEG;;;AACI,MAAM,oBAAoB,GAAI,KAAD,IAA6B;EAC/D,MAAM;IAAE,UAAU,GAAG,SAAf;IAA0B,WAAW,GAAG,KAAxC;IAA+C,WAA/C;IAA4D,YAA5D;IAA0E,IAAI,GAAG;EAAjF,IAA8F,KAApG;EAEA,MAAM,gBAAgB,GAAG,qBAAA,CAAA,mBAAA,EAAzB;EACA,MAAM;IAAE,gBAAF;IAAoB
|
|
1
|
+
{"version":3,"sources":["utils/useComboboxBaseState.ts"],"names":[],"mappings":"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","sourcesContent":["import * as React from 'react';\nimport { useControllableState, useFirstMount } from '@fluentui/react-utilities';\nimport { useOptionCollection } from '../utils/useOptionCollection';\nimport { OptionValue } from '../utils/OptionCollection.types';\nimport { useSelection } from '../utils/useSelection';\nimport type { ComboboxBaseProps, ComboboxBaseOpenEvents } from './ComboboxBase.types';\n\n/**\n * State shared between Combobox and Dropdown components\n */\nexport const useComboboxBaseState = (props: ComboboxBaseProps) => {\n const { appearance = 'outline', inlinePopup = false, multiselect, onOpenChange, size = 'medium' } = props;\n\n const optionCollection = useOptionCollection();\n const { getOptionAtIndex, getOptionsMatchingValue } = optionCollection;\n\n const [activeOption, setActiveOption] = React.useState<OptionValue | undefined>();\n\n // track whether keyboard focus outline should be shown\n // tabster/keyborg doesn't work here, since the actual keyboard focus target doesn't move\n const [focusVisible, setFocusVisible] = React.useState(false);\n\n // track focused state to conditionally render collapsed listbox\n const [hasFocus, setHasFocus] = React.useState(false);\n\n const ignoreNextBlur = React.useRef(false);\n\n const selectionState = useSelection(props);\n const { selectedOptions } = selectionState;\n\n // calculate value based on props, internal value changes, and selected options\n const isFirstMount = useFirstMount();\n const [controllableValue, setValue] = useControllableState({\n state: props.value,\n initialState: undefined,\n });\n\n const value = React.useMemo(() => {\n // don't compute the value if it is defined through props or setValue,\n if (controllableValue !== undefined) {\n return controllableValue;\n }\n\n // handle defaultValue here, so it is overridden by selection\n if (isFirstMount && props.defaultValue !== undefined) {\n return props.defaultValue;\n }\n\n if (multiselect) {\n return selectedOptions.join(', ');\n }\n\n return selectedOptions[0];\n }, [controllableValue, isFirstMount, multiselect, props.defaultValue, selectedOptions]);\n\n // Handle open state, which is shared with options in context\n const [open, setOpenState] = useControllableState({\n state: props.open,\n defaultState: props.defaultOpen,\n initialState: false,\n });\n\n const setOpen = (event: ComboboxBaseOpenEvents, newState: boolean) => {\n onOpenChange?.(event, { open: newState });\n setOpenState(newState);\n };\n\n // update active option based on change in open state\n React.useEffect(() => {\n if (open && !activeOption) {\n // if there is a selection, start at the most recently selected item\n if (selectedOptions.length > 0) {\n const lastSelectedOption = getOptionsMatchingValue(\n v => v === selectedOptions[selectedOptions.length - 1],\n ).pop();\n lastSelectedOption && setActiveOption(lastSelectedOption);\n }\n // default to starting at the first option\n else {\n setActiveOption(getOptionAtIndex(0));\n }\n } else if (!open) {\n // reset the active option when closing\n setActiveOption(undefined);\n }\n // this should only be run in response to changes in the open state\n // eslint-disable-next-line react-hooks/exhaustive-deps\n }, [open]);\n\n return {\n ...optionCollection,\n ...selectionState,\n activeOption,\n appearance,\n focusVisible,\n hasFocus,\n ignoreNextBlur,\n inlinePopup,\n open,\n setActiveOption,\n setFocusVisible,\n setHasFocus,\n setOpen,\n setValue,\n size,\n value,\n };\n};\n"],"sourceRoot":"../src/"}
|
|
@@ -27,11 +27,13 @@ function useComboboxPopup(props, triggerShorthand, listboxShorthand) {
|
|
|
27
27
|
targetRef,
|
|
28
28
|
containerRef
|
|
29
29
|
} = react_positioning_1.usePositioning(popperOptions);
|
|
30
|
+
const listboxRef = react_utilities_1.useMergedRefs(listboxShorthand === null || listboxShorthand === void 0 ? void 0 : listboxShorthand.ref, containerRef);
|
|
31
|
+
const listbox = listboxShorthand && { ...listboxShorthand,
|
|
32
|
+
ref: listboxRef
|
|
33
|
+
};
|
|
30
34
|
return [{ ...triggerShorthand,
|
|
31
35
|
ref: react_utilities_1.useMergedRefs(triggerShorthand === null || triggerShorthand === void 0 ? void 0 : triggerShorthand.ref, targetRef)
|
|
32
|
-
},
|
|
33
|
-
ref: react_utilities_1.useMergedRefs(listboxShorthand === null || listboxShorthand === void 0 ? void 0 : listboxShorthand.ref, containerRef)
|
|
34
|
-
}];
|
|
36
|
+
}, listbox];
|
|
35
37
|
}
|
|
36
38
|
|
|
37
39
|
exports.useComboboxPopup = useComboboxPopup;
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"sources":["utils/useComboboxPopup.ts"],"names":[],"mappings":";;;;;;;AAAA,MAAA,mBAAA,gBAAA,OAAA,CAAA,6BAAA,CAAA;;AACA,MAAA,iBAAA,gBAAA,OAAA,CAAA,2BAAA,CAAA;;AAeA,SAAgB,gBAAhB,CACE,KADF,EAEE,gBAFF,EAGE,gBAHF,EAG2D;
|
|
1
|
+
{"version":3,"sources":["utils/useComboboxPopup.ts"],"names":[],"mappings":";;;;;;;AAAA,MAAA,mBAAA,gBAAA,OAAA,CAAA,6BAAA,CAAA;;AACA,MAAA,iBAAA,gBAAA,OAAA,CAAA,2BAAA,CAAA;;AAeA,SAAgB,gBAAhB,CACE,KADF,EAEE,gBAFF,EAGE,gBAHF,EAG2D;EAKzD,MAAM;IAAE;EAAF,IAAkB,KAAxB,CALyD,CAOzD;;EACA,MAAM,aAAa,GAAG;IACpB,QAAQ,EAAE,OADU;IAEpB,KAAK,EAAE,OAFa;IAGpB,MAAM,EAAE;MAAE,SAAS,EAAE,CAAb;MAAgB,QAAQ,EAAE;IAA1B,CAHY;IAIpB,GAAG,mBAAA,CAAA,2BAAA,CAA4B,WAA5B;EAJiB,CAAtB;EAOA,MAAM;IAAE,SAAF;IAAa;EAAb,IAA8B,mBAAA,CAAA,cAAA,CAAe,aAAf,CAApC;EAEA,MAAM,UAAU,GAAG,iBAAA,CAAA,aAAA,CAAc,gBAAgB,KAAA,IAAhB,IAAA,gBAAgB,KAAA,KAAA,CAAhB,GAAgB,KAAA,CAAhB,GAAA,gBAAgB,CAAE,GAAhC,EAAqC,YAArC,CAAnB;EACA,MAAM,OAAO,GAAG,gBAAgB,IAAI,EAAE,GAAG,gBAAL;IAAuB,GAAG,EAAE;EAA5B,CAApC;EAEA,OAAO,CAAC,EAAE,GAAG,gBAAL;IAAuB,GAAG,EAAE,iBAAA,CAAA,aAAA,CAAc,gBAAgB,KAAA,IAAhB,IAAA,gBAAgB,KAAA,KAAA,CAAhB,GAAgB,KAAA,CAAhB,GAAA,gBAAgB,CAAE,GAAhC,EAAqC,SAArC;EAA5B,CAAD,EAAgF,OAAhF,CAAP;AACD;;AAxBD,OAAA,CAAA,gBAAA,GAAA,gBAAA","sourcesContent":["import { resolvePositioningShorthand, usePositioning } from '@fluentui/react-positioning';\nimport { ExtractSlotProps, Slot, useMergedRefs } from '@fluentui/react-utilities';\nimport type { ComboboxBaseProps } from './ComboboxBase.types';\nimport { Listbox } from '../components/Listbox/Listbox';\n\nexport function useComboboxPopup(\n props: ComboboxBaseProps,\n triggerShorthand?: ExtractSlotProps<Slot<'button'>>,\n listboxShorthand?: ExtractSlotProps<Slot<typeof Listbox>>,\n): [trigger: ExtractSlotProps<Slot<'button'>>, listbox?: ExtractSlotProps<Slot<typeof Listbox>>];\nexport function useComboboxPopup(\n props: ComboboxBaseProps,\n triggerShorthand?: ExtractSlotProps<Slot<'input'>>,\n listboxShorthand?: ExtractSlotProps<Slot<typeof Listbox>>,\n): [trigger: ExtractSlotProps<Slot<'input'>>, listbox?: ExtractSlotProps<Slot<typeof Listbox>>];\n\nexport function useComboboxPopup(\n props: ComboboxBaseProps,\n triggerShorthand?: ExtractSlotProps<Slot<'input'>> | ExtractSlotProps<Slot<'button'>>,\n listboxShorthand?: ExtractSlotProps<Slot<typeof Listbox>>,\n): [\n trigger: ExtractSlotProps<Slot<'input'>> | ExtractSlotProps<Slot<'button'>>,\n listbox?: ExtractSlotProps<Slot<typeof Listbox>>,\n] {\n const { positioning } = props;\n\n // popper options\n const popperOptions = {\n position: 'below' as const,\n align: 'start' as const,\n offset: { crossAxis: 0, mainAxis: 2 },\n ...resolvePositioningShorthand(positioning),\n };\n\n const { targetRef, containerRef } = usePositioning(popperOptions);\n\n const listboxRef = useMergedRefs(listboxShorthand?.ref, containerRef);\n const listbox = listboxShorthand && { ...listboxShorthand, ref: listboxRef };\n\n return [{ ...triggerShorthand, ref: useMergedRefs(triggerShorthand?.ref, targetRef) }, listbox];\n}\n"],"sourceRoot":"../src/"}
|
|
@@ -11,7 +11,7 @@ const useSelection = props => {
|
|
|
11
11
|
const {
|
|
12
12
|
defaultSelectedOptions,
|
|
13
13
|
multiselect,
|
|
14
|
-
|
|
14
|
+
onOptionSelect
|
|
15
15
|
} = props;
|
|
16
16
|
const [selectedOptions, setSelectedOptions] = react_utilities_1.useControllableState({
|
|
17
17
|
state: props.selectedOptions,
|
|
@@ -41,15 +41,24 @@ const useSelection = props => {
|
|
|
41
41
|
}
|
|
42
42
|
|
|
43
43
|
setSelectedOptions(newSelection);
|
|
44
|
-
|
|
44
|
+
onOptionSelect === null || onOptionSelect === void 0 ? void 0 : onOptionSelect(event, {
|
|
45
45
|
optionValue: option.value,
|
|
46
46
|
selectedOptions: newSelection
|
|
47
47
|
});
|
|
48
48
|
};
|
|
49
49
|
|
|
50
|
+
const clearSelection = event => {
|
|
51
|
+
setSelectedOptions([]);
|
|
52
|
+
onOptionSelect === null || onOptionSelect === void 0 ? void 0 : onOptionSelect(event, {
|
|
53
|
+
optionValue: undefined,
|
|
54
|
+
selectedOptions: []
|
|
55
|
+
});
|
|
56
|
+
};
|
|
57
|
+
|
|
50
58
|
return {
|
|
51
|
-
|
|
52
|
-
selectOption
|
|
59
|
+
clearSelection,
|
|
60
|
+
selectOption,
|
|
61
|
+
selectedOptions
|
|
53
62
|
};
|
|
54
63
|
};
|
|
55
64
|
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"sources":["utils/useSelection.ts"],"names":[],"mappings":";;;;;;;AAAA,MAAA,iBAAA,gBAAA,OAAA,CAAA,2BAAA,CAAA;;AAIO,MAAM,YAAY,GAAI,KAAD,IAA0C;EACpE,MAAM;IAAE,sBAAF;IAA0B,WAA1B;IAAuC;EAAvC,
|
|
1
|
+
{"version":3,"sources":["utils/useSelection.ts"],"names":[],"mappings":";;;;;;;AAAA,MAAA,iBAAA,gBAAA,OAAA,CAAA,2BAAA,CAAA;;AAIO,MAAM,YAAY,GAAI,KAAD,IAA0C;EACpE,MAAM;IAAE,sBAAF;IAA0B,WAA1B;IAAuC;EAAvC,IAA0D,KAAhE;EAEA,MAAM,CAAC,eAAD,EAAkB,kBAAlB,IAAwC,iBAAA,CAAA,oBAAA,CAAqB;IACjE,KAAK,EAAE,KAAK,CAAC,eADoD;IAEjE,YAAY,EAAE,sBAFmD;IAGjE,YAAY,EAAE;EAHmD,CAArB,CAA9C;;EAMA,MAAM,YAAY,GAAG,CAAC,KAAD,EAAyB,MAAzB,KAAgD;IACnE;IACA,IAAI,MAAM,CAAC,QAAX,EAAqB;MACnB;IACD,CAJkE,CAMnE;;;IACA,IAAI,YAAY,GAAG,CAAC,MAAM,CAAC,KAAR,CAAnB,CAPmE,CASnE;;IACA,IAAI,WAAJ,EAAiB;MACf,MAAM,aAAa,GAAG,eAAe,CAAC,SAAhB,CAA0B,CAAC,IAAI,CAAC,KAAK,MAAM,CAAC,KAA5C,CAAtB;;MACA,IAAI,aAAa,GAAG,CAAC,CAArB,EAAwB;QACtB;QACA,YAAY,GAAG,CAAC,GAAG,eAAe,CAAC,KAAhB,CAAsB,CAAtB,EAAyB,aAAzB,CAAJ,EAA6C,GAAG,eAAe,CAAC,KAAhB,CAAsB,aAAa,GAAG,CAAtC,CAAhD,CAAf;MACD,CAHD,MAGO;QACL;QACA,YAAY,GAAG,CAAC,GAAG,eAAJ,EAAqB,MAAM,CAAC,KAA5B,CAAf;MACD;IACF;;IAED,kBAAkB,CAAC,YAAD,CAAlB;IACA,cAAc,KAAA,IAAd,IAAA,cAAc,KAAA,KAAA,CAAd,GAAc,KAAA,CAAd,GAAA,cAAc,CAAG,KAAH,EAAU;MAAE,WAAW,EAAE,MAAM,CAAC,KAAtB;MAA6B,eAAe,EAAE;IAA9C,CAAV,CAAd;EACD,CAvBD;;EAyBA,MAAM,cAAc,GAAI,KAAD,IAA2B;IAChD,kBAAkB,CAAC,EAAD,CAAlB;IACA,cAAc,KAAA,IAAd,IAAA,cAAc,KAAA,KAAA,CAAd,GAAc,KAAA,CAAd,GAAA,cAAc,CAAG,KAAH,EAAU;MAAE,WAAW,EAAE,SAAf;MAA0B,eAAe,EAAE;IAA3C,CAAV,CAAd;EACD,CAHD;;EAKA,OAAO;IAAE,cAAF;IAAkB,YAAlB;IAAgC;EAAhC,CAAP;AACD,CAxCM;;AAAM,OAAA,CAAA,YAAA,GAAY,YAAZ","sourcesContent":["import { useControllableState } from '@fluentui/react-utilities';\nimport { OptionValue } from './OptionCollection.types';\nimport { SelectionEvents, SelectionProps, SelectionValue } from './Selection.types';\n\nexport const useSelection = (props: SelectionProps): SelectionValue => {\n const { defaultSelectedOptions, multiselect, onOptionSelect } = props;\n\n const [selectedOptions, setSelectedOptions] = useControllableState({\n state: props.selectedOptions,\n defaultState: defaultSelectedOptions,\n initialState: [],\n });\n\n const selectOption = (event: SelectionEvents, option: OptionValue) => {\n // if the option is disabled, do nothing\n if (option.disabled) {\n return;\n }\n\n // for single-select, always return the selected option\n let newSelection = [option.value];\n\n // toggle selected state of the option for multiselect\n if (multiselect) {\n const selectedIndex = selectedOptions.findIndex(o => o === option.value);\n if (selectedIndex > -1) {\n // deselect option\n newSelection = [...selectedOptions.slice(0, selectedIndex), ...selectedOptions.slice(selectedIndex + 1)];\n } else {\n // select option\n newSelection = [...selectedOptions, option.value];\n }\n }\n\n setSelectedOptions(newSelection);\n onOptionSelect?.(event, { optionValue: option.value, selectedOptions: newSelection });\n };\n\n const clearSelection = (event: SelectionEvents) => {\n setSelectedOptions([]);\n onOptionSelect?.(event, { optionValue: undefined, selectedOptions: [] });\n };\n\n return { clearSelection, selectOption, selectedOptions };\n};\n"],"sourceRoot":"../src/"}
|