我正在建立一条指令,该指令应替换组件(装入程序)中包含该元素的元素,并在到达延迟时发送错误消息。
遇到的问题:列表中的所有元素均由加载程序代替,而不是我单击的加载程序。
我找不到只选择已单击元素的方法。
Stackblitz: https://stackblitz.com/edit/angular-wmybgc?file=src%2Fapp%2Floader-and-error-handler.directive.ts
指令:
import { StoreService } from '@services/store/store.service';
import { Directive, Input, ViewContainerRef, TemplateRef, ComponentFactoryResolver, Type } from '@angular/core';
import { LoaderComponent } from '@components-ui/loader/loader.component';
export class LoaderAndErrorContext {
$implicit: boolean;
message: string;
}
@Directive({
selector: '[loaderAndErrorHandler]'
})
export class LoaderAndErrorHandlerDirective {
private isLoading: boolean;
@Input('loaderAndErrorHandlerWait') private delay: number;
@Input('loaderAndErrorHandlerBeforeDisplaying') private message: string;
@Input() set loaderAndErrorHandler(isLoading: boolean) {
this.isLoading = isLoading;
this.viewControllerRef.clear();
if (this.isLoading) {
this.displayComponent(LoaderComponent);
setTimeout(() => {
this.store.sendNotification(this.message);
}, this.delay);
}
else {
this.viewControllerRef.clear();
this.viewControllerRef.createEmbeddedView(this.templateRef);
}
}
constructor(
private viewControllerRef: ViewContainerRef,
private templateRef: TemplateRef<any>,
private componentFactoryResolver: ComponentFactoryResolver,
private store: StoreService
) {
this.displayComponent = this.displayComponent.bind(this);
}
displayComponent = (component: Type<LoaderComponent>, message?: string): void => {
const componentFactory = this.componentFactoryResolver.resolveComponentFactory(component);
message
? this.viewControllerRef.createComponent(componentFactory).instance['message'] = message
: this.viewControllerRef.createComponent(componentFactory);
}
}
实施:
<h2>Mes documents</h2>
<ul [@fadeInOutStagger]="documents.length">
<ng-container *loaderAndErrorHandler="isLoading; wait 2000 beforeDisplaying errorMessage;">
<li *ngFor="let document of documents | sortBy:'label'">
<article (click)="getDocument(document.id)" class="document-label">
<input type="image" src="assets/images/icon/icone_document.svg">
<label>
<strong>{{document.label}}</strong>
</label>
</article>
<article class="document-date">
<p>{{document.date | dateTo:'JJ Mois'}}</p>
</article>
</li>
</ng-container>
</ul>
答案 0 :(得分:0)
您可以这样操作:
<h2>Mes documents</h2>
<ul>
<ng-container *ngFor="let document of documents; let i = index" >
<li *loaderAndErrorHandler="document.isLoading; wait 2000 beforeDisplaying errorMessage;">
<article (click)="getDocument(document.id, i)" class="document-label">
<img src="https://image.noelshack.com/fichiers/2019/11/7/1552854323-iconfinder-note3-254240.png" height="20px" width="20px">
<label>
<strong>{{document.label}}</strong>
</label>
</article>
<article class="document-date">
<p>{{document.date}}</p>
</article>
</li>
</ng-container>
</ul>
getDocument
方法将循环索引作为额外的参数,以检索要更新的良好参数。对于该示例,您必须选择其他值以确保文档存在于数据中。
import { Component, Input, ViewRef } from '@angular/core';
import { StoreService } from './services/store/store.service';
@Component({
selector: 'my-app',
templateUrl: './app.component.html',
styleUrls: ['./app.component.scss'],
})
export class AppComponent {
documents = [
{
id: '123',
label: 'Certificat of something great',
date: '15 jun.',
isLoading: false
},
{
id: '123',
label: 'Certificat of something not so great',
date: '15 jun.',
isLoading: false
},
{
id: '123',
label: 'Certificat of something ok',
date: '15 jun.',
isLoading: false
},
];
public errorMessage = 'Erreur: Une erreur s\'est produite durant la récupération de votre document.\nVeuillez renouveler votre requête ultérieurement.'
constructor(private store: StoreService) {
this.store.notificationPublisher.subscribe(notification => {
console.log('Notification:', notification)
})
}
public getDocument = (documentId: string, documentIndex: number): void => {
this.documents[documentIndex].isLoading = true;
setTimeout(() => {
this.documents[documentIndex].isLoading = false;
}, 1000)
}
}
我只为每个文档和您用*ngFor
循环的项目添加了状态。
编辑:您可以在此处进行测试=> https://stackblitz.com/edit/angular-hfnhg7