Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Allow user-created choices for selects #1117

Closed
wants to merge 2 commits into from
Closed
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
10 changes: 10 additions & 0 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -122,6 +122,7 @@ Or include Choices directly:
choices: [],
renderChoiceLimit: -1,
maxItemCount: -1,
addChoices: false,
addItems: true,
addItemFilter: null,
removeItems: true,
Expand Down Expand Up @@ -304,6 +305,15 @@ Pass an array of objects:

**Usage:** The amount of items a user can input/select ("-1" indicates no limit).

### addChoices
**Type**: `Boolean` **Default:** `false`

**Input types affected:** `select-multiple`, `select-one`

**Usage:** Whether a user can add choices

**Note:** `addItems` must also be `true`

### addItems

**Type:** `Boolean` **Default:** `true`
Expand Down
18 changes: 18 additions & 0 deletions cypress/e2e/select-multiple.spec.ts
Original file line number Diff line number Diff line change
Expand Up @@ -1006,6 +1006,24 @@ describe('Choices - select multiple', () => {
});
});
});

describe('adding user-created choices', () => {
it('allows the user to add choices', () => {
const newChoice = 'New Choice';

cy.get('[data-test-hook=add-choices]')
.find('.choices__input--cloned')
.type(newChoice)
.type('{enter}');

cy.get('[data-test-hook=add-choices]')
.find('.choices__list--multiple')
.last()
.should($el => {
expect($el).to.contain(newChoice);
});
});
});
});
});
});
21 changes: 21 additions & 0 deletions cypress/e2e/select-one.spec.ts
Original file line number Diff line number Diff line change
Expand Up @@ -1145,5 +1145,26 @@ describe('Choices - select one', () => {
.should('have.length', 3);
});
});

