UNPKG

coveo-search-ui-extensions

Version:

Small generic components to extend the functionality of Coveo's Search UI framework.

96 lines 4.54 kB
import { ActionButton } from './ActionButton'; /** * An action button able to handle multiple states and their transitions. */ export class StatefulActionButton { constructor(element, options, bindings) { var _a; this.element = element; this.options = options; this.bindings = bindings; const optionsValidity = this.checkOptionsValidity(); if (!optionsValidity.areValid) { console.warn(`Cannot render the stateful action button because options are invalid.\n\t${optionsValidity.errorMessage}`); return; } this.currentState = this.options.initialState; (_a = this.currentState.onStateEntry) === null || _a === void 0 ? void 0 : _a.apply(this); this.innerActionButton = new ActionButton(element, Object.assign(Object.assign({}, this.options.initialState), { click: this.handleClick.bind(this) }), bindings); } /** * Switch the state of the instance if the state and the transition between the current and new state are allowed. * @param state a state to try to switch to */ switchTo(state) { if (this.options.states.indexOf(state) === -1) { console.warn(`State '${state.name}' does not exist on this StatefulActionButton\nEnsure to use the object references used at the instantiation.`); return; } if (!this.isTransitionAllowed(state)) { console.warn(`Transition from State '${this.currentState.name}' to State '${state.name}' is not allowed on this StatefulActionButton.\nEnsure to use the object references used at the instantiation.`); return; } const [oldStateExit, newStateEntry] = [this.currentState.onStateExit, state.onStateEntry]; this.innerActionButton.updateIcon(state.icon); this.innerActionButton.updateTooltip(state.tooltip); this.currentState = state; oldStateExit === null || oldStateExit === void 0 ? void 0 : oldStateExit.call(this); newStateEntry === null || newStateEntry === void 0 ? void 0 : newStateEntry.call(this); } /** * Return the current state of the instance. */ getCurrentState() { return this.currentState; } /** * Check if the options given to the constructor are valid. * If not, it will also display the appropriate warning. */ checkOptionsValidity() { var _a; if (!((_a = this.options.states) === null || _a === void 0 ? void 0 : _a.length)) { return { areValid: false, errorMessage: 'States is not defined or empty.' }; } if (!this.options.initialState) { return { areValid: false, errorMessage: 'InitialState is not defined.' }; } if (this.options.states.indexOf(this.options.initialState) < 0) { return { areValid: false, errorMessage: 'InitialState is not in the list of state.' }; } return !this.options.allowedTransitions ? { areValid: true } : this.areTransitionsValid(); } areTransitionsValid() { for (let index = 0; index < this.options.allowedTransitions.length; index++) { const transition = this.options.allowedTransitions[index]; if (this.options.states.indexOf(transition.from) === -1) { return { areValid: false, errorMessage: this.generateInvalidTransitionMessage(index, true) }; } if (this.options.states.indexOf(transition.to) === -1) { return { areValid: false, errorMessage: this.generateInvalidTransitionMessage(index, false) }; } } return { areValid: true }; } generateInvalidTransitionMessage(transitionNumber, isOrigin) { return `${isOrigin ? 'Origin' : 'Destination'} of Transition #${transitionNumber} is not in the list of states. Ensure to use the same object reference as in the options.states.`; } /** * Check if a transition from the current state to @param state is allowed. * @param state the destination of the transition */ isTransitionAllowed(state) { if (!this.options.allowedTransitions) { return true; } return this.options.allowedTransitions.some((transition) => transition.from === this.currentState && transition.to === state); } /** * Handle user click. */ handleClick() { this.currentState.click(); } } StatefulActionButton.ID = 'StatefulActionButton'; //# sourceMappingURL=StatefulActionButton.js.map