首页 > 解决方案 > 角管道正在阻止模板函数执行

问题描述

我有一个应用程序,它采用对象数组并使用模板函数按对象属性值以升序或降序对数据进行排序sortByField()。该应用程序还可以过滤掉数据,这样如果用户输入搜索查询,则只显示匹配的记录。管道haku用于从数据中搜索查询,管道sivutus用于对数据进行分页。

代码中的错误是,如果附加了管道,该函数sortByField()不会按字段对数据进行排序。table| haku:postitoimipaikka | sivutus:sivu

一旦我从表中移除管道,该sortByField()功能就会正常运行。

这有效:

<tr *ngFor="let ottoautomaatti of ottoautomaatit">

这不起作用:

<tr *ngFor="let ottoautomaatti of ottoautomaatit | haku:postitoimipaikka | sivutus:sivu">

sivu.component.html:

<div class="form-group row">
  <label for="postitoimipaikka" class="col-sm-2 col-form-label">Postitoimipaikka</label>
  <div class="col-sm-10">
    <input class="form-control" type="text" id="postitoimipaikka" [(ngModel)]="postitoimipaikka"
      placeholder="Postitoimipaikka"> </div>
</div>

<p>Löytyi {{ ottoautomaatit | lukumaara:postitoimipaikka }} hakutulosta.</p>

<div class="btn-group" role="group" aria-label="Basic example">
  <button type="button" class="btn btn-secondary" (click)="edellinen(sivu)">Edellinen</button>
  <button type="button" class="btn btn-secondary" (click)="seuraava(sivu)">Seuraava</button>
</div>

<br><br>

<table class="table table-bordered table-responsive">
  <thead>
    <tr>
      <th (click)="sortByField('sijaintipaikka')">Sijaintipaikka</th>
      <th (click)="sortByField('sijaintipaikan_tyyppi')">Sijaintipaikan tyyppi</th>
      <th (click)="sortByField('postinumero')">Postinumero</th>
      <th (click)="sortByField('postitoimipaikka')">Postitoimipaikka</th>
      <th (click)="sortByField('kohteen_osoite')">kohteen_osoite</th>
      <th (click)="sortByField('aukioloaika')">Aukioloaika</th>
      <th (click)="sortByField('aukioloaika_lisatiedot')">Aukioloaika (lisatiedot)</th>
    </tr>
  </thead>
  <tbody>
    <tr *ngFor="let ottoautomaatti of ottoautomaatit | haku:postitoimipaikka | sivutus:sivu">
      <td>{{ ottoautomaatti.sijaintipaikka }}</td>
      <td>{{ ottoautomaatti.sijaintipaikan_tyyppi }}</td>
      <td>{{ ottoautomaatti.postinumero }}</td>
      <td>{{ ottoautomaatti.postitoimipaikka }}</td>
      <td>{{ ottoautomaatti.kohteen_osoite }}</td>
      <td>{{ ottoautomaatti.aukioloaika }}</td>
      <td>{{ ottoautomaatti.aukioloaika_lisatiedot }}</td>
    </tr>
  </tbody>
</table>

sivu.component.ts:

import { Component, OnInit } from '@angular/core';
import { Router, ActivatedRoute } from '@angular/router';
import { OttoautomaatitService } from '../ottoautomaatit.service';
import { ottoautomaatti } from '../ottoautomaatti.interface';

@Component({
  selector: 'app-sivu',
  templateUrl: './sivu.component.html',
  styleUrls: ['./sivu.component.css']
})
export class SivuComponent implements OnInit {

  postitoimipaikka: string;
  ottoautomaatit: ottoautomaatti[] = [];
  sivu: number;
  lukumaara: number = 0;

  lastSortedByField;
  ascendingOrder = true;

  constructor(
    private reitti: ActivatedRoute,
    private reititin: Router,
    private service: OttoautomaatitService
  ) { }

  ngOnInit() {
    this.service.haeKaikki().then((data) => {
      this.ottoautomaatit = data;
    })

    this.reitti.params.subscribe(parametrit => {
      this.sivu = +parametrit.sivu;
    })
  }

