Home > Enterprise >  How to filter items from drop down list?
How to filter items from drop down list?

Time:04-08

I have an HTML table with data that is displayed (here is an illustration)

enter image description here

In fact, I would like to create a drop-down list and filter the HTML table according to the "type" column. There are two items in the drop-down list => "IN" or "OUT".

My problem is that when I select "IN" or "OUT", the HTML table does not refresh the page.

If I select "IN" for example, I should retrieve all rows with "IN" (here is an example)

enter image description here

To come back to my code... The method is called onChangeType()

    public onChangeType(type:any) {
        console.log("Debut ");
     
        this.selectedBrand=type;
            this.filteredCustomer=this.customerTransferts.filter(
              (item) => item.type === this.selectedBrand
            );
            console.log("Test => ");
            console.log(this.filteredCustomer);     
      }

Here are my consoles.logs from my browser.

enter image description here

I retrieve all the information....

But why is my drop down list not working?

I can share the whole code with you.

TS

    export class CustomerTransfertComponent implements OnInit, OnDestroy {
      private unsubscribe$ = new Subject<void>();
      customerTransferts: CustomerTransfert[] = [];
      filteredCustomer: CustomerTransfert[]=[];
     
      public selectedBrand: any; 
     
     
      constructor(
        private service: CustomerTransfertService, 
        private modalService: BsModalService)
        { }
     
      ngOnInit(): void {
        this.getCustomerTransfert();
        this.onChangeType;
      }
     
      ngOnDestroy(): void {
        this.unsubscribe$.next();
        this.unsubscribe$.complete();
      }
     
      /* Display datas for the HTML table  */ 
      private getCustomerTransfert(): void {
        this.service.getCustomerTransfert().pipe(
          takeUntil(this.unsubscribe$)
        ).subscribe(res => {
          console.log("Step 1");
     
          this.customerTransferts = res.PREA.map(val => {
            console.log("Step 2");
            return {
              cler: val.CLER,
              num: val.NUM,
              ref_rbc: val.REF_RBC,
              type: val.TYPE,
              quantite: val.QUANTITE,
              isin: val.ISIN,
              trade_date: val.TRADE_DATE,
              reception_date: val.RECEPTION_DATE,
              statut: val.STATUT,
              label: val.LABEL,
              svm: val.SVM,
              coursMoyenAchat: val.COURS_MOYEN_ACHAT,
              personneContact: val.PERSONNE_CONTACT,
              tel: val.TEL,
              fax: val.FAX,
              date: val.DATE,
              traitementDate: val.TRAITEMENT_DATE,
              annulationDate: val.ANNULATION_DATE,
              intitule1: val.INTITULE1,
              contrepartie: val.CONTREPARTIE,  
              tis: val.TIS   
     
            }
          });
        });
      }
    public onChangeType(type:any) {
        console.log("Debut ");
     
        this.selectedBrand=type;
            this.filteredCustomer=this.customerTransferts.filter(
              (item) => item.type === this.selectedBrand
            );
            console.log("Test => ");
            console.log(this.filteredCustomer);     
      }
     
     
    deleteCustomerTransfert(line: CustomerTransfert): void {
      this.modalService.show(CustomerTransfertCancelConfirmModalComponent, {
        initialState: {
          customerTransfertToCancel: line,
        },
     
        providers: [
     
          { provide: CustomerTransfertService }
     
        ]
     
      });
     
      }
     
    }

HTML

    <select  style="max-width: 100px" [ngModel]="selectedBrand" (ngModelChange)="onChangeType($event)">
        <option [value]="'IN'">IN</option>
        <option [value]="'OUT'">OUT</option>
    </select>

Thank you for your help and your time

EDIT

HTML

<div >
   <div >
      <div >
         <h1 >Consultation des transferts</h1>
         <div >
            <div  style="width: 100%;">
               <div >
                  <select  style="max-width: 100px" [ngModel]="selectedBrand" (ngModelChange)="onChangeType($event)">
                  <option [value]="'IN'">IN</option>
                  <option [value]="'OUT'">OUT</option>
                  </select>
                  <div >
                  </div>
                  <table >
                     <thead >
                        <tr >
                           <th scope="col">Client</th>
                           <th scope="col">N° de préavis</th>
                           <th scope="col">Réf</th>
                           <th scope="col">Type</th>
                           <th scope="col">Quantité</th>
                           <th scope="col">ISIN</th>
                           <th scope="col">Titre</th>
                           <th scope="col">Trade date</th>
                           <th scope="col">Settlement date</th>
                           <th scope="col">Status</th>
                           <th scope="col"></th>
                     </thead>
                     <tbody>
                        <tr *ngFor="let customerTransfert of customerTransferts">
                           <td scope="row" >{{customerTransfert.cler}}</td>
                           <td scope="row" >
                              <a [routerLink]="['/transferts/customer-transfert-details/'   customerTransfert.num]">{{customerTransfert.num}} </a>
                           </td>
                           <td scope="row" >{{customerTransfert.ref_rbc}}</td>
                           <td scope="row" >{{customerTransfert.type}}</td>
                           <td scope="row" >{{customerTransfert.quantite | number:'1.2-2'}}</td>
                           <td scope="row" >{{customerTransfert.isin}}</td>
                           <td scope="row" >{{customerTransfert.label}}</td>
                           <td scope="row" >{{customerTransfert.trade_date | cphFormatDate:'dd/MM/yyyy' }}</td>
                           <td scope="row" >{{customerTransfert.reception_date | cphFormatDate:'dd/MM/yyyy' }}</td>
                           <ng-container *ngIf="customerTransfert.statut === 1">
                              <td scope="row" >{{customerTransfert.statut}}</td>
                              <td >
                                 <button (click)="deleteCustomerTransfert(customerTransfert)" >Delete</button>
                              </td>
                           </ng-container>
                           <ng-container *ngIf="customerTransfert.statut === 8">
                              <td scope="row" >{{customerTransfert.statut}}</td>
                              <td >
                              </td>
                           </ng-container>
                           <ng-container *ngIf="customerTransfert.statut === 9">
                              <td scope="row" >{{customerTransfert.statut}}</td>
                              <td >
                              </td>
                           </ng-container>
                        </tr>
                     </tbody>
                  </table>
               </div>
            </div>
         </div>
      </div>
      <div ></div>
   </div>