describe('adding user-created choices', () => {
beforeEach(() => {
cy.get('[data-test-hook=add-choices]').find('.choices').click();
});

it('allows the user to add choices', () => {
const newChoice = 'New Choice';

cy.get('[data-test-hook=add-choices]')
.find('.choices__input--cloned')
.type(newChoice)
.type('{enter}');

cy.get('[data-test-hook=add-choices]')
.find('.choices__list--single .choices__item')
.should(($el) => {
expect($el).to.contain(newChoice);
});
});
});
});
});
53 changes: 29 additions & 24 deletions public/assets/scripts/choices.js
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
/*! choices.js v10.2.0 | © 2022 Josh Johnson | https://github.com/jshjohnson/Choices#readme */
/*! choices.js v10.2.0 | © 2023 Josh Johnson | https://github.com/jshjohnson/Choices#readme */
(function webpackUniversalModuleDefinition(root, factory) {
if(typeof exports === 'object' && typeof module === 'object')
module.exports = factory();
Expand Down Expand Up @@ -807,9 +807,8 @@ var Choices = /** @class */function () {
} else if (activeChoices.length >= 1) {
choiceListFragment = this._createChoicesFragment(activeChoices, choiceListFragment);
}
// If we have choices to show
var activeItems = this._store.activeItems; // If we have choices to show
if (choiceListFragment.childNodes && choiceListFragment.childNodes.length > 0) {
var activeItems = this._store.activeItems;
var canAddItem = this._canAddItem(activeItems, this.input.value);
// ...and we can select them
if (canAddItem.response) {
Expand All @@ -822,13 +821,15 @@ var Choices = /** @class */function () {
}
} else {
// Otherwise show a notice
var canAddChoice = this._canAddChoice(activeItems, this.input.value);
var dropdownItem = void 0;
var notice = void 0;
if (this._isSearching) {
notice = typeof this.config.noResultsText === 'function' ? this.config.noResultsText() : this.config.noResultsText;
if (canAddChoice.response) {
dropdownItem = this._getTemplate('notice', canAddChoice.notice);
} else if (this._isSearching) {
var notice = typeof this.config.noResultsText === 'function' ? this.config.noResultsText() : this.config.noResultsText;
dropdownItem = this._getTemplate('notice', notice, 'no-results');
} else {
notice = typeof this.config.noChoicesText === 'function' ? this.config.noChoicesText() : this.config.noChoicesText;
var notice = typeof this.config.noChoicesText === 'function' ? this.config.noChoicesText() : this.config.noChoicesText;
dropdownItem = this._getTemplate('notice', notice, 'no-choices');
}
this.choiceList.append(dropdownItem);
Expand Down Expand Up @@ -1151,6 +1152,11 @@ var Choices = /** @class */function () {
this._store.dispatch((0, choices_1.activateChoices)(true));
}
};
Choices.prototype._canAddChoice = function (activeItems, value) {
var canAddItem = this._canAddItem(activeItems, value);
canAddItem.response = this.config.addChoices && canAddItem.response;
return canAddItem;
};
Choices.prototype._canAddItem = function (activeItems, value) {
var canAddItem = true;
var notice = typeof this.config.addItemText === 'function' ? this.config.addItemText(value) : this.config.addItemText;
Expand Down Expand Up @@ -1354,16 +1360,19 @@ var Choices = /** @class */function () {
var target = event.target;
var enterKey = constants_1.KEY_CODES.ENTER_KEY;
var targetWasButton = target && target.hasAttribute('data-button');
if (this._isTextElement && target && target.value) {
var addedItem = false;
if (target && target.value) {
var value = this.input.value;
var canAddItem = this._canAddItem(activeItems, value);
if (canAddItem.response) {
var canAddChoice = this._canAddChoice(activeItems, value);
if (this._isTextElement && canAddItem.response || !this._isTextElement && canAddChoice.response) {
this.hideDropdown(true);
this._addItem({
value: value
});
this._triggerChange(value);
this.clearInput();
addedItem = true;
}
}
if (targetWasButton) {
Expand All @@ -1373,12 +1382,16 @@ var Choices = /** @class */function () {
if (hasActiveDropdown) {
var highlightedChoice = this.dropdown.getChild(".".concat(this.config.classNames.highlightedState));
if (highlightedChoice) {
// add enter keyCode value
if (activeItems[0]) {
activeItems[0].keyCode = enterKey; // eslint-disable-line no-param-reassign
}
if (addedItem) {
this.unhighlightAll();
} else {
if (activeItems[0]) {
// add enter keyCode value
activeItems[0].keyCode = enterKey; // eslint-disable-line no-param-reassign
}

this._handleChoiceAction(activeItems, highlightedChoice);
this._handleChoiceAction(activeItems, highlightedChoice);
}
}
event.preventDefault();
} else if (this._isSelectOneElement) {
Expand Down Expand Up @@ -2874,6 +2887,7 @@ exports.DEFAULT_CONFIG = {
silent: false,
renderChoiceLimit: -1,
maxItemCount: -1,
addChoices: false,
addItems: true,
addItemFilter: null,
removeItems: true,
Expand Down Expand Up @@ -4168,7 +4182,7 @@ function getMergeFunction(key, options) {
function getEnumerableOwnPropertySymbols(target) {
return Object.getOwnPropertySymbols
? Object.getOwnPropertySymbols(target).filter(function(symbol) {
return target.propertyIsEnumerable(symbol)
return Object.propertyIsEnumerable.call(target, symbol)
})
: []
}
Expand Down Expand Up @@ -6816,15 +6830,6 @@ function applyMiddleware() {
};
}

/*
* This is a dummy function to check if the function name has been altered by minification.
* If the function has been minified and NODE_ENV !== 'production', warn the user.
*/

function isCrushed() {}

if (false) {}




Expand Down
2 changes: 0 additions & 2 deletions public/assets/scripts/choices.min.js

This file was deleted.

2 changes: 1 addition & 1 deletion public/assets/scripts/choices.min.js.LICENSE.txt
Original file line number Diff line number Diff line change
@@ -1 +1 @@
/*! choices.js v10.2.0 | © 2022 Josh Johnson | https://github.com/jshjohnson/Choices#readme */
/*! choices.js v10.2.0 | © 2023 Josh Johnson | https://github.com/jshjohnson/Choices#readme */
11 changes: 11 additions & 0 deletions public/test/select-multiple/index.html
Original file line number Diff line number Diff line change
Expand Up @@ -397,6 +397,15 @@ <h2>Select multiple inputs</h2>
multiple
></select>
</div>

<div data-test-hook="add-choices">
<label for="choices-add-choices">Add choices</label>
<select class="form-control" name="choices-add-choices" id="choices-add-choices" multiple>
<option value="Choice 1">Choice 1</option>
<option value="Choice 2">Choice 2</option>
<option value="Choice 3">Choice 3</option>
</select>
</div>
</div>
</div>
<script>
Expand Down Expand Up @@ -622,6 +631,8 @@ <h2>Select multiple inputs</h2>
},
],
});

new Choices('#choices-add-choices', { addChoices: true });
});
</script>
</body>
Expand Down
12 changes: 12 additions & 0 deletions public/test/select-one/index.html
Original file line number Diff line number Diff line change
Expand Up @@ -417,6 +417,16 @@ <h2>Select one inputs</h2>
<button class="destroy">Destroy</button>
<button class="init">Init</button>
</div>

<div data-test-hook="add-choices">
<label for="choices-add-choices">Add choices</label>
<select class="form-control" name="choices-add-choices" id="choices-add-choices">
<option value="Choice 1">Choice 1</option>
<option value="Choice 2">Choice 2</option>
<option value="Choice 3">Choice 3</option>
</select>
</div>

</div>
</div>
<script>
Expand Down Expand Up @@ -676,6 +686,8 @@ <h2>Select one inputs</h2>
document.querySelector('button.init').addEventListener('click', () => {
newDestroyInitChoices.init();
});

new Choices('#choices-add-choices', { addChoices: true });
});
</script>
</body>
Expand Down
1 change: 1 addition & 0 deletions public/types/src/scripts/choices.d.ts
Original file line number Diff line number Diff line change
Expand Up @@ -150,6 +150,7 @@ declare class Choices implements Choices {
_stopLoading(): void;
_handleLoadingState(setLoading?: boolean): void;
_handleSearch(value: string): void;
_canAddChoice(activeItems: Item[], value: string): Notice;
_canAddItem(activeItems: Item[], value: string): Notice;
_searchChoices(value: string): number;
_addEventListeners(): void;
Expand Down
Loading