  edellinen = (sivu: number) => {
    if (sivu - 1 < 0) {
      this.reititin.navigateByUrl(`/sivu/0`);
    } else {
      this.reititin.navigateByUrl(`/sivu/${sivu - 1}`);
    }
  }

  seuraava = (sivu: number) => {
    this.reititin.navigateByUrl(`/sivu/${sivu + 1}`);
  }

  sortByField(field) {
    if (this.lastSortedByField === field) {
      this.ascendingOrder = !this.ascendingOrder;
    }
    else {
      this.lastSortedByField = field;
      this.ascendingOrder = true;
    }

    if (this.ascendingOrder) {
      this.ottoautomaatit = this.ottoautomaatit.sort((a, b) => {
        if (a[field] < b[field])
          return -1;
        if (a[field] > b[field])
          return 1;
        return 0;
      });
    } else {
      this.ottoautomaatit = this.ottoautomaatit.sort((a, b) => {
        if (a[field] < b[field])
          return 1;
        if (a[field] > b[field])
          return -1;
        return 0;
      });
    }

  }

}

ottoautomaatit.service.ts:

import { Injectable } from '@angular/core';
import { HttpClient } from '@angular/common/http';
import { ottoautomaatti } from '../app/ottoautomaatti.interface';

@Injectable()
export class OttoautomaatitService {

  constructor(public http: HttpClient) { }

  urli = "./assets/data.json";
  lukumaara: number = 0;

  haeKaikki = (): Promise<ottoautomaatti[]> => {
    return new Promise((resolve, reject) => {
      this.http.get(this.urli).subscribe((data: ottoautomaatti[]) => {
        resolve(data);
      }, (error) => {
        reject(error);
      })
    })
  }

  asetaLukumaara = (lukumaara: number) => {
    this.lukumaara = lukumaara;
  }

  haeLukumaara = () => {
    return this.lukumaara;
  }

}

haku.pipe.ts:

import { Pipe, PipeTransform } from '@angular/core';
import { ottoautomaatti } from './ottoautomaatti.interface';
import { OttoautomaatitService } from '../app/ottoautomaatit.service';

@Pipe({
  name: 'haku'
})
export class HakuPipe implements PipeTransform {

  constructor(private service: OttoautomaatitService) {}

  transform(ottoautomaatit: ottoautomaatti[], postitoimipaikka: string): any {
    let palautettavatAutomaatit: ottoautomaatti[] = [];

    if (postitoimipaikka) {
      palautettavatAutomaatit = ottoautomaatit.filter(o => o.postitoimipaikka.includes(postitoimipaikka.toUpperCase()));
    } else {
      palautettavatAutomaatit = ottoautomaatit;
    }
    this.service.asetaLukumaara(palautettavatAutomaatit.length);
    this.service.asetaLukumaara(palautettavatAutomaatit.length);
    return palautettavatAutomaatit;
  }

}

sivutus.pipe.ts:

import { Pipe, PipeTransform } from '@angular/core';
import { ottoautomaatti } from './ottoautomaatti.interface';

@Pipe({
  name: 'sivutus'
})
export class SivutusPipe implements PipeTransform {

  transform(ottoautomaatit: ottoautomaatti[], sivu: number): any {

    let data: ottoautomaatti[] = [];
    let indeksi = 0;
    let per_sivu = 100;

    for (let ottoautomaatti of ottoautomaatit) {
      if (indeksi >= (sivu * per_sivu) && indeksi < (sivu + 1) * per_sivu) {
        data.push(ottoautomaatti);
      }
      indeksi++;
    }

    return data;

  }

}

我希望能够单击表头,然后按升序或降序对数据进行排序,并对数据进行分页并使用搜索功能。

实际结果是应用程序中只有以下功能之一成功运行,而不是两者都成功:

标签: angulartypescript

解决方案


管道只能处理它获得的输入,传递多个管道意味着第一个管道的输出作为第二个管道的输入。

所以为了让你的管道工作,你应该返回数组并像这里一样环绕它


推荐阅读