我有一个带有材质设计表的角度组件,其中显示了对象。该组件通过数据源获取其数据。数据源从http服务获取其数据。表格本身可以过滤。
这是我的代码,简化 - 如果您需要,请随时询问有关某些事项的更多信息..
customer.component.html
<md-input-container floatPlaceholder="never">
<input mdInput #filter placeholder="Filter customers">
</md-input-container>
<md-table #table [dataSource]="dataSource">
<ng-container cdkColumnDef="customerid">
<md-header-cell *cdkHeaderCellDef> ID </md-header-cell>
<md-cell *cdkCellDef="let row"> {{row.id}} </md-cell>
</ng-container>
<ng-container cdkColumnDef="remove">
<md-header-cell *cdkHeaderCellDef></md-header-cell>
<md-cell *cdkCellDef="let row">
<button md-button (click)="deleteCustomer(row)">
Remove Customer
</button>
</md-cell>
</ng-container>
<md-header-row *cdkHeaderRowDef="displayedColumns">
</md-header-row>
<md-row *cdkRowDef="let row; columns: displayedColumns;">
</md-row>
</md-table>
customer.component.ts
export class CustomerOverviewComponent implements OnInit {
public displayedColumns: string[] = [
"customerid", "remove"
];
public dataSource: CustomerOverviewDataSource | null;
@ViewChild("filter") filter: ElementRef;
constructor(private dataService: CustomerOverviewService,
private cdRef: ChangeDetectorRef) {
this.initDataSource(dataService);
}
ngOnInit(): void {
Observable.fromEvent(this.filter.nativeElement, "keyup")
.debounceTime(150)
.subscribe(() => {
if (!this.dataSource) { return; }
this.dataSource.filter = this.filter.nativeElement.value;
});
}
public deleteCustomer(customer: CustomerOverview): void {
this.dataSource.disconnect();
this.dataService
.Delete(customer.id)
.subscribe(data => {
this.error.info(`Customer with Id: ${data._body} deleted!`);
}, (err) => {
this.error.error(`Unable to delete customer: ${err.message}`);
});
this.dataSource.connect();
}
private initDataSource(dataService: CustomerOverviewService): void {
this.dataSource = new CustomerOverviewDataSource(this.dataService);
}
}
customer.service.ts
@Injectable()
export class CustomerOverviewService {
private actionUrl: string;
private headers: Headers;
dataChange: BehaviorSubject<CustomerOverview[]> = new BehaviorSubject<CustomerOverview[]>([]);
get data(): CustomerOverview[] { return this.dataChange.value; }
constructor(private http: Http, private authHttp: AuthHttpService, public snackBar: MdSnackBar) {
this.actionUrl = Configuration.API_SERVER + "api/customeroverview/";
this.headers = new Headers();
this.headers.append("Content-Type", "application/json; charset=utf-8");
this.headers.append("Accept", "application/json");
this.GetAll().forEach(s => this.dataChange.next(s));
}
public GetAll = (): Observable<CustomerOverview[]> => {
return this.authHttp
.get(this.actionUrl)
.map((response: Response) => <CustomerOverview[]>response.json())
.publishReplay(1)
.refCount();
}
public Delete = (id: number): Observable<any> => {
return this.authHttp.delete(this.actionUrl + id)
.catch(console.log("Delete Catch"));
}
}
export class CustomerOverviewDataSource extends DataSource<any> {
_filterChange = new BehaviorSubject("");
get filter(): string { return this._filterChange.value; }
set filter(filter: string) { this._filterChange.next(filter); }
constructor(private dataService: CustomerOverviewService) {
super();
}
/** Connect function called by the table to retrieve one stream containing the data to render. */
connect(): Observable<CustomerOverview[]> {
const displayDataChanges: any = [
this.dataService.GetAll(),
this._filterChange,];
return Observable.merge(...displayDataChanges).map(() => {
return this.dataService.data.slice().filter((item: CustomerOverview) => {
let searchStr: string = (item.gender + item.lastname + item.firstname + item.personalnumber
+ item.consultant + item.hasConsultingEntities).toLowerCase();
return searchStr.indexOf(this.filter.toLowerCase()) !== -1;
});
});
}
disconnect(): void {
console.log("disconnect");
}
}
当我从表中删除实体时,它不会更新。对象存储在哪里,所以我可以知道我要更新什么?我觉得HTML得到的对象是在常量变量displayDataChanges中,我不能改变它吗?
感谢任何正确方向的提示..
答案 0 :(得分:2)
你已经关闭,但这里有一些东西:
我不知道手动调用connect()
和disconnect()
的有效用例。 AFAIK connect()
只应在表之后调用,而disconnect()
是表,如果您需要进行任何类型的取消订阅或其他清理,则会进行回调。您可以从deleteCustomer()
。
displayDataChanges
包含dataService.GetAll()
。这意味着当表调用connect()
并且订阅结果时,GetAll()
将运行。我怀疑这是你想要的,因为GetAll()
已经被调用并缓存在CustomerOverviewService
的构造函数中。您可能希望dataService.dataChange
BehaviorSubject
成为displayDataChanges
的一部分。这意味着无论何时拨打dataChange.next(vals)
,您的connect()
Observable都会发出新值,表格也会更新。
调用Delete()
时,您的服务状态不会更改。每当请求完成时,您应该使用BehaviorSubject
推进next()
以使用新值更新dataChange
。您可以对当前data
进行排序并删除该条目,也可以再次致电GetAll()
。在任何一种情况下,next()
将新结果导入dataChange
,以便表格重新呈现。