Angular11项目提交表单调用NbStepper.reset报undefined错误如何解决
问题原因
- 核心问题是
@ViewChild获取的settingFormStepper实例不存在,所以调用reset方法时报错。 - 直接诱因:你的
nb-stepper被包裹在带有*ngIf="!loading"的nb-card-body节点内:- 提交表单时通常会把
loading状态设为true触发加载态,此时*ngIf判定为假,整个nb-card-body内的DOM会被销毁,对应的settingFormStepper实例也会被回收变为undefined - 接口请求成功回调执行时,
loading状态还没重置为false,stepper还没重新渲染,引用自然为空。
- 提交表单时通常会把
修复方案
你可以根据业务场景选择任意一种方案:
方案1:替换*ngIf为[hidden]控制显示隐藏
[hidden]只会控制元素的CSS显示状态,不会销毁DOM和对应的组件实例,引用会一直存在,修改模板代码即可:
<!-- 原代码 --> <nb-card-body *ngIf="!loading" > <!-- 替换为 --> <nb-card-body [hidden]="loading" >
方案2:调用reset前先加非空判断
如果不想改动显示逻辑,加个判断即可避免报错,不会影响正常功能:
this.settingsService.create(formData) .subscribe((settings) => { this.toastrService.show(' Settings added', { status: 'success', duration: 10000 }); this.settingsService.resetForm(); // 新增非空判断 if (this.settingFormStepper) { this.settingFormStepper.reset(); } })
方案3:先重置加载态再操作stepper
如果必须保留*ngIf逻辑,需要先更新loading状态、等视图渲染完成后再调用reset方法,需要用到Angular的变更检测能力:
首先在组件中注入ChangeDetectorRef:
import { ChangeDetectorRef } from '@angular/core'; constructor(private cdr: ChangeDetectorRef) {}
再修改回调逻辑:
this.settingsService.create(formData) .subscribe((settings) => { this.toastrService.show(' Settings added', { status: 'success', duration: 10000 }); this.settingsService.resetForm(); // 先关闭加载态 this.loading = false; // 手动触发变更检测,等待stepper渲染完成 this.cdr.detectChanges(); this.settingFormStepper.reset(); })
内容的提问来源于stack exchange,提问作者hanushic
相关产品推荐
相关产品推荐