</div>

EDIT2

filteredCustomer: CustomerTransfert[]=[];

CutsomerTransfert

export interface CustomerTransfert {
    cler: string;
    num: number;
    ref_rbc: string;
    type: string;
    quantite: number;
    isin: string;
    trade_date: Date;
    reception_date: Date;
    statut: number;
    label: string;
    svm: number;
    coursMoyenAchat: number;
    personneContact: string;
    tel: number;
    fax: number;
    date: Date;
    traitementDate: Date,
    annulationDate: Date,
    intitule1: string, 
    contrepartie: string,     
    tis: number,
}

JSON file => enter image description here

CodePudding user response:

You need to link the filtered array in your html

Change:

<tr *ngFor="let customerTransfert of customerTransferts">

To:

<tr *ngFor="let customerTransfert of filteredCustomer">

Then instantiate filteredCustomer in your subscribe callback:

private getCustomerTransfert(): void {
        this.service.getCustomerTransfert().pipe(
          takeUntil(this.unsubscribe$)
        ).subscribe(res => {
          console.log("Step 1");
     
          this.customerTransferts = res.PREA.map(val => {
            console.log("Step 2");
            return {
              cler: val.CLER,
              num: val.NUM,
              ref_rbc: val.REF_RBC,
              type: val.TYPE,
              quantite: val.QUANTITE,
              isin: val.ISIN,
              trade_date: val.TRADE_DATE,
              reception_date: val.RECEPTION_DATE,
              statut: val.STATUT,
              label: val.LABEL,
              svm: val.SVM,
              coursMoyenAchat: val.COURS_MOYEN_ACHAT,
              personneContact: val.PERSONNE_CONTACT,
              tel: val.TEL,
              fax: val.FAX,
              date: val.DATE,
              traitementDate: val.TRAITEMENT_DATE,
              annulationDate: val.ANNULATION_DATE,
              intitule1: val.INTITULE1,
              contrepartie: val.CONTREPARTIE,  
              tis: val.TIS   
            }
          });
          this.filteredCustomer = this.customerTransferts
        });
}

That should do it.

Also, you can remove this.onChangeType; from ngOnInit as it isn't doing anything.

CodePudding user response:

To rehydrate the view you need to work with observables.

So I suggest you to work with pipe async instead of use subscription inside component, so you can skip the unsubscription inside OnDestroy.

Plus, after declaring the observable you can rehydrate it updating the table value inside your onChangeType method.

For sake of semplicity I paste how you could refactoring your ts:

export class TableComponent implements OnInit {
  table$: Observable<any>;

  // ...other vars declarations

  constructor(
    private service: CustomerTransfertService,
    private modalService: BsModalService
  ) {}

  ngOnInit(): void {
    this.table$ = this.getCustomerTransfert()[0];
  }

  /* Display datas for the HTML table  */
  private getCustomerTransfert(): Observable<void> {
    return this.service.getCustomerTransfert().pipe(
      map((res) =>
        res.PREA.map((val) => ({
          cler: val.CLER,
          num: val.NUM,
          ref_rbc: val.REF_RBC,
          type: val.TYPE,
          quantite: val.QUANTITE,
          isin: val.ISIN,
          trade_date: val.TRADE_DATE,
          reception_date: val.RECEPTION_DATE,
          statut: val.STATUT,
          label: val.LABEL,
          svm: val.SVM,
          coursMoyenAchat: val.COURS_MOYEN_ACHAT,
          personneContact: val.PERSONNE_CONTACT,
          tel: val.TEL,
          fax: val.FAX,
          date: val.DATE,
          traitementDate: val.TRAITEMENT_DATE,
          annulationDate: val.ANNULATION_DATE,
          intitule1: val.INTITULE1,
          contrepartie: val.CONTREPARTIE,
          tis: val.TIS,
        }))
      )
    );
  }

  public onChangeType(type: any) {
    this.table$ =
      type === 'IN'
        ? this.table$.pipe(filter((res) => res.type === 'IN'))
        : this.table$.pipe(filter((res) => res.type === 'OUT'));
  }

  //...other methods
}

so in your component html you can render your table like the following:

<ng-container *ngIf="table$ | async as table">
  <table>
    <tbody>
      <tr>
        <td>
          table.cler
        </td>
      </tr>
      <tr>
        <td>
          table.num
        </td>
      </tr>
      <tr>
        <td>
         ecc..
        </td>
      </tr>
    </tbody>
  </table>
</ng-container>

I'm not test this snippet but in general way when you need to update your view, this is the approch you need to follow.

Let me know.

  • Related