向组件

问题描述

这是我的场景:

我有一个组件,配置了 OnPush 策略,可以逐页显示 PDF 文档,并允许用户滚动页面并导航到某个页面。它还公开了一个输入属性 scrollToPage,它允许父级导航到某个页面

@Component({
    selector: 'pdf-document',templateUrl: './pdf-document.component.html',changeDetection: ChangeDetectionStrategy.OnPush,})
export class PdfDocumentComponent implements OnChanges {
    @input() scrollToPage: number;
    
    ngOnChanges(changes: SimpleChanges) {
        if (changes.scrollToPage) {
            this.goToPage(this.scrollToPage);
        }
    }

    public goToPage(page: number) {
        ...
    }
}

除一种情况外,一切都按预期工作:

  1. 父级将 scrollToPage 输入设置为数字 2
  2. ngOnChanges 触发并滚动到第 2 页
  3. 用户导航到 PdfDocumentComponent 内的另一个页面(从视图调用 goToPage 函数
  4. 父级再次将 scrollToPage 输入设置为数字 2

在这种情况下,不会触发 ngOnChanges 并且不会调用 goToPage 函数,因为 scrollToPage 的先前值是相同的,编号为 2。

为了解决这个问题,我只能看到 3 个选项,但它们似乎都不合适并且或多或少是黑客:

  1. 将输入类型更改为对象并始终发送新引用。 (我不喜欢这样,因为当我真的希望它发送一个简单的数字时发送一个对象是没有意义的)
  2. 在父组件中使用 @ViewChild 获取对子组件的引用并从那里调用 goToPage 函数。 (我不喜欢这样,因为我想让我的组件与外部的契约尽可能清晰——只使用 @input 和 @output 属性。否则,我也必须记录这些公共函数。)
  3. 将 OnPush 策略更改为认。 (这实际上不是我的选择)

你们知道这个问题的其他解决方案吗?有没有更优雅的解决方法

解决方法

您可以参加 KeyDown 活动。当用户按下一个键时执行。

<input type="text" (keydown)="onKeyDownEvent($event)" /> 

这里是 JavaScript 中键盘事件的详细信息,您可以将其用于此目的。 [1]:onKeyPress Vs. onKeyUp and onKeyDown