coveo-search-ui
Version:
Coveo JavaScript Search Framework
216 lines (183 loc) • 7.56 kB
text/typescript
/// <reference path="Facet.ts" />
import { Facet } from './Facet';
import { FacetValue } from './FacetValue';
import { IPopulateOmniboxObject } from '../Omnibox/OmniboxInterface';
import { ValueElementRenderer } from './ValueElementRenderer';
import { Utils } from '../../utils/Utils';
import { IAnalyticsActionCause, analyticsActionCauseList, IAnalyticsFacetMeta } from '../Analytics/AnalyticsActionListMeta';
import { $$ } from '../../utils/Dom';
import { KeyboardUtils, KEYBOARD } from '../../utils/KeyboardUtils';
export interface IValueElementKlass {
new (facet: Facet, facetValue: FacetValue): ValueElement;
}
export interface IValueElementEventsBinding {
displayNextTime: boolean;
pinFacet: boolean;
omniboxObject?: IPopulateOmniboxObject;
}
export class ValueElement {
public renderer: ValueElementRenderer;
private isOmnibox: boolean;
constructor(
public facet: Facet,
public facetValue: FacetValue,
public onSelect?: (elem: ValueElement, cause: IAnalyticsActionCause) => void,
public onExclude?: (elem: ValueElement, cause: IAnalyticsActionCause) => void
) {}
public build(): ValueElement {
this.renderer = new ValueElementRenderer(this.facet, this.facetValue).build();
this.bindEvent({ displayNextTime: true, pinFacet: this.facet.options.preservePosition });
return this;
}
public bindEvent(eventBindings: IValueElementEventsBinding) {
if (!Utils.isNullOrUndefined(eventBindings.omniboxObject)) {
this.isOmnibox = true;
} else {
this.isOmnibox = false;
}
this.handleEventForCheckboxChange(eventBindings);
if (this.facetValue.excluded) {
this.handleEventForExcludedValueElement(eventBindings);
} else {
this.handleEventForValueElement(eventBindings);
}
}
public select() {
this.facetValue.selected = true;
this.facetValue.excluded = false;
this.renderer.setCssClassOnListValueElement();
}
public unselect() {
this.facetValue.selected = false;
this.facetValue.excluded = false;
this.renderer.setCssClassOnListValueElement();
}
public exclude() {
this.facetValue.selected = false;
this.facetValue.excluded = true;
this.renderer.setCssClassOnListValueElement();
}
public unexclude() {
this.facetValue.selected = false;
this.facetValue.excluded = false;
this.renderer.setCssClassOnListValueElement();
}
public toggleExcludeWithUA() {
let actionCause: IAnalyticsActionCause;
if (this.facetValue.excluded) {
actionCause = this.isOmnibox ? analyticsActionCauseList.omniboxFacetUnexclude : analyticsActionCauseList.facetUnexclude;
} else {
actionCause = this.isOmnibox ? analyticsActionCauseList.omniboxFacetExclude : analyticsActionCauseList.facetExclude;
}
this.facet.toggleExcludeValue(this.facetValue);
if (this.onExclude) {
this.facet.triggerNewQuery(() => this.onExclude(this, actionCause));
} else {
this.facet.triggerNewQuery(() =>
this.facet.usageAnalytics.logSearchEvent<IAnalyticsFacetMeta>(actionCause, this.getAnalyticsFacetMeta())
);
}
}
protected handleSelectValue(eventBindings: IValueElementEventsBinding) {
this.facet.keepDisplayedValuesNextTime = eventBindings.displayNextTime && !this.facet.options.useAnd;
var actionCause: IAnalyticsActionCause;
if (this.facetValue.excluded) {
actionCause = this.isOmnibox ? analyticsActionCauseList.omniboxFacetUnexclude : analyticsActionCauseList.facetUnexclude;
this.facet.unexcludeValue(this.facetValue);
} else {
if (this.facetValue.selected) {
actionCause = this.isOmnibox ? analyticsActionCauseList.omniboxFacetDeselect : analyticsActionCauseList.facetDeselect;
} else {
actionCause = this.isOmnibox ? analyticsActionCauseList.omniboxFacetSelect : analyticsActionCauseList.facetSelect;
}
this.facet.toggleSelectValue(this.facetValue);
}
if (this.onSelect) {
this.facet.triggerNewQuery(() => this.onSelect(this, actionCause));
} else {
this.facet.triggerNewQuery(() =>
this.facet.usageAnalytics.logSearchEvent<IAnalyticsFacetMeta>(actionCause, this.getAnalyticsFacetMeta())
);
}
}
protected handleExcludeClick(eventBindings: IValueElementEventsBinding) {
this.facet.keepDisplayedValuesNextTime = eventBindings.displayNextTime && !this.facet.options.useAnd;
this.toggleExcludeWithUA();
}
protected handleSelectEventForExcludedValueElement(eventBindings: IValueElementEventsBinding) {
const clickEvent = () => {
if (eventBindings.pinFacet) {
this.facet.pinFacetPosition();
}
if (eventBindings.omniboxObject) {
this.omniboxCloseEvent(eventBindings.omniboxObject);
}
this.handleSelectValue(eventBindings);
this.tryDismissSearchResults();
return false;
};
$$(this.renderer.label).on('click', e => {
e.stopPropagation();
clickEvent();
});
$$(this.renderer.stylishCheckbox).on('keydown', KeyboardUtils.keypressAction([KEYBOARD.SPACEBAR, KEYBOARD.ENTER], clickEvent));
}
protected handleExcludeEventForValueElement(eventBindings: IValueElementEventsBinding) {
const excludeAction = (event: Event) => {
if (eventBindings.omniboxObject) {
this.omniboxCloseEvent(eventBindings.omniboxObject);
}
this.handleExcludeClick(eventBindings);
this.tryDismissSearchResults();
event.stopPropagation();
event.preventDefault();
};
$$(this.renderer.excludeIcon).on('click', excludeAction);
$$(this.renderer.excludeIcon).on('keydown', KeyboardUtils.keypressAction([KEYBOARD.SPACEBAR, KEYBOARD.ENTER], excludeAction));
}
protected handleSelectEventForValueElement(eventBindings: IValueElementEventsBinding) {
const selectAction = (event: Event) => {
if (eventBindings.pinFacet) {
this.facet.pinFacetPosition();
}
this.tryDismissSearchResults();
$$(this.renderer.checkbox).trigger('change');
event.preventDefault();
};
$$(this.renderer.label).on('click', selectAction);
$$(this.renderer.stylishCheckbox).on('keydown', KeyboardUtils.keypressAction([KEYBOARD.SPACEBAR, KEYBOARD.ENTER], selectAction));
}
protected handleEventForExcludedValueElement(eventBindings: IValueElementEventsBinding) {
this.handleSelectEventForExcludedValueElement(eventBindings);
this.handleExcludeEventForValueElement(eventBindings);
}
protected handleEventForValueElement(eventBindings: IValueElementEventsBinding) {
this.handleSelectEventForValueElement(eventBindings);
this.handleExcludeEventForValueElement(eventBindings);
}
protected handleEventForCheckboxChange(eventBindings: IValueElementEventsBinding) {
$$(this.renderer.checkbox).on('change', () => {
if (eventBindings.omniboxObject) {
this.omniboxCloseEvent(eventBindings.omniboxObject);
}
this.handleSelectValue(eventBindings);
});
}
protected omniboxCloseEvent(eventArg: IPopulateOmniboxObject) {
eventArg.closeOmnibox();
eventArg.clear();
}
private tryDismissSearchResults() {
if (this.facet && this.facet.facetSearch && this.facet.facetSearch.dismissSearchResults) {
this.facet.facetSearch.dismissSearchResults();
}
}
private getAnalyticsFacetMeta(): IAnalyticsFacetMeta {
return {
facetId: this.facet.options.id,
facetField: this.facet.options.field.toString(),
facetValue: this.facetValue.value,
facetTitle: this.facet.options.title
};
}
}