我想要的行为:当用户从下拉菜单中选择“标签”时,以该Label作为参数调用api,并使用从api接收的数据重绘图表。页面中有多个相同的图表,并带有各自的下拉列表。 问题是我的解决方案不起作用,我不确定如何使它起作用。我的解决方案:
export class ChartComponent implements OnInit, OnDestroy{
private _label = new ReplaySubject<string>()
//Gets value from dropdown menu
@Input() set label(value: string) {this._label.next(value)}
apiSub: Subscription
constructor(private apiService: ApiService) {
}
ngOnInit() {
this.apiSub = this.apiService
.getData(this._label)
.subscribe(this.redrawGraph.bind(this),
console.error
)
}
ngOnDestroy() {
this.apiSub.unsubscribe();
}
redrawGraph(data:Data[]){
//Chart drawing logic
}
}
export class ApiService {
response= new ReplaySubject<Observable<Data[]>>()
constructor(private http: HttpClient) {
}
private static _handleError(err: HttpErrorResponse | any) {
return Observable.throw(err.message || 'Error: Unable to connect to API.');
}
getData( label: Observable<string> ): Observable<Data[]> {
label.subscribe(label => {
this.response.next(this.http
.get<Data[]>(`${Urls.DATA}?label=${label}`)
.catch(ApiService._handleError));
})
return this.response.mergeMap(x => x)
}
现在,只有在第一次标签更改时才调用redrawGraph()。而且,当存在多个图形时,显然存在不良行为,因为据我所知,服务是单例的,但是我不知道如何将响应绑定到“ this”而返回响应。
我要避免的是每次标签更改时都必须从Chart组件订阅/取消订阅api方法,而只需要一个流:标签更改-> api调用->重新绘制图表。那么如何正确执行呢?
答案 0 :(得分:0)
要使其生效,您需要为每个图表创建一个单独的主题。 该代码将如下所示:
getData( label: Observable<string> ): Observable<Data[]> {
let response : Subject = Subject<Data[]>();
label.subscribe(label => {
response.next(this.http
.get<Data[]>(`${Urls.DATA}?label=${label}`)
.catch(ApiService._handleError));
})
return response;
}