【问题标题】:Add (change) event listener to a field at runtime在运行时向字段添加(更改)事件侦听器
【发布时间】:2026-01-05 15:10:02
【问题描述】:

我有一些表单字段,使用JSON*ngFor 呈现。 字段的数量和顺序以及类型可能会有所不同。根据 JSON 上的参数,它们可以是 datetime 字段或文本字段。

唯一不变的是前两个始终是日期时间字段,StartDateEndDate

现在我希望能够检测这些字段的值何时发生变化,因此我可以检查StartDate 是否低于或等于EndDate

这是我的模板:

// Code to render the fields, be it datetime or text
  <div class="form-group">
  <div *ngIf="IsDateTime(campo.data_type); else textField">
       <app-datetimepicker #campoData [Cabecalho]="campo.alias" ></app-datetimepicker>
  </div>
    <ng-template #textField>
     <label>{{campo.alias}}</label>
     <input type="text" class="form-control">
    </ng-template> 

由于只有在JSON 的请求完成后,这些字段在编译时才存在,所以我无法将(change) 添加到 HTML,因为可能还有其他日期时间输入,但我只想要前两个。

我可以得到这两个字段和它们的值,我正在寻找一种方法来添加一个监听器当输入值发生变化时,但到目前为止没有成功。

我尝试了Renderer2,但收到了错误消息,我发现的大多数问题都告诉我将(change) 事件添加到模板中,但这不符合我的需要。

我怎么能这样做呢?

【问题讨论】:

    标签: angular datetime input event-binding


    【解决方案1】:

    你可以尝试做这样的事情:

    1. 声明这个新的 observable:
    formValueChanges$: Observable<any>;
    
    1. 初始化表单后,订阅其更改:
    // yourForm should be the name of your form
    this.formValueChanges$ = this.yourForm.valueChanges
       .pipe(
          //takeUntil(this.destroy$),
          debounceTime(0),
          distinctUntilChanged(),
          shareReplay(1)
        );
    
    1. 订阅后,您可以按所需字段进行过滤(我猜是您的示例中的 campo):
    this.formValueChanges$  
       .pipe(   
          //takeUntil(this.destroy$),
            distinctUntilKeyChanged('campo')
          )
          .subscribe(formValue => {
    
             // Here should be your logic
          });
    

    注意:您必须进行适当的导入

    import {
      map,
      takeUntil,
      filter,
      debounceTime,
      distinctUntilChanged,
      shareReplay,
      distinctUntilKeyChanged,
      finalize,
    } from 'rxjs/operators';
    import { Observable } from 'rxjs';
    

    【讨论】: