Thursday, May 23, 2024
 Popular · Latest · Hot · Upcoming
182
rated 0 times [  189] [ 7]  / answers: 1 / hits: 6563  / 5 Years ago, wed, august 21, 2019, 12:00:00

I'm trying to filter a default value if no result is found on my query.



I tried using ng-template, but I simply don't manage to do it.






Rather than writing, here are images to better understand :



enter



enter



This is my successful filter : it correctly shows my datas once I filter them in the search box.






However if I try to enter an invalid data as done below :



enter



It simply returns me an empty html table.



Which is not what I'd like to achieve. I'd like it instead to show a message saying : no data found.



How can I do it please?






And here is my source code :



Component :



import {Component, OnInit} from '@angular/core';
import {IProduct} from './product';

@Component({
selector: 'pm-products',
templateUrl: './product-list.component.html',
styleUrls: ['./product-list.component.css']
})

export class ProductListComponent implements OnInit {

///////////////////////////////////// PROPERTIES //////////////////////////////////////

// String Interpolation
pageTitle = 'Product List';

// Property binding
imageWidth = 50;
imageMargin = 2;

// Event binding
showImage = false;

// Two-way binding
// listFilter = 'cart';

// Filter products
private _listFilter: string;

// Filter Products Array
filteredProducts: IProduct[];

///////////////////////////////////// CONSTRUCTOR //////////////////////////////////////

constructor() {
this.filteredProducts = this.products;
this.listFilter = 'cart';
}

/////////////////////////////////// GETTERS/SETTERS ///////////////////////////////////

get listFilter(): string {
return this._listFilter;
}

set listFilter(value: string) {
this._listFilter = value;
/***
* If there is a list of filtered value, show the list of the filtered values => this.performFilter(this.listFilter)
* Else, (if there is no filtered) return the whole set of products
*/
this.filteredProducts = this.listFilter ? this.performFilter(this.listFilter) : this.products;
}

/////////////////////////////////////// METHODS ///////////////////////////////////////

// Get Products
products: IProduct[] = [
{
productId: 2,
productName: 'Garden Cart',
productCode: 'GDN-0023',
releaseDate: 'March 18, 2019',
description: '15 gallon capacity rolling garden cart',
price: 32.99,
starRating: 4.2,
imageUrl: 'assets/images/garden_cart.png'
},
{
productId: 5,
productName: 'Hammer',
productCode: 'TBX-0048',
releaseDate: 'May 21, 2019',
description: 'Curved claw steel hammer',
price: 8.9,
starRating: 4.8,
imageUrl: 'assets/images/hammer.png'
},
];

performFilter(filterBy: string): IProduct[] {
/**
* filterBy result => to lower case. => case insensitive comparison.
* Return a new array of the filtered productS by the product name,
* by checking if that product name given is an index of the an element in the product array.
*/
filterBy = filterBy.toLowerCase(); // 1.
return this.products.filter((product: IProduct) => product.productName.toLowerCase().indexOf(filterBy) !== - 1); // 2.
}

toggleImage = (): void => {
this.showImage = !this.showImage;
}

////////////////////////////////// LIFECYCLE HOOKS ///////////////////////////////////

ngOnInit(): void {
console.log('hello');
}
}


HTML



<div class=card>

<div class=card-header>{{pageTitle}}</div>

<!-- CARD -->
<div class=card-body>
<div class=row>
<div class=col-md-2> Filter by:</div>
<div class=col-md-4>
<input [(ngModel)]=listFilter type=text/>
</div>
</div>
<div class=row>
<div class=col-md-6>
<h4>Filtered by: {{listFilter}} </h4>
</div>
</div>
<!-- ./CARD -->

<!-- TABLE -->
<div class=table-responsive>
<table *ngIf=products && products.length class=table>
<thead>
<tr>
<th>
<button (click)=toggleImage() class=btn btn-primary>{{showImage ? Hide : Show}} image</button>
</th>
<th>Product</th>
<th>Code</th>
<th>Available</th>
<th>Price</th>
<th>5 Star Rating</th>
</tr>
</thead>
<tbody>
<tr *ngFor=let product of filteredProducts>
<td><img *ngIf=showImage [src]=product.imageUrl [title]=product.productName
[style.width.px]=imageWidth [style.margin.px]=imageMargin alt=></td>
<td>{{product.productName}}</td>
<td>{{product.productCode | lowercase | convertToSpaces: '-'}}</td>
<td>{{product.releaseDate}}</td>
<td>{{product.price | currency: 'EUR':'symbol':'2.2-2'}}</td>
<td>{{product.starRating}}</td>
</tr>
</tbody>
</table>
</div>
<!-- ./TABLE -->
</div>
</div>





Please take care of yourself.


More From » angular

 Answers
3

Maybe just include an *ngIf=!filteredProducts.length wherever you'd like to show your message.



ex.




<tr *ngFor=let product of filteredProducts>
//Your table stuff
</tr>
<tr *ngIf=!filteredProducts.length>
<td colspan=6>No data found</td>
</tr>

[#6494] Tuesday, August 20, 2019, 5 Years  [reply] [flag answer]
Only authorized users can answer the question. Please sign in first, or register a free account.
jesseh

Total Points: 579
Total Questions: 98
Total Answers: 99

Location: Reunion
Member since Mon, Dec 28, 2020
3 Years ago
jesseh questions
;