From 87d220acae805524663ec045e986feee65bc9dbc Mon Sep 17 00:00:00 2001 From: "Joseph J. Schmitt" Date: Tue, 20 Jun 2017 13:13:32 -0400 Subject: [PATCH] Add reference to omnibox into locals of all &-callback functions (#64) Makes it consistent. Some things had access and others didn't, it's just easier if everything has this reference now. --- README.md | 69 ++++++++++---------- package.json | 2 +- src/angularComponent/ngcOmniboxController.js | 26 ++++---- 3 files changed, 50 insertions(+), 47 deletions(-) diff --git a/README.md b/README.md index 719579d..1623c6c 100644 --- a/README.md +++ b/README.md @@ -152,14 +152,14 @@ are made to your data. The following bindings are available on the main `` component: -- `source({query, suggestions}) {Promise}` _(Required)_: An expression that populates the list of -suggestions by returning a `Promise` that resolves to an array of suggestions. The individual -suggestions can be of any type, but the list of suggestions must be an array. If you wish to provide -nested suggestions (such as category headers, or a tree structure) then you must provide a key -called `children` on your suggestion which will then be looped through to find more children, or the -end of the list. In its locals it has access to a string called `query` with the current query in -the input field, and an array called `suggestions`, which is the current list of suggestions being -displayed. +- `source({query, suggestions, omnibox}) {Promise}` _(Required)_: An expression that populates the +list of suggestions by returning a `Promise` that resolves to an array of suggestions. The +individual suggestions can be of any type, but the list of suggestions must be an array. If you wish +to provide nested suggestions (such as category headers, or a tree structure) then you must provide +a key called `children` on your suggestion which will then be looped through to find more children, +or the end of the list. In its locals it has access to a string called `query` with the current +query in the input field, and an array called `suggestions`, which is the current list of +suggestions being displayed. To display a hint to the user in addition to suggestions, resolve the promise with an object that has keys for `hint` and `suggestions`: `{hint: 'My hint', suggestions: [...]}`. A hint is displayed to the right of the text that has been input by the user. Pressing RIGHT on the keyboard replaces @@ -184,15 +184,15 @@ you need to support a "free-text" suggestion with multiple on, be sure to add it function as a suggestion. - `hideOnBlur {Boolean}`: Whether the list of suggestions should automatically hide when the component itself loses focus. Hitting ESC will always close the list of suggestions. -- `isSelectable({suggestion}) {Boolean}`: An expression that should evaluate to a Boolean that -determines if a suggestion is able to be interacted with. This expression will be executed whenever -a suggestion is attempted to be highlighted either by the keyboard or mouse. In its locals it has -access to an object called `suggestion` which is the current suggestion that is being interacted -with. A non-selectable suggestion cannot be clicked on, hovered over, or interacted with via the -keyboard. -- `canShowSuggestions({query}) {Boolean}`: An expression that should evaluate to a Boolean that -determines whether or not the list of suggestions can be displayed. In its locals it has access to a -string called `query` which is the current query being searched on. +- `isSelectable({suggestion, omnibox}) {Boolean}`: An expression that should evaluate to a Boolean +that determines if a suggestion is able to be interacted with. This expression will be executed +whenever a suggestion is attempted to be highlighted either by the keyboard or mouse. In its locals +it has access to an object called `suggestion` which is the current suggestion that is being +interacted with. A non-selectable suggestion cannot be clicked on, hovered over, or interacted with +via the keyboard. +- `canShowSuggestions({query, omnibox}) {Boolean}`: An expression that should evaluate to a Boolean +that determines whether or not the list of suggestions can be displayed. In its locals it has access +to a string called `query` which is the current query being searched on. - `requireMatch {Boolean}`: An expression that should evaluate to a Boolean that determines if a matched suggestion is required for the field (defaults to `false`). This has a few effects on the behavior of the omnibox: @@ -218,30 +218,31 @@ behavior of the omnibox: The following &-callback functions are available for binding on the `ngc-omnibox` component in response to events: -- `onFocus({event})`: An expression that's called when the component gets focus. This includes not -just the input field, but the component in general. This is necessary since selecting the choices -might blur the input field, but not the component itself. If you need to know when just the input -field receives focus, you can use the `target` property of the event object to figure it out. -- `onBlur({event})`: An expression that's called when the component loses focus. This also includes -the entire component, not just the field. This blur event also has logic to reduce the noise that -sometimes happens where it'll lose focus then immediately regain it, so the blur is called only -after a timeout to make sure it doesn't re-receive focus first. -- `onChosen({choice, $event})`: An expression that's called when a suggestion is chosen. In its -locals it has access to `choice`, which is the item that was chosen, and an `$event` object. The +- `onFocus({event, omnibox})`: An expression that's called when the component gets focus. This +includes not just the input field, but the component in general. This is necessary since selecting +the choices might blur the input field, but not the component itself. If you need to know when just +the input field receives focus, you can use the `target` property of the event object to figure it +out. +- `onBlur({event, omnibox})`: An expression that's called when the component loses focus. This also +includes the entire component, not just the field. This blur event also has logic to reduce the +noise that sometimes happens where it'll lose focus then immediately regain it, so the blur is +called only after a timeout to make sure it doesn't re-receive focus first. +- `onChosen({choice, $event, omnibox})`: An expression that's called when a suggestion is chosen. In +its locals it has access to `choice`, which is the item that was chosen, and an `$event` object. The `$event` object has the following properties: `isDefaultPrevented`, `preventDefault()`, and `performDefault()`. If `isDefaultPrevented` is set to true by calling `preventDefault()` from this callback function, then the choice is not automatically added to the ngModel. If you then do want the choice to be added, you can call `performDefault()` to do so. -- `onUnchosen({choice, $event})`: An expression that's called when a suggestion is unchosen (removed as a -choice). In its locals it has access to `choice`, which is the item that was unchosen, and an -`$event` object. The `$event` object has the following properties: `isDefaultPrevented`, +- `onUnchosen({choice, $event, omnibox})`: An expression that's called when a suggestion is unchosen +(removed as a choice). In its locals it has access to `choice`, which is the item that was unchosen, +and an `$event` object. The `$event` object has the following properties: `isDefaultPrevented`, `preventDefault()`, and `performDefault()`. If `isDefaultPrevented` is set to true by calling `preventDefault()` from this callback function, then the choice is not automatically removed from the ngModel. If you then do want the choice to be removed, you can call `performDefault()` to do so. -- `onShowSuggestions({suggestions})`: An expression that's called when the suggestions UI is shown. -In its locals it has access to `suggestions`. -- `onHideSuggestions({suggestions})`: An expression that's called when the suggestions UI is -hidden. In its locals it has access to `suggestions`. +- `onShowSuggestions({suggestions, omnibox})`: An expression that's called when the suggestions UI +is shown. In its locals it has access to `suggestions`. +- `onHideSuggestions({suggestions, omnibox})`: An expression that's called when the suggestions UI +is hidden. In its locals it has access to `suggestions`. ## Omnibox Controller diff --git a/package.json b/package.json index 909cb11..51582b7 100644 --- a/package.json +++ b/package.json @@ -1,6 +1,6 @@ { "name": "ngc-omnibox", - "version": "0.4.1", + "version": "0.4.2", "description": "A modern, flexible, Angular 1.x autocomplete library with limited assumptions.", "main": "dist/ngc-omnibox.js", "scripts": { diff --git a/src/angularComponent/ngcOmniboxController.js b/src/angularComponent/ngcOmniboxController.js index 0798054..9e5d5a5 100644 --- a/src/angularComponent/ngcOmniboxController.js +++ b/src/angularComponent/ngcOmniboxController.js @@ -46,7 +46,7 @@ export default class NgcOmniboxController { let blurTimeout; this.element.addEventListener('focus', (event) => { clearTimeout(blurTimeout); - this.onFocus({event}); + this.onFocus({event, omnibox: this}); }, true); this.element.addEventListener('blur', (event) => { blurTimeout = setTimeout(() => { @@ -56,7 +56,7 @@ export default class NgcOmniboxController { $scope.$apply(); } - this.onBlur({event}); + this.onBlur({event, omnibox: this}); }, SUGGESTIONS_BLUR_THRESHOLD); }, true); @@ -190,7 +190,7 @@ export default class NgcOmniboxController { const [uiItemMatch] = this._suggestionsUiList.filter((uiItem) => uiItem.data === item); - if (uiItemMatch && this.isSelectable({suggestion: uiItemMatch.data}) !== false) { + if (uiItemMatch && this.isSelectable({suggestion: uiItemMatch.data, omnibox: this}) !== false) { this.highlightedIndex = uiItemMatch.index; } } @@ -224,7 +224,7 @@ export default class NgcOmniboxController { } const suggestion = this._suggestionsUiList[newIndex]; - if (suggestion && this.isSelectable({suggestion: suggestion.data}) === false) { + if (suggestion && this.isSelectable({suggestion: suggestion.data, omnibox: this}) === false) { if (typeof startHighlightIndex !== 'number') { startHighlightIndex = newIndex; } @@ -266,7 +266,7 @@ export default class NgcOmniboxController { } const suggestion = this._suggestionsUiList[newIndex]; - if (suggestion && this.isSelectable({suggestion: suggestion.data}) === false) { + if (suggestion && this.isSelectable({suggestion: suggestion.data, omnibox: this}) === false) { if (typeof startHighlightIndex !== 'number') { startHighlightIndex = newIndex; } @@ -393,7 +393,7 @@ export default class NgcOmniboxController { * @param {Boolean} shouldFocusField -- Whether to focus the input field after choosing */ choose(item, shouldFocusField = true) { - if (item && this.isSelectable({suggestion: item}) !== false) { + if (item && this.isSelectable({suggestion: item, omnibox: this}) !== false) { const $event = { isDefaultPrevented: false, @@ -410,7 +410,7 @@ export default class NgcOmniboxController { } }; - this.onChosen({choice: item, $event}); + this.onChosen({choice: item, $event, omnibox: this}); !$event.isDefaultPrevented && $event.performDefault(); this.query = ''; @@ -442,7 +442,7 @@ export default class NgcOmniboxController { } }; - this.onUnchosen({choice: item, $event}); + this.onUnchosen({choice: item, $event, omnibox: this}); !$event.isDefaultPrevented && $event.performDefault(); } } @@ -457,14 +457,16 @@ export default class NgcOmniboxController { this._shouldShowSuggestions = !this.hideSuggestions && (this.shouldShowLoadingElement || !!this.suggestions) && - this.canShowSuggestions({query: this.query}) !== false; + this.canShowSuggestions({query: this.query, omnibox: this}) !== false; if (this._shouldShowSuggestions && this._shouldShowSuggestions !== shouldShowSuggestionsCurrently) { - this.onShowSuggestions && this.onShowSuggestions({suggestions: this.suggestions}); + this.onShowSuggestions && this.onShowSuggestions({suggestions: this.suggestions, + omnibox: this}); } else if (!this._shouldShowSuggestions && this._shouldShowSuggestions !== shouldShowSuggestionsCurrently) { - this.onHideSuggestions && this.onHideSuggestions({suggestions: this.suggestions}); + this.onHideSuggestions && this.onHideSuggestions({suggestions: this.suggestions, + omnibox: this}); } return this._shouldShowSuggestions; @@ -483,7 +485,7 @@ export default class NgcOmniboxController { this._showLoading(); this.hideSuggestions = false; - const promise = this.source({query: this.query, suggestions: this.suggestions}); + const promise = this.source({query: this.query, suggestions: this.suggestions, omnibox: this}); this._sourceFunctionPromise = promise; return promise.then((suggestions) => {