Me gustaría obtener datos del servidor usando Autocompletar componente con angular2/material2. ( https://material.angular.io/components/component/autocompletar )
t
emailCtrl: FormControl; filteredEmails: any; constructor( private companieService: CompanieService, ) { this.emailCtrl = new FormControl(); this.filteredEmails = this.emailCtrl.valueChanges .startWith(null) .map(email => this.filterEmails(email)); } filterEmails(email: string) { this.userService.getUsersByEmail(email) .subscribe( res => { return res }, error => { console.log(error); } ) }html
<md-input-container> <input mdInput placeholder="Email" [mdAutocomplete]="auto" [formControl]="emailCtrl" [(ngModel)]="fetchedUser.profile.email"> </md-input-container> <md-autocomplete #auto="mdAutocomplete"> <md-option *ngFor="let email of filteredEmails | async" [value]="email"> {{email}} </md-option> </md-autocomplete> Servicio: userService.getUsersByEmail(email) está extrayendo este tipo de datos:
['email1@email.com','email2@email.com','email3@email.com']No tengo errores pero tampoco resultados en el autocompletar. Veo en el depurador de Chrome (red de pestañas) Los datos se extraen correctamente para cada cambio en la entrada
Te daré mi ejemplo que suelo usar,
this.SearchForm.controls['city_id'].valueChanges .debounceTime(CONFIG.DEBOUNCE_TIME) .subscribe(name => { this.domain = [['name', 'ilike', name]]; this.DataService.getAutoComplete('res.city', this.domain) .subscribe(res => { return this._filteredCity = res['result']['records'] }) })HTML
<div class="mb-1 ml-1 mt-1" fxFlex="30"> <md-input-container style="width: 100%"> <input mdInput placeholder="Kota" (blur)="checkAutoComplete('city_id')" [mdAutocomplete]="city_id" [required]="true" [formControl]="SearchForm.controls['city_id']"> </md-input-container> <md-autocomplete #city_id="mdAutocomplete" [displayWith]="displayFn"> <md-option *ngFor="let city of _filteredCity" [value]="city"> <span>{{ city.name }}</span> </md-option> </md-autocomplete> <div *ngIf="SearchForm.controls['city_id'].hasError('required') && SearchForm.controls['city_id'].touched" class="mat-text-warn text-sm">Kolom ini wajib diisi.</div> </div>así
Así es como lo hice.
.html
<input formControlName="search" [mdAutocomplete]="auto" type="text" class="form-control"> <md-autocomplete #auto="mdAutocomplete"> <md-option *ngFor="let data of filteredData | async" [value]="data.text"> {{ data.text }} </md-option> </md-autocomplete>.ts
filteredData: Observable<any[]>; // async pipe needs to be an Observable myContent: any[] = []; this.filteredData = this.myformGroup.get('search').valueChanges .debounceTime(400) .switchMap(value => { // get data from the server. my response is an array [{id:1, text:'hello world'}] as an Observable return this.myApiService.getSearch(value); }).map(res => this.myContent = res);Hazme saber si esto funciona para ti.
mi.componente.html
<form [formGroup]="myForm"> <mat-form-field> <input matInput formControlName="email" [matAutocomplete]="autoEmailGroup" name="email" type="email" placeholder="Email" aria-label="Email" /> <mat-autocomplete autoActiveFirstOption #autoEmailGroup="matAutocomplete"> <mat-option *ngFor="let email of emailOptions | async" [value]="email">{{ email }}</mat-option> </mat-autocomplete> </mat-form-field> </form>mi.componente.ts
import { Component, OnInit } from '@angular/core'; import { FormGroup, FormBuilder, FormControl } from '@angular/forms'; import { Observable } from 'rxjs'; import { startWith, tap, switchMap, map, filter } from 'rxjs/operators'; import { empty } from 'rxjs/observable/empty'; @Component({ selector: 'my-component', templateUrl: './my.component.html', styleUrls: ['./my.component.scss'] }) export class MyComponent implements OnInit { myForm: FormGroup; emailOptions: Observable<string[]>; constructor( private fb: FormBuilder, private http: HttpClient, ) { } createForm() { this.myForm = this.fb.group({ email: new FormControl(), }); const _fetchEmailsFromServer = (): Observable<string[]> => { // TODO you need to ultilize your service here return empty(); }; this.emailOptions = this.myForm.get('email')!.valueChanges .pipe( startWith(''), switchMap((input: string) => { return _fetchEmailsFromServer().pipe( // handle your HTTP response here map((response: any): string[] => { return <string[]> response!.data!.emails; }), tap((emails: string[]) => { // LOGGING console.log('Received emails:', emails); }), // you can filter emails fetched from your server here if you want ); }), ).pipe( // default value to be displayed before HTTP task is completed startWith([]), ); } }Referencia: