primengprimeng-turbotable

How to filter on a primeNG table with a dropdown and apply the filter only when pressing the apply button?


I am trying to filter a column in the primeNG table with a drop down menu, but I want to apply the filter only when I press the Apply button. Now filtering happens in the onChange event. If I remove the onChange event the filter does not work

This is the code without onChange event:

<p-table #dt1 [value]="customers">
    <ng-template pTemplate="header">
        <tr>
            <th>
               <div>
              Status
              <p-columnFilter field="status" matchMode="equals" display="menu"   [showOperator]="false" [showMatchModes]="false"> 
                  <ng-template pTemplate="filter" let-value let-filter="filterCallback">
                      <p-dropdown [ngModel]="value" [options]="statuses"  placeholder="Any">
                          <ng-template let-option pTemplate="item">
                              {{option.label}}
                          </ng-template>
                      </p-dropdown>
                  </ng-template>
              </p-columnFilter>
          </div>
            </th>
        </tr>
    </ng-template>
    <ng-template pTemplate="body" let-customer>
        <tr>        
            <td>
            {{customer.status}}
            </td>
        </tr>
    </ng-template>
</p-table>

When I press the Apply button the filter value is null

Here is a stackblitz: https://stackblitz.com/edit/primeng-tablefilter-demo-hbvzhe


Solution

  • I don't know if you still need the answer, but I'll post it anyway for other people to find it.

    The documentation isn't really clear on the filterCallback element of the filter (feel free to tell me if i have missed something), but i managed to stop it from calling the lazy load with this code:

    On the filter template itself:

      <ng-template pTemplate="filter" let-value let-filter="filterCallback">
        <p-dropdown
          [ngModel]="value"
          (onChange)="customFilterCallback(filter, $event.value)"></p-dropdown>
      </ng-template>
    
     customFilterCallback(filter: (a) => void, value: any): void {
       this.stopListening = true;
       filter(value);
       this.stopListening = false;
     }
    

    On the method listening to the onLazyLoad event of the table:

    (onLazyLoad)="lazy_load($event)"
    
    lazy_load(event: LazyLoadEvent): void {
      if (this.stopListening) {
        return;
      }
      ...loading stuff
    }
    

    Using this solution you can stop the loading every time you change the custom filter. Of course, the data displayed isn't going to match the filter until the "Apply" button is pressed (or until the lazy loading is triggered any other way).

    It really would be better if the library provided a way to stop the onLazyLoad event when the filter is changed.

    EDIT: This of course only works for custom filters, when you add a new constraint to the default filter, it's going to trigger the lazy loading.