[英]Angular component does not update correctly using @Input and a Service
I'm using Angular version 7 with a component that has a serie of divs being rendering according to the data coming from an @Input
and it should be updated due the service response, nevertheless the component is not correctly updated, the loader remains loading ( loading=true
) until I click into the text input and then I click elsewhere.我正在使用 Angular 版本 7 和一个组件,该组件具有根据来自
@Input
的数据呈现的一系列 div 并且它应该由于服务响应而更新,但是组件没有正确更新,加载器仍在加载( loading=true
) 直到我单击文本输入,然后单击其他位置。
Template:模板:
<div class="row" *ngFor="let message of messages">
<div>{{message.date}}</div>
<div>{{message.body}}</div>
</div>
<div class="row" *ngIf="thread.isOpen">
<div class="panel" >
<form (ngSubmit)="onSubmit()" [formGroup]="messageForm">
<textarea class="textarea" name="message" id="message" formControlName="message"></textarea>
<button class="btn"">
<span *ngIf="!loading; else loadingTemplate">send</span>
<ng-template #loadingTemplate>
<i class="fa fa-spin"></i>
</ng-template>
</button>
</form>
</div>
Component:零件:
@Input() messages;
messageForm: FormGroup;
loading: boolean = false;
ngOnInit(): void {
this.loadFromControls();
}
loadFromControls(): void {
this.messageForm = this.formBuilder.group({
message: this.formBuilder.control('', [])
});
}
onSubmit() {
if (!this.messageForm.valid) return;
this.loading = true;
const message = this.messageForm.controls['message'].value;
this.service.sendMessage(this.thread._id, message).subscribe(() => {
if (this.messages) {
this.messages.push({
isFromExtranet: true,
date: new Date(),
body: message
});
}
this.messageForm.controls['message'].setValue("");
this.loading = false;
}, (err) => this.errorMessage(err));
}
Service服务
sendMessage(id: string, message: string): Observable<any> {
return this.http.post(`/api/messages/${id}`, { message })
.map((res) => res.json())
.catch((error) => Observable.throw(error.json().code || 'error'));
}
I've been dealing with this a few hours and maybe I'm just missing something very basic.我已经处理了几个小时,也许我只是错过了一些非常基本的东西。
Can you try update the code as per below and make sure that you're getting correct value from @Input decorator.您可以尝试按照以下方式更新代码,并确保您从 @Input 装饰器中获得正确的值。
<div *ngIf="isDataloaded>
<div class="row" *ngFor="let message of messages">
<div>{{message.date}}</div>
<div>{{message.body}}</div>
</div>
<div class="row" *ngIf="thread.isOpen">
<div class="panel" >
<form (ngSubmit)="onSubmit()" [formGroup]="messageForm">
<textarea class="textarea" name="message" id="message" formControlName="message"></textarea>
<button class="btn"">
<span *ngIf="!loading; else loadingTemplate">send</span>
<ng-template #loadingTemplate>
<i class="fa fa-spin"></i>
</ng-template>
</button>
</form>
</div>
</div>
Component.ts组件.ts
@Input() messages;
isDataloaded = flase;
messageForm: FormGroup;
loading: boolean = false;
ngOnInit(): void {
this.loadFromControls();
}
loadFromControls(): void {
this.messageForm = this.formBuilder.group({
message: this.formBuilder.control('', [])
});
}
onSubmit() {
this.loading = true;
if (!this.messageForm.valid) return;
const message = this.messageForm.controls['message'].value;
this.service.sendMessage(this.thread._id, message).subscribe(() => {
if (this.event.data.discussionThread.messages) {
this.event.data.discussionThread.messages.push({
isFromExtranet: true,
date: new Date(),
body: message
});
}
this.messageForm.controls['message'].setValue("");
this.loading = false;
}, (err) => this.errorMessage(err));
this.isDataloaded = true;
}
I fixed using a BehaviorSubject
, as:我使用
BehaviorSubject
进行了修复,如下所示:
loading$: BehaviorSubject<boolean> = new BehaviorSubject(false);
...
this.loading$.next(true);
instead of:代替:
loading: boolean = false;
...
this.loading = true;
and in the template with async as:并在模板中异步为:
<span *ngIf="!(loading$ | async); else loadingTemplate">
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.