Skip to content
Merged
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
Original file line number Diff line number Diff line change
Expand Up @@ -1084,6 +1084,23 @@ describe('IgxSimpleCombo', () => {
expect(combo.selection.length).toEqual(1);
});

it('should clear input on blur when dropdown is collapsed with no match', () => {
input.triggerEventHandler('focus', {});
fixture.detectChanges();

UIInteractions.simulateTyping('new', input);

const toggleButton = fixture.debugElement.query(By.css('.' + CSS_CLASS_TOGGLEBUTTON));
toggleButton.triggerEventHandler('click', UIInteractions.getMouseEvent('click'));
fixture.detectChanges();

UIInteractions.triggerEventHandlerKeyDown('Tab', input);
fixture.detectChanges();

expect(combo.value).toEqual('');
expect(combo.selection.length).toEqual(0);
});

it('should empty any invalid item values', () => {
combo.valueKey = 'key';
combo.displayKey = 'value';
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -92,6 +92,8 @@ export class IgxSimpleComboComponent extends IgxComboBaseDirective implements Co
// stores the last filtered value - move to common?
private _internalFilter = '';

private _collapsing = false;

/** @hidden @internal */
public get filteredData(): any[] | null {
return this._filteredData;
Expand Down Expand Up @@ -201,7 +203,11 @@ export class IgxSimpleComboComponent extends IgxComboBaseDirective implements Co
}
}
});
this.dropdown.opening.pipe(takeUntil(this.destroy$)).subscribe(() => {
this.dropdown.opening.pipe(takeUntil(this.destroy$)).subscribe((args) => {
if (args.cancel) {
return;
}
this._collapsing = false;
const filtered = this.filteredData.find(this.findAllMatches);
if (filtered === undefined || filtered === null) {
this.filterValue = this.searchValue = this.comboInput.value;
Expand All @@ -216,12 +222,16 @@ export class IgxSimpleComboComponent extends IgxComboBaseDirective implements Co
this._internalFilter = this.comboInput.value;
});
this.dropdown.closing.pipe(takeUntil(this.destroy$)).subscribe((args) => {
if (args.cancel) {
return;
}
if (this.getEditElement() && !args.event) {
this.comboInput.focus();
this._collapsing = true;
} else {
this.clearOnBlur();
this._onTouchedCallback();
}
this.comboInput.focus();
});
this.dropdown.closed.pipe(takeUntil(this.destroy$)).subscribe(() => {
this.filterValue = this._internalFilter = this.comboInput.value;
Expand All @@ -246,7 +256,7 @@ export class IgxSimpleComboComponent extends IgxComboBaseDirective implements Co
if (this.collapsed && this.comboInput.focused) {
this.open();
}
if (!this.comboInput.value.trim() && this.selectionService.size(this.id) > 0) {
if (!this.comboInput.value.trim() && this.selection.length) {
// handle clearing of input by space
this.clearSelection();
this._onChangeCallback(null);
Expand Down Expand Up @@ -282,6 +292,7 @@ export class IgxSimpleComboComponent extends IgxComboBaseDirective implements Co
}
if (!this.collapsed && event.key === this.platformUtil.KEYMAP.TAB) {
this.clearOnBlur();
this.close();
}
this.composing = false;
super.handleKeyDown(event);
Expand Down Expand Up @@ -316,6 +327,16 @@ export class IgxSimpleComboComponent extends IgxComboBaseDirective implements Co
this.comboInput.focus();
}

/** @hidden @internal */
public onBlur(): void {
// when clicking the toggle button to close the combo and immediately clicking outside of it
// the collapsed state is not modified as the dropdown is still not closed
if (this.collapsed || this._collapsing) {
this.clearOnBlur();
}
super.onBlur();
}

/** @hidden @internal */
public onFocus(): void {
this._internalFilter = this.comboInput.value || '';
Expand Down Expand Up @@ -452,29 +473,22 @@ export class IgxSimpleComboComponent extends IgxComboBaseDirective implements Co

private clearOnBlur(): void {
const filtered = this.filteredData.find(this.findMatch);
if (filtered === undefined || filtered === null || this.getElementKey(filtered) !== this.selectedItem) {
this.clearAndClose();
// selecting null in primitive data returns undefined as the search text is '', but the item is null
if (filtered === undefined && this.selectedItem !== null || !this.selection.length) {
this.clear();
return;
}
}

private getElementKey(element: any): any {
const elementVal = this.valueKey ? element[this.valueKey] : element;
return elementVal;
}

private getElementVal(element: any): string {
const elementVal = this.displayKey ? element[this.displayKey] : element;
return String(elementVal);
}

private clearAndClose(): void {
private clear(): void {
this.clearSelection(true);
this._internalFilter = '';
this.searchValue = '';
if (!this.collapsed) {
this.close();
}
}

private isValid(value: any): boolean {
Expand Down