角2,无法修补值来形成控件

问题描述:

在我的角2应用程序中,我有一个编辑分配组件,当用户单击编辑按钮时加载。它显示一个表单并填充所有表单控件,并使用Firebase数据库中现有的值进行编辑。当我第一次点击编辑按钮时,它会加载表单控件中的所有值。然后,如果我返回或导航到任何其他链接,然后再次单击编辑按钮,表单控件不会修补来自Firebase数据库的值。角2,无法修补值来形成控件

下面的图像将帮助你理解这个问题更好:

我点击编辑按钮第一次一切,如果我回去一些其他的链接,然后点击返回正常工作 enter image description here

然后再次编辑按钮表单不会用来自Firebase数据库的值修补表单控件。 enter image description here

我验证我的表单如

constructor(
    private _routeParams: ActivatedRoute, 
    private _db: AngularFireDatabase, 
    private _fb: FormBuilder, 
    private _uploadService: UploadService, 
    private _getAsnService: GetAssignmentService, 
    private _editAsnSvc: EditAssignmentService, 
) { 
    console.log("in constructor"); 
    this.validate(); 
} 

ngOnInit() { 
    console.log("in init"); 
    this.getRouteParams(); 
    this.assignment = this._getAsnService.getAssignment(this.asnDetailKey); // this.assignment is FirebaseObjectObservable retrieved from firebase DB 
    this.setInputValues(); 
    this.getCourses(); 
    this.validate(); 
} 

validate() { 
this.form = this._fb.group({ 
    course: ['', Validators.compose([Validators.required])], 
    batch: ['', Validators.compose([Validators.required])], 
    subject: ['', Validators.compose([Validators.required])], 
    name: ['', Validators.compose([Validators.required])], 
    description: ['', Validators.compose([Validators.required])], 
    dueDate: ['', Validators.compose([Validators.required])] 
    }); 
    this.today = new Date().toJSON().split('T')[0]; 
} 

setInputValues() { 
    this.assignment.subscribe(asnDetails => { 
    console.log("setting values"); // <----- These are the values you see in console 
    this._assignment = asnDetails; 
    console.log(this._assignment); // <----- _assignment contains all values but form controls are unable to patch them 
    this.form.get('course').patchValue(this._assignment.course); 
    this.form.get('batch').patchValue(this._assignment.batch); 
    this.form.get('subject').patchValue(this._assignment.subject); 
    this.form.get('name').patchValue(this._assignment.AsnName); 
    this.form.get('description').patchValue(this._assignment.AsnDesc); 
    this.form.get('dueDate').patchValue(this._assignment.dueDate); 

    this.batches = this._db.list('/batches/' + this._assignment.course); 
}); 
} 

感谢

*编辑*

我删除了setInputValues方法也做了validateForm方法内部验证(我改变名称从validate到validateForm)通过传递asnDetails给它告知@ developer033

ngOnInit() { 
this.getRouteParams(); 
this.assignment = this._getAsnService.getAssignment(this.asnDetailKey); 
this.assignment.subscribe(asnDetails => this.validateForm(asnDetails)); 
this.getCourses(); 
} 

validateForm(asnDetails) { 
this.form = this._fb.group({ 
    course: [asnDetails.course, Validators.compose([Validators.required])], 
    batch: [asnDetails.batch, Validators.compose([Validators.required])], 
    subject: [asnDetails.subject, Validators.compose([Validators.required])], 
    name: [asnDetails.AsnName, Validators.compose([Validators.required])], 
    description: [asnDetails.AsnDesc, Validators.compose([Validators.required])], 
    dueDate: [asnDetails.dueDate, Validators.compose([Validators.required])] 
}); 
this.today = new Date().toJSON().split('T')[0]; 
this.batches = this._db.list('/batches/' + asnDetails.course); 
} 

我还创建了一个initForm方法,并从构造函数中调用它来初始化窗体。

initForm() { 
this.form = this._fb.group({ 
    course: ['', Validators.compose([Validators.required])], 
    batch: ['', Validators.compose([Validators.required])], 
    subject: ['', Validators.compose([Validators.required])], 
    name: ['', Validators.compose([Validators.required])], 
    description: ['', Validators.compose([Validators.required])], 
    dueDate: ['', Validators.compose([Validators.required])] 
}); 
} 

我认为这是动态验证模型驱动表单的更简洁的方式。

+1

为什么你不简化它,并在'validate()'中设置所有的值?事实上,你不需要'setInputValues()'。 – developer033

+0

如何动态地做到这一点?我是否需要传递赋值对象作为参数进行验证?对不起,我新来角。 – PR7

+0

是的,将'assignment'传递给你的'validate()'(也可以考虑重命名这个函数)。另外,不需要'Validator.compose'。请参阅[** this plunker **](http://plnkr.co/edit/NuCkJ8sK38oXKE9yyA7q?p=info)。 – developer033

您的validate()方法其实是错误的。它使用默认值和自动执行的验证器初始化表单。名称validate()是误导性的。在你的情况下,你每次创建一个带有this._fb.group()的新表单,并且你松开了以前的所有值。它的第一次正常工作,因为请求需要一些时间,并在此期间你的方法确实运行。我猜在所有其他情况下,请求可能会被缓存,因此在您的validate方法之前调用setInputValues。在致电asnService之前,只需将呼叫移至validate(),您应该会很好。问候Chris

+0

谢谢你ChrisY。它帮助:) – PR7