问题
I was trying to use the Material Angular autocomplete and I came across the displayWith function which can be apparently used to be the output that is displayed on selection. I wanted to call a custom function within the display function like
displayFn(id) {
return this.getValue(id)
}
getValue(id) {
/**return some string
}
For the autocomplete
<mat-autocomplete #autoOutlet="matAutocomplete" [displayWith]="displayFn">
<mat-option *ngFor="let option of outletFilterOptions | async [value]="option.outletId">
{{ option.outletName }}
</mat-option>
</mat-autocomplete>
As you see I am using the id
as the model instead of the entire object.
When the display function returned an error that this.getValue is undefined I searched Stack Overflow for a solution and was suggested that I use something like [displayWith]="displayFn.bind(this)"
.
But unfortunately, that isn't working for me either. I am using Angular material 5.1.0.
Is there something I am missing?
回答1:
displayFn = value => {
// now you have access to 'this'
this.someMethod();
return 'formatted display';
}
回答2:
You could just change your template to be
<mat-autocomplete #autoOutlet="matAutocomplete" [displayWith]="displayFn(id, this)">
Inside of templates this
is a reference to your Component. Then just change your function to
displayFn(id, _this) {
return _this.getValue(id)
}
If [displayWith]
needs to be a function, you could create a property that returns your displayFn
like this:
get createDisplayFn() {
return (id) => {
return this.getValue(id)
}
}
and change your binding to [displayWith]="createDisplayFn"
. As ES6 arrow function can't be rebinded, this
should still be a reference to your component.
回答3:
It is because of this is not binding to the component and its binding to mat-select option
NOw for using component's function, you have to use arrow function, the preferable method or pass this from the HTML function
I will use the arrow function to use the component's function
Without arrow function
displayFn(data: any) {
return data.Id?this.sometask(data):''
}
With arrow function
displayFn = (data: any) => {
return data.Id?this.sometask(data):''
}
This work in my scenario and it worked in your scenario too.
回答4:
Define cThis = this
as a property of your class, and then use it inside your displayFn
function:
<mat-autocomplete #autoOutlet="matAutocomplete" [displayWith]="displayFn(id, cThis)">
cThis = this;
displayFn(id, cThis) {
return cThis.getValue(id)
}
getValue(id) {
/**return some string
}
Demo that shows binding in displayWith
回答5:
You just missed an undefined
check before using attribute.
<mat-autocomplete #auto="matAutocomplete" [displayWith]="displayFn" (optionSelected)="optionSelected($event)">
<mat-option *ngFor="let user of users" [value]="user" >
{{ user.first_name }} {{ user.last_name }}
</mat-option>
displayFn(user) {
if (!user) return '';
return user.name;
}
来源:https://stackoverflow.com/questions/49939310/binding-this-in-angular-material-autocomplete-displaywith-using-angular-5