StackOverflow 上有个敌人遇到了一个问题:
在 feature module 里,对一个 Component 进行提早加载:
留神上图第 9 行,导入了 CommonModule.
这个被提早加载的 Component 的模板文件里,应用到了 async 这个 pipe,其实当初 CommonModule 里。然而,因为该 module 被提早加载,因而并未动态地定义在 feature module 的 declarations 模块里。所以,该 Component 被加载的时候,其上下文无法访问到 async pipe.
所以,最初会呈现运行时谬误:
ERROR Error: The pipe ‘async’ could not be found!
解决方案,我曾经回复在 StackOverflow 里了:
https://stackoverflow.com/que…
在被提早加载的 Component 里,将其所属的 feature module 的定义人工加上即可:
import {ChangeDetectionStrategy, Component, NgModule} from '@angular/core';
import {Product, provideDefaultConfig, CmsConfig} from '@spartacus/core';
import {CurrentProductService, MediaModule, OutletModule, CarouselModule} from '@spartacus/storefront';
import {BehaviorSubject, combineLatest, Observable, of} from 'rxjs';
import {distinctUntilChanged, filter, map, tap} from 'rxjs/operators';
import {CommonModule} from '@angular/common';
import {RouterModule} from '@angular/router';
@Component({
selector: 'app-product-images',
templateUrl: './razer-product-images.component.html',
changeDetection: ChangeDetectionStrategy.OnPush,
})
export class CustomProductImagesComponent {private mainMediaContainer = new BehaviorSubject(null);
private product$: Observable<Product> = this.currentProductService
.getProduct()
.pipe(filter(Boolean),
distinctUntilChanged(),
tap((p: Product) => {this.mainMediaContainer.next(p.images?.PRIMARY ? p.images.PRIMARY : {});
})
);
thumbs$: Observable<any[]> = this.product$.pipe(map((p: Product) => this.createThumbs(p))
);
mainImage$ = combineLatest([this.product$, this.mainMediaContainer]).pipe(map(([, container]) => container)
);
constructor(private currentProductService: CurrentProductService) {}
openImage(item: any): void {this.mainMediaContainer.next(item);
}
isActive(thumbnail): Observable<boolean> {
return this.mainMediaContainer.pipe(filter(Boolean),
map((container: any) => {
return (
container.zoom &&
container.zoom.url &&
thumbnail.zoom &&
thumbnail.zoom.url &&
container.zoom.url === thumbnail.zoom.url
);
})
);
}
/** find the index of the main media in the list of media */
getActive(thumbs: any[]): Observable<number> {
return this.mainMediaContainer.pipe(filter(Boolean),
map((container: any) => {
const current = thumbs.find((t) =>
t.media &&
container.zoom &&
t.media.container &&
t.media.container.zoom &&
t.media.container.zoom.url === container.zoom.url
);
return thumbs.indexOf(current);
})
);
}
/**
* Return an array of CarouselItems for the product thumbnails.
* In case there are less then 2 thumbs, we return null.
*/
private createThumbs(product: Product): Observable<any>[] {
if (
!product.images ||
!product.images.GALLERY ||
product.images.GALLERY.length < 2
) {return [];
}
return (<any[]>product.images.GALLERY).map((c) => of({container: c}));
}
}
@NgModule({
imports: [
CommonModule,
RouterModule,
MediaModule,
OutletModule,
CarouselModule
],
declarations:[CustomProductImagesComponent]
})
export class CustomProductImagesModule {}
更多 Jerry 的原创文章,尽在:” 汪子熙 ”: