DebounceTime在Angular的订阅上不起作用

时间:2019-05-22 15:23:35

标签: angular

我是Angular和其他任何编程语言的新手。所以即使有关于此主题的其他文章,我也不太了解如何将debounceTime应用于我的项目,因为我编写了代码用于执行搜索的方法与其他方法不同。

我在html上有一个输入,该输入在keyup事件上调用一个函数,如下所示:

<input type="text" class="layout-search theme-search" placeholder="Pesquise outro vendedor ou unidade aqui..."
      (click)="searchError = false" (keyup)="search($event.target.value)" />

位于组件ts文件中的search()函数为:

  searchResult: Search;

  search(searchValue: any) {

    if (searchValue.length >= 3) {

      this.searchService.getSearch(searchValue)
        .subscribe(
          value => {
            this.searchResult = value;
            this.searchError = false;
          },

          error => this.searchError = true
        );

    } else {
      this.searchResult = undefined;
    }
  }

和searchService:

export class SearchService {

  private apiSearch = environment.apiBaseUrl + 'search/?search=';

  constructor(private http: HttpClient) { }

  getSearch(value: any): Observable<Search> {
     return this.http.get<Search>(this.apiSearch + value);
  }

我已将debounceTime导入组件:

 import { debounceTime } from 'rxjs/operators';

并尝试将search()编辑为:

  searchResult: Search;

  search(searchValue: any) {

    if (searchValue.length >= 3) {

      this.searchService.getSearch(searchValue)
      .pipe(debounceTime(1000))
        .subscribe(
          value => {
            this.searchResult = value;
            this.searchError = false;
          },

          error => this.searchError = true
        );

    } else {
      this.searchResult = undefined;
    }
  }

但是它似乎不起作用,浏览器或VS Code上也没有显示任何错误。 按照目前的方式,搜索可以正常工作,但是对于输入中按下的每个键,都要求提供API。

1 个答案:

答案 0 :(得分:0)

我以前已经实现了此功能,而不是在(keyup)元素的input输出上调用函数,而是使用fromEvent创建了一个侦听keyup事件的Observable。功能如下:

setupTypeaheadObservable() {
    fromEvent(this.searchInput.nativeElement, 'keyup')
        .pipe(
        map((ev: KeyboardEvent) => {
            if (ev && ev.key === 'Escape') {
            this.searchInput.nativeElement.blur();
            }
            return ev;
        }),
        filter((ev: KeyboardEvent) => ev.key !== 'Enter' && ev.key !== 'ArrowUp' && ev.key !== 'ArrowDown' && ev.key !== 'Escape'),
        debounceTime(this.typeaheadDebounceTime),
        distinctUntilChanged(),
        tap(() => this.valueChanged.emit(this.searchInput.nativeElement.value)),
        takeUntil(this.destroy$)
    ).subscribe()
}

在我的系统中,我忽略了Enter,Up,Down和Escape,因此我可以用其他方式处理这些事件。另外,我从setupTypeaheadObservable()方法调用ngOnInit。人们开始打字时就可以使用。最后,我将值从该组件传递给另一个将调用搜索服务的组件。因此,您可以直接致电搜索服务,而不用发出事件。

Here's a Stackblitz并附有示例。 TypeaheadComponent是包含所有这些代码的位置。