From 4a0d20ef71799b2c79151f9611595a75f1176e67 Mon Sep 17 00:00:00 2001 From: miukimiu Date: Wed, 8 Jul 2020 13:39:41 +0100 Subject: [PATCH 01/15] Fixing includes to return true when object exists in array --- src/components/combo_box/combo_box.tsx | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/components/combo_box/combo_box.tsx b/src/components/combo_box/combo_box.tsx index 0c5bd260bc1b..11e2651be735 100644 --- a/src/components/combo_box/combo_box.tsx +++ b/src/components/combo_box/combo_box.tsx @@ -528,7 +528,7 @@ export class EuiComboBox extends Component< Boolean(singleSelection) && onCreateOption && selectedOptions.length > 0 && - !options.includes(selectedOptions[0]) + !JSON.stringify(options).includes(JSON.stringify(selectedOptions[0])) ); }; From 76752a21d521d13bfe4316950789af6a3f3f9de3 Mon Sep 17 00:00:00 2001 From: miukimiu Date: Wed, 8 Jul 2020 14:17:10 +0100 Subject: [PATCH 02/15] changelog --- CHANGELOG.md | 1 + 1 file changed, 1 insertion(+) diff --git a/CHANGELOG.md b/CHANGELOG.md index 60aafb7ed292..2f7f28f484f0 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -12,6 +12,7 @@ No public interface changes since `27.0.0`. - Fixed a bug in `EuiResizableContainer` preventing nested containers ([#3699](https://github.com/elastic/eui/pull/3699)) - Fixed a bug in `EuiResizableContainer` preventing resizing by arrow keys in some cases ([#3699](https://github.com/elastic/eui/pull/3699)) +- Fixed a bug in `EuiComboBox` preventing the options list to open when `singleSelection` and `onCreateOption` are true ([#3706](https://github.com/elastic/eui/pull/3706)) **Breaking changes** From 0cfa8543f0823e2064642a5a6f24f8383ca97db3 Mon Sep 17 00:00:00 2001 From: miukimiu Date: Wed, 15 Jul 2020 12:26:46 +0100 Subject: [PATCH 03/15] Allowing list to open for single selection custom options --- .../src/views/combo_box/combo_box_example.js | 40 +++++++- .../single_selection_custom_options.js | 91 +++++++++++++++++++ src/components/combo_box/combo_box.tsx | 27 +----- 3 files changed, 134 insertions(+), 24 deletions(-) create mode 100644 src-docs/src/views/combo_box/single_selection_custom_options.js diff --git a/src-docs/src/views/combo_box/combo_box_example.js b/src-docs/src/views/combo_box/combo_box_example.js index 4133c4cf74bf..ed0fbc9f93d7 100644 --- a/src-docs/src/views/combo_box/combo_box_example.js +++ b/src-docs/src/views/combo_box/combo_box_example.js @@ -83,7 +83,19 @@ const singleSelectionSnippet = ``; + +import SingleSelectionCustomOptions from './single_selection_custom_options'; +const singleSelectionCustomOptionsSource = require('!!raw-loader!./single_selection_custom_options'); +const singleSelectionCustomOptionsHtml = renderToHtml( + SingleSelectionCustomOptions +); +const singleSelectionCustomOptionsSnippet = ``; import DisallowCustomOptions from './disallow_custom_options'; @@ -405,6 +417,32 @@ export const ComboBoxExample = { snippet: singleSelectionSnippet, demo: , }, + { + title: 'Single selection with custom options', + source: [ + { + type: GuideSectionTypes.JS, + code: singleSelectionCustomOptionsSource, + }, + { + type: GuideSectionTypes.HTML, + code: singleSelectionCustomOptionsHtml, + }, + ], + text: ( + +

+ You can allow the user to select a single option and also allow the + creation of custom options. To do that, use the{' '} + singleSelection in conjunction with the{' '} + onCreateOption prop. +

+
+ ), + props: { EuiComboBox }, + snippet: singleSelectionCustomOptionsSnippet, + demo: , + }, { title: 'Disallowing custom options', source: [ diff --git a/src-docs/src/views/combo_box/single_selection_custom_options.js b/src-docs/src/views/combo_box/single_selection_custom_options.js new file mode 100644 index 000000000000..b7e1fab8697e --- /dev/null +++ b/src-docs/src/views/combo_box/single_selection_custom_options.js @@ -0,0 +1,91 @@ +import React, { useState } from 'react'; + +import { EuiComboBox } from '../../../../src/components'; +import { DisplayToggles } from '../form_controls/display_toggles'; + +const options = [ + { + label: 'Titan', + 'data-test-subj': 'titanOption', + }, + { + label: 'Enceladus', + }, + { + label: 'Mimas', + }, + { + label: 'Dione', + }, + { + label: 'Iapetus', + }, + { + label: 'Phoebe', + }, + { + label: 'Rhea', + }, + { + label: + "Pandora is one of Saturn's moons, named for a Titaness of Greek mythology", + }, + { + label: 'Tethys', + }, + { + label: 'Hyperion', + }, +]; + +export default () => { + const [selectedOptions, setSelected] = useState([options[2]]); + + const onChange = selectedOptions => { + // We should only get back either 0 or 1 options. + setSelected(selectedOptions); + }; + + const onCreateOption = (searchValue, flattenedOptions = []) => { + const normalizedSearchValue = searchValue.trim().toLowerCase(); + + if (!normalizedSearchValue) { + return; + } + + const newOption = { + label: searchValue, + }; + + // Create the option if it doesn't exist. + if ( + flattenedOptions.findIndex( + option => option.label.trim().toLowerCase() === normalizedSearchValue + ) === -1 + ) { + options.push(newOption); + } + + // Select the option. + setSelected([newOption]); + }; + + return ( + + + + ); +}; diff --git a/src/components/combo_box/combo_box.tsx b/src/components/combo_box/combo_box.tsx index 11e2651be735..3fdabb3256ed 100644 --- a/src/components/combo_box/combo_box.tsx +++ b/src/components/combo_box/combo_box.tsx @@ -473,10 +473,7 @@ export class EuiComboBox extends Component< this.clearSearchValue(); - if ( - this.isSingleSelectionCustomOption() || - (Boolean(singleSelection) && matchingOptions.length < 1) - ) { + if (Boolean(singleSelection) && matchingOptions.length < 1) { // Adding a custom option to a single select that does not appear in the list of options this.closeList(); } @@ -516,29 +513,13 @@ export class EuiComboBox extends Component< return flattenOptions.length === numberOfSelectedOptions; }; - isSingleSelectionCustomOption = () => { - const { - onCreateOption, - options, - selectedOptions, - singleSelection, - } = this.props; - // The selected option of a single select is custom and does not appear in the list of options - return ( - Boolean(singleSelection) && - onCreateOption && - selectedOptions.length > 0 && - !JSON.stringify(options).includes(JSON.stringify(selectedOptions[0])) - ); - }; - onComboBoxFocus: FocusEventHandler = event => { if (this.props.onFocus) { this.props.onFocus(event); } - if (!this.isSingleSelectionCustomOption()) { - this.openList(); - } + + this.openList(); + this.setState({ hasFocus: true }); }; From ffddd6af7bd7aca9cbbcac2ee4ccf08284575218 Mon Sep 17 00:00:00 2001 From: miukimiu Date: Wed, 15 Jul 2020 12:44:24 +0100 Subject: [PATCH 04/15] Updated changelog --- CHANGELOG.md | 5 +---- 1 file changed, 1 insertion(+), 4 deletions(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index 6025b724be84..6a57f4170dd6 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -4,10 +4,7 @@ - Removed `src/test` and `@types/enzyme` references from `eui.d.ts` ([#3715](https://github.com/elastic/eui/pull/3715)) - Added `index.d.ts` file to `lib/test` and `es/test` ([#3715](https://github.com/elastic/eui/pull/3715)) - Added `descriptionFlexItemProps` and `fieldFlexItemProps` props to `EuiDescribedFormGroup` ([#3717](https://github.com/elastic/eui/pull/3717)) - -**Bug fixes** - -- Fixed a bug in `EuiComboBox` preventing the options list to open when `singleSelection` and `onCreateOption` are true ([#3706](https://github.com/elastic/eui/pull/3706)) +- Updated `EuiComboBox` to allow the options list to open for single selection custom options ([#3706](https://github.com/elastic/eui/pull/3706)) ## [`27.0.0`](https://github.com/elastic/eui/tree/v27.0.0) - Added `paddingSize` prop to `EuiCard` ([#3638](https://github.com/elastic/eui/pull/3638)) From bc2f62031737c7bb16d06fef8d658a1d82c754b7 Mon Sep 17 00:00:00 2001 From: miukimiu Date: Thu, 16 Jul 2020 11:26:47 +0100 Subject: [PATCH 05/15] PR review --- src/components/combo_box/combo_box.tsx | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/components/combo_box/combo_box.tsx b/src/components/combo_box/combo_box.tsx index 3fdabb3256ed..d964e7ccdb0e 100644 --- a/src/components/combo_box/combo_box.tsx +++ b/src/components/combo_box/combo_box.tsx @@ -473,7 +473,7 @@ export class EuiComboBox extends Component< this.clearSearchValue(); - if (Boolean(singleSelection) && matchingOptions.length < 1) { + if (Boolean(singleSelection)) { // Adding a custom option to a single select that does not appear in the list of options this.closeList(); } From f1f26bed95989982349155840d71bea1e72c151c Mon Sep 17 00:00:00 2001 From: miukimiu Date: Thu, 16 Jul 2020 11:33:21 +0100 Subject: [PATCH 06/15] Improving example --- .../combo_box/single_selection_custom_options.js | 11 +---------- 1 file changed, 1 insertion(+), 10 deletions(-) diff --git a/src-docs/src/views/combo_box/single_selection_custom_options.js b/src-docs/src/views/combo_box/single_selection_custom_options.js index b7e1fab8697e..95c52db1c99d 100644 --- a/src-docs/src/views/combo_box/single_selection_custom_options.js +++ b/src-docs/src/views/combo_box/single_selection_custom_options.js @@ -46,7 +46,7 @@ export default () => { setSelected(selectedOptions); }; - const onCreateOption = (searchValue, flattenedOptions = []) => { + const onCreateOption = (searchValue = []) => { const normalizedSearchValue = searchValue.trim().toLowerCase(); if (!normalizedSearchValue) { @@ -57,15 +57,6 @@ export default () => { label: searchValue, }; - // Create the option if it doesn't exist. - if ( - flattenedOptions.findIndex( - option => option.label.trim().toLowerCase() === normalizedSearchValue - ) === -1 - ) { - options.push(newOption); - } - // Select the option. setSelected([newOption]); }; From 39d2e33631a09df8dab82e4249ae026cb4579c4d Mon Sep 17 00:00:00 2001 From: miukimiu Date: Thu, 16 Jul 2020 19:30:09 +0100 Subject: [PATCH 07/15] Improving example --- .../single_selection_custom_options.js | 40 ++++++------------- 1 file changed, 13 insertions(+), 27 deletions(-) diff --git a/src-docs/src/views/combo_box/single_selection_custom_options.js b/src-docs/src/views/combo_box/single_selection_custom_options.js index 95c52db1c99d..9649c267071a 100644 --- a/src-docs/src/views/combo_box/single_selection_custom_options.js +++ b/src-docs/src/views/combo_box/single_selection_custom_options.js @@ -1,40 +1,29 @@ import React, { useState } from 'react'; -import { EuiComboBox } from '../../../../src/components'; -import { DisplayToggles } from '../form_controls/display_toggles'; +import { EuiComboBox, EuiFormRow } from '../../../../src/components'; const options = [ { - label: 'Titan', - 'data-test-subj': 'titanOption', + label: 'Software Developer', + 'data-test-subj': 'softDevOption', }, { - label: 'Enceladus', + label: 'Mobile Developer', }, { - label: 'Mimas', + label: 'Javascript Engineer', }, { - label: 'Dione', + label: 'UX Designer', }, { - label: 'Iapetus', + label: 'UI Designer', }, { - label: 'Phoebe', + label: 'Product Designer', }, { - label: 'Rhea', - }, - { - label: - "Pandora is one of Saturn's moons, named for a Titaness of Greek mythology", - }, - { - label: 'Tethys', - }, - { - label: 'Hyperion', + label: 'QA Engineer', }, ]; @@ -62,12 +51,9 @@ export default () => { }; return ( - + { onCreateOption={onCreateOption} isClearable={false} /> - + ); }; From a7e9b12681b8d2ab1c74a872633bd445f06edc82 Mon Sep 17 00:00:00 2001 From: miukimiu Date: Thu, 16 Jul 2020 19:37:58 +0100 Subject: [PATCH 08/15] Addind isClearable --- src-docs/src/views/combo_box/single_selection.js | 4 ++-- .../src/views/combo_box/single_selection_custom_options.js | 2 +- 2 files changed, 3 insertions(+), 3 deletions(-) diff --git a/src-docs/src/views/combo_box/single_selection.js b/src-docs/src/views/combo_box/single_selection.js index 38afbf8c1a1c..3877745215b3 100644 --- a/src-docs/src/views/combo_box/single_selection.js +++ b/src-docs/src/views/combo_box/single_selection.js @@ -54,12 +54,12 @@ export default () => { canPrepend canAppend> ); diff --git a/src-docs/src/views/combo_box/single_selection_custom_options.js b/src-docs/src/views/combo_box/single_selection_custom_options.js index 9649c267071a..0866f07c9455 100644 --- a/src-docs/src/views/combo_box/single_selection_custom_options.js +++ b/src-docs/src/views/combo_box/single_selection_custom_options.js @@ -61,7 +61,7 @@ export default () => { selectedOptions={selectedOptions} onChange={onChange} onCreateOption={onCreateOption} - isClearable={false} + isClearable={true} /> ); From 23a0b1040411ad152c16eba98f8f7df217d0e619 Mon Sep 17 00:00:00 2001 From: miukimiu Date: Thu, 16 Jul 2020 22:35:31 +0100 Subject: [PATCH 09/15] Improving examples --- src-docs/src/views/combo_box/single_selection.js | 2 +- src-docs/src/views/combo_box/single_selection_custom_options.js | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/src-docs/src/views/combo_box/single_selection.js b/src-docs/src/views/combo_box/single_selection.js index 3877745215b3..888b522b81a2 100644 --- a/src-docs/src/views/combo_box/single_selection.js +++ b/src-docs/src/views/combo_box/single_selection.js @@ -54,7 +54,7 @@ export default () => { canPrepend canAppend> { label="Your occupation" helpText="Select an occupation from the list. If your occupation isn’t available, create a custom one."> Date: Fri, 17 Jul 2020 12:34:19 +0100 Subject: [PATCH 10/15] Improving explanation text --- src-docs/src/views/combo_box/combo_box_example.js | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/src-docs/src/views/combo_box/combo_box_example.js b/src-docs/src/views/combo_box/combo_box_example.js index ed0fbc9f93d7..f81642427fe0 100644 --- a/src-docs/src/views/combo_box/combo_box_example.js +++ b/src-docs/src/views/combo_box/combo_box_example.js @@ -437,6 +437,10 @@ export const ComboBoxExample = { singleSelection in conjunction with the{' '} onCreateOption prop.

+

+ Creating custom options might not be obvious, so provide a help text + explaining that this option is available. +

), props: { EuiComboBox }, From 16bca05756d2ee6b218e5bd64f244178656a451c Mon Sep 17 00:00:00 2001 From: miukimiu Date: Fri, 17 Jul 2020 12:39:05 +0100 Subject: [PATCH 11/15] Adding note --- src-docs/src/views/combo_box/combo_box_example.js | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/src-docs/src/views/combo_box/combo_box_example.js b/src-docs/src/views/combo_box/combo_box_example.js index f81642427fe0..95dd5747d569 100644 --- a/src-docs/src/views/combo_box/combo_box_example.js +++ b/src-docs/src/views/combo_box/combo_box_example.js @@ -438,8 +438,8 @@ export const ComboBoxExample = { onCreateOption prop.

- Creating custom options might not be obvious, so provide a help text - explaining that this option is available. + Note: Creating custom options might not be obvious, + so provide a help text explaining that this option is available.

), From 4426ccfec7fbfed212d5c5bf71d86c0fb01c7267 Mon Sep 17 00:00:00 2001 From: miukimiu Date: Fri, 17 Jul 2020 16:33:53 +0100 Subject: [PATCH 12/15] Addressing PR issues --- src-docs/src/views/combo_box/combo_box_example.js | 1 + src-docs/src/views/combo_box/single_selection.js | 1 - src-docs/src/views/combo_box/single_selection_custom_options.js | 1 - 3 files changed, 1 insertion(+), 2 deletions(-) diff --git a/src-docs/src/views/combo_box/combo_box_example.js b/src-docs/src/views/combo_box/combo_box_example.js index 95dd5747d569..6f340754fdec 100644 --- a/src-docs/src/views/combo_box/combo_box_example.js +++ b/src-docs/src/views/combo_box/combo_box_example.js @@ -82,6 +82,7 @@ const singleSelectionSnippet = ``; diff --git a/src-docs/src/views/combo_box/single_selection.js b/src-docs/src/views/combo_box/single_selection.js index 888b522b81a2..3da807d85b5a 100644 --- a/src-docs/src/views/combo_box/single_selection.js +++ b/src-docs/src/views/combo_box/single_selection.js @@ -59,7 +59,6 @@ export default () => { options={options} selectedOptions={selectedOptions} onChange={onChange} - isClearable={true} /> ); diff --git a/src-docs/src/views/combo_box/single_selection_custom_options.js b/src-docs/src/views/combo_box/single_selection_custom_options.js index 2cd8f1978904..2f2cc1e9b2ca 100644 --- a/src-docs/src/views/combo_box/single_selection_custom_options.js +++ b/src-docs/src/views/combo_box/single_selection_custom_options.js @@ -61,7 +61,6 @@ export default () => { selectedOptions={selectedOptions} onChange={onChange} onCreateOption={onCreateOption} - isClearable={true} /> ); From aa7d31af70f104e7d3333d8872119528d0e1c22e Mon Sep 17 00:00:00 2001 From: Elizabet Oliveira Date: Fri, 17 Jul 2020 16:34:54 +0100 Subject: [PATCH 13/15] Update src-docs/src/views/combo_box/combo_box_example.js Co-authored-by: Caroline Horn <549577+cchaos@users.noreply.github.com> --- src-docs/src/views/combo_box/combo_box_example.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src-docs/src/views/combo_box/combo_box_example.js b/src-docs/src/views/combo_box/combo_box_example.js index 95dd5747d569..31112055cc01 100644 --- a/src-docs/src/views/combo_box/combo_box_example.js +++ b/src-docs/src/views/combo_box/combo_box_example.js @@ -439,7 +439,7 @@ export const ComboBoxExample = {

Note: Creating custom options might not be obvious, - so provide a help text explaining that this option is available. + so provide help text explaining that this option is available.

), From 70f067c124f441725fd759a818a10201265eff9a Mon Sep 17 00:00:00 2001 From: Elizabet Oliveira Date: Fri, 17 Jul 2020 16:36:49 +0100 Subject: [PATCH 14/15] Update src-docs/src/views/combo_box/combo_box_example.js Co-authored-by: Caroline Horn <549577+cchaos@users.noreply.github.com> --- src-docs/src/views/combo_box/combo_box_example.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src-docs/src/views/combo_box/combo_box_example.js b/src-docs/src/views/combo_box/combo_box_example.js index 4effe0eab2e8..0ec481f843f2 100644 --- a/src-docs/src/views/combo_box/combo_box_example.js +++ b/src-docs/src/views/combo_box/combo_box_example.js @@ -439,7 +439,7 @@ export const ComboBoxExample = { onCreateOption prop.

- Note: Creating custom options might not be obvious, + Note: Creating custom options might not be obvious to the user, so provide help text explaining that this option is available.

From 07202663d1d064119483a5f7cb15df0671e66c5a Mon Sep 17 00:00:00 2001 From: miukimiu Date: Fri, 17 Jul 2020 16:38:03 +0100 Subject: [PATCH 15/15] Snippet --- src-docs/src/views/combo_box/combo_box_example.js | 7 ++++--- 1 file changed, 4 insertions(+), 3 deletions(-) diff --git a/src-docs/src/views/combo_box/combo_box_example.js b/src-docs/src/views/combo_box/combo_box_example.js index 0ec481f843f2..eeed2b836205 100644 --- a/src-docs/src/views/combo_box/combo_box_example.js +++ b/src-docs/src/views/combo_box/combo_box_example.js @@ -82,7 +82,6 @@ const singleSelectionSnippet = ``; @@ -96,6 +95,7 @@ const singleSelectionCustomOptionsSnippet = ``; @@ -439,8 +439,9 @@ export const ComboBoxExample = { onCreateOption prop.

- Note: Creating custom options might not be obvious to the user, - so provide help text explaining that this option is available. + Note: Creating custom options might not be obvious + to the user, so provide help text explaining that this option is + available.

),