Reputation: 92
I'm using 3 inputs to filter my data with a http request with searchvaluechanges and observable. My problem is to filter the table with the data I get. The table is filled with a http GET when the dashboard is loaded. Currently I'm not sure if mat-table is the best approach. I can't see a way to make it work.
Dashboard.component.html
<div class="row align-items-end">
<div class="col">
<input (change)="searchValueChange()" [(ngModel)]="filter.articleNumber" id="search-box" matInput
placeholder="Articlenumber...">
<input (change)="searchValueChange()" [(ngModel)]="filter.name" matInput placeholder="Name...">
<input (change)="searchValueChange()" [(ngModel)]="filter.description" matInput placeholder="Description...">
</div>
</div>
<div class="row">
<div class="col">
<mat-table [dataSource]="articles" class="mat-elevation-z8">
<!-- ArticleNumber Column -->
<ng-container matColumnDef="articleNumber">
<mat-header-cell *matHeaderCellDef> Articlenumber</mat-header-cell>
<mat-cell *matCellDef="let article"> {{article.articleNumber}} </mat-cell>
</ng-container>
</mat-table>
</div>
</div>
Dashboard.component.ts
export class DashboardComponent implements OnInit {
public search$: Observable<ArticleSmall[]>;
public filter: ArticleFilter = {
articleNumber: '',
name: '',
description: ''
};
public articles: ArticleSmall[] = [];
public searchTerms: Subject<any> = new Subject<any>();
public dataSource = new MatTableDataSource(this.articles);
public displayedColumns: string[] = ['articleNumber', 'name', 'description', 'actions'];
constructor(private articleService: ArticleService) {
}
public ngOnInit(): void {
this.getArticles();
this.search$ = this.searchTerms.pipe(
debounceTime(300),
distinctUntilChanged(),
switchMap(() => this.articleService.search(this.filter.articleNumber, this.filter.name, this.filter.description)));
}
public searchValueChange(): void {
this.searchTerms.next(JSON.stringify(this.filter));
}
//this loads all articles with reduced information in the Dashboards Mat-Table
public getArticles(): void {
this.articleService.getAllArticles()
.pipe(
map((articles: Article[]) => articles.map((article: Article) => {
const newArticle: ArticleSmall = {
name: article.name,
articleNumber: article.articleNumber,
description: article.description
};
return newArticle;
}
))
).subscribe((data: ArticleSmall[]) => this.articles = data);
}
}
Upvotes: 0
Views: 142
Reputation: 10790
Well, you need to make a few changes :
MatTableDataSource
<mat-table [dataSource]="dataSource" class="mat-elevation-z8">
<!-- ArticleNumber Column -->
<ng-container matColumnDef="articleNumber">
<mat-header-cell *matHeaderCellDef> Articlenumber</mat-header-cell>
<mat-cell *matCellDef="let article"> {{article.articleNumber}} </mat-cell>
</ng-container>
</mat-table>
$search
to update MatTableDataSource
's data. public ngOnInit(): void {
// previous code
this.$search.subscribe(data=>{ // I assumed that your service returns the data not response itself.
this.dataSource.data = data;
});
}
Edit 3. Also you need to change your initial load of data as below :
public getArticles(): void {
this.articleService.getAllArticles()
.pipe(
map((articles: Article[]) => articles.map((article: Article) => {
const newArticle: ArticleSmall = {
name: article.name,
articleNumber: article.articleNumber,
description: article.description
};
return newArticle;
}
))
).subscribe((data: ArticleSmall[]) => this.dataSource.data = data);
}
Upvotes: 1
Reputation: 418
Use the this.changeDetectorRefs.detectChanges()
function when you get the data inside your subscribe method.
You need to inject ChangeDetectorRefs
in the constructor.
You can find more info here
Upvotes: 1