mat-autocomplete displayWith async (how to return from "subscribe")

2,986 views
Skip to first unread message

Tolga Koseoglu

unread,
Jan 5, 2019, 1:54:40 AM1/5/19
to Angular and AngularJS discussion
Hi,

Background:
I've created a custom control that ultimately sets an ID. The main object is of type "Project" and has a property called "ContactID". The custom control I've created allows to set that ContactID. 
The custom control uses angular material's mat-autocomplete. The problem I am having is that I don't want to show the selected Contact's ID (ContactID) in the UI. I rather want to show the Contact's Name. 

My Problem:
I am trying to use the [displayWith] attribute in order to get to the Contact's name. However, in order to do that, I need to make a HTTP request and then return it. That is somehow not working. Bear in mind, the custom control's sole responsibility is to deal with the ContactID. That's all it knows. 

Source Code:

Mark-up of the page consuming my custom control

<w1-contact-autocomplete-directive *ngIf="isEditMode"
name="contactId"
[(ngModel)]="projectMarketing.detail.contactId"
[disabled]="!w1UserContextService.userCanWriteDataField('project','contact')"></w1-contact-autocomplete-directive>

Custom Control Mark-up

<form #contactAutocompleteForm="ngForm"
novalidate>
<mat-form-field class="width100 marginBottom10px"
appearance="outline">
<mat-label>Type to find Contact</mat-label>
<input type="text"
name="contact"
matInput
[matAutocomplete]="autoContact"
[disabled]="disabled"
[(ngModel)]="value"
(ngModelChange)="contactSearchQueryChanged($event)" />
<button mat-button
*ngIf="value"
matSuffix
mat-icon-button
aria-label="Clear"
(click)="clearContactSelection()">
<mat-icon>close</mat-icon>
</button>
<mat-autocomplete #autoContact="matAutocomplete"
[displayWith]="displayContactFullName.bind(this)">
<mat-option *ngFor="let contact of contacts|async"
[value]="contact.id">
{{contact.detail.fullName}}
</mat-option>
</mat-autocomplete>
</mat-form-field>
</form>


Custom Control Code: (This is where is issue lies). How can I return from "subscribe"?

displayContactFullName(contactId: string) {
if (contactId) {
return this.contactService.getContact(contactId).subscribe(rawContact => {
this.contact = new Contact(rawContact);
let returnValue = this.contact.detail.fullName;
console.log(returnValue);
return returnValue;
});
}
else {
return contactId;
}
}

Thank you

--Tolga










Sander Elias

unread,
Jan 7, 2019, 11:52:20 PM1/7/19
to Angular and AngularJS discussion
Hi Tolga,
 

displayContactFullName(contactId: string) {
if (contactId) {
return this.contactService.getContact(contactId).subscribe(rawContact => {
this.contact = new Contact(rawContact);
let returnValue = this.contact.detail.fullName;
console.log(returnValue);
return returnValue;
});
}
else {
return of(contactId);
}
} 
 
Make sure you always return an observable, (the change I did above) and then use the async pipe in your template.
Be aware that this might lead to a  huge number of small requests. Perhaps it's better to load the entire file at once?

Regards
Sander
Reply all
Reply to author
Forward
0 new messages