15

I want to modify the autocomplete component for multiple selection. What I want is that the suggestion panel should be opened for multiple selection via checkbox, and close it if user clicks outside of suggestion panel. As per the docs we can handle it via panelClosingActions but I cant find any way how to use it.

M able to keep Panel open via MdAutocompleteTrigger event and openPanel method but what happens is if 2nd index is selected and m selecting 4th index then 2nd index checkbox unticks and ticks again.

<md-autocomplete #auto="mdAutocomplete" id=autoComplete>
  <md-option *ngFor="let state of filteredStates | async" 
[value]="state.name" (click)="handleAutocomplete()">
<md-checkbox [checked]="state.selected" [(ngModel)]="state.selected">
    <span>{{ state.name }}</span> |
    <small>Population: {{state.population}}</small>
</md-checkbox>
  </md-option>
</md-autocomplete>

@ViewChild('autocomplete', {read: MdAutoCompleteTrigger})
autoComplete: MdAutocompleteTrigger

handleAutocomplete(){
this.autoComplete.openPanel();
}

Any help is really appreciated

Rohan Sampat
  • 930
  • 1
  • 13
  • 30
  • See my answer here: https://stackoverflow.com/questions/50491195/open-matautocomplete-with-open-openpanel-method/57117207#57117207 – Jai Jul 19 '19 at 17:50

4 Answers4

16

I'm facing the same issue.

Only solution I found is to immediately reopen the options panel when an option is selected using mat-autocomplete optionSelected method.

HTML

<mat-autocomplete 
#auto="matAutocomplete" 
[displayWith]="displayFn" 
(optionSelected)="openPanel()">
    <mat-option *ngFor="let tag of filteredSources" [value]="tag.id">
        <span>{{ tag.text }}</span>
    </mat-option>
</mat-autocomplete>

TS

@ViewChild(MatAutocompleteTrigger) autoTrigger: MatAutocompleteTrigger;
openPanel(): void {
    const self = this;
    setTimeout(function () {
        self.autoTrigger.openPanel();
    }, 1);
}

This is not an elegant solution as the panel still closes and there is a blinking effect, but I couldn't find a better solution as MatAutocompleteTrigger panelClosingActions is readonly.

Roketz
  • 169
  • 4
6

Preventing event propagation for the autocomplete options

In the template:

<mat-autocomplete>
    <mat-option *ngFor="let option of options">
        <mat-checkbox (click)="checkOption($event)">
            {{ option.name }}
        </mat-checkbox>
    </mat-option>
</mat-autocomplete>

And in the component:

checkOption(event) {
    // this prevents the click event to get to the autocomplete component
    event.stopPropagation();
}
che
  • 633
  • 6
  • 4
  • This only works when you click on the checkbox, but not when you select an option using the keyboard (arrow down + enter) – Typhon Feb 16 '23 at 12:18
4

After digging a lot I found out that material does not expose its methods to do so. So, in short, it's not possible yet

Rohan Sampat
  • 930
  • 1
  • 13
  • 30
  • 1
    Ey, hitting the same problem now, have you figured out any update on this? very weird they haven't think in this common scenario right? – Alejandro Lora Apr 16 '18 at 08:12
0

I've been facing the same issue with multiple autocomplete. Here is how I fixed it.

HTML: (the one I want to let the panel opened when I select an option)

<mat-autocomplete  #emitterAuto="matAutocomplete" 
                   [displayWith]="autoCompleteDisplayLegalEntity"
                   (optionSelected)="onOptionSelected(0)">
       <mat-option *ngFor="let emitter of aFilteredEmitters$ | async"
                   [value]="emitter"> 
              <mat-icon *ngIf="emitter.is_organization">business</mat-icon>
              <mat-icon *ngIf="!emitter.is_organization">person</mat-icon>
              {{ displayLegalEntity(emitter) }}
      </mat-option>
      <mat-option value="create-legal-entity" class="add-organization">
              <mat-icon>add</mat-icon>Ajouter…
      </mat-option>
</mat-autocomplete>

TS:

import { QueryList, ViewChildren } from '@angular/core';
@ViewChildren(MatAutocompleteTrigger) autoTrigger: QueryList<MatAutocompleteTrigger>;
public onOptionSelected(value: number) {
    const self = this;
    setTimeout(function () {
        self.autoTrigger['_results'][value].openPanel();
    }, 1);
}

Value is the N mat-autocomplete where you want to apply this function.

Ex: If you want to open the panel of the second mat-autocomplete, value = 1.

Hope it can help someone, and sorry for my English I'm French.