当字段未触及时,Angular Responsive form返回空值
在我的用例中,当用户单击编辑按钮时,Angular向后端发出HTTP调用并检索对象,然后在编辑表单上填充这些值。用户可以更新或保持字段不变。单击当字段未触及时,Angular Responsive form返回空值,angular,angular6,angular7,angular-httpclient,Angular,Angular6,Angular7,Angular Httpclient,在我的用例中,当用户单击编辑按钮时,Angular向后端发出HTTP调用并检索对象,然后在编辑表单上填充这些值。用户可以更新或保持字段不变。单击update按钮时,Angular应获取表单中的所有值并将其发送到后端。因此,问题是,在将值加载到编辑页面表单并更新一些字段并保留一些字段不变后,未触及的值将变为空。这真奇怪 产品编辑.component.html <div *ngIf="productDataAvailable()"> <h2>Update Product&
update
按钮时,Angular应获取表单中的所有值并将其发送到后端。因此,问题是,在将值加载到编辑页面表单并更新一些字段并保留一些字段不变后,未触及的值将变为空。这真奇怪
产品编辑.component.html
<div *ngIf="productDataAvailable()">
<h2>Update Product</h2>
<br/>
<form [formGroup]="productForm">
<div class="form-group">
<label for="id">Product Id</label>
<input class="form-control" formControlName="id" id="id" type="text" value="{{product.id}}">
<small class="form-text text-muted" id="emailHelp"></small>
</div>
<div class="form-group">
<label for="name">Name</label>
<input class="form-control" formControlName="name" id="name" type="text" value="{{product.name}}">
</div>
<div class="form-group">
<label for="description">Description</label>
<input class="form-control" formControlName="description" height="100" id="description" required type="text"
[value]="product.description" width="200">
</div>
<div class="form-group">
<label for="currency">Price</label> <br/>
<label>
<select (load)="loadCurrencies()" class="form-control" [value]="product.price.currency.symbol" formControlName="currency" id="currency" name="currency">
<option *ngFor="let currency of currencies" value={{currency.id}}>
{{currency.name}}
</option>
</select>
</label>
<input formControlName="price" id="price" required style="margin: 10px; padding: 5px" type="text" [value]="product.price.amount">
</div>
<div class="form-group">
<label>Category:
<select (load)="loadCategories()" class="form-control" formControlName="category" name="category">
<option [value]="category.id" *ngFor="let category of categories">
{{category.name}}
</option>
</select>
</label>
</div>
<div class="form-group">
<label>Manufacturer:
<select (load)="loadManufacturers()" class="form-control" [value]="product.manufacturer.name" formControlName="manufacturer" name="manufacturer">
<option [value]="manufacturer.id" *ngFor="let manufacturer of manufacturers" >
{{manufacturer.name}}
</option>
</select>
</label>
</div>
<button (click)="updateProduct()" class="btn btn-primary" type="submit">Submit</button>
<button (click)="goBack()" class="btn btn-primary" style="margin-left: 30px" type="button">Cancel</button>
</form>
</div>
据我所知,您已发出HTTP请求以从服务器获取数据,但您没有以正确的方式填充
productForm
FormGroup。由于您使用的是被动表单,我强烈建议您使用或更新FormControls
updateProduct() {
const id = this.route.snapshot.paramMap.get('id');
const url = SERVER_URL + PRODUCT_API_URL + 'update';
//console.log(this.productFrom.value)
const product = this.productForm.value
this.productService.updateProduct(url, product).subscribe(
value => {
console.log('Successfully updated product');
}, error1 => {
console.log('Failed to update product');
},
() => {
this.router.navigate(['/product/list']);
});
}
对于您的情况,我建议使用patchValue
,因为它比setValue
更灵活<代码>补丁值不要求在参数中指定所有FormControls,以便更新/设置表单控件的值
这就是如何使用patchValue。在getProduct()
方法中,您可以通过这样做将getProductDetails()
响应中的属性从getProductDetails()传递到FormGroup中
getProduct() {
const id = this.route.snapshot.paramMap.get('id');
const url = SERVER_URL + PRODUCT_API_URL + 'find/' + id;
this.productService.getProductDetails(url).pipe()
.subscribe(
data => {
this.productForm.patchValue({
id: data.id
name: data.name
description: data.description
// other form fields
})
},
error => {
console.log(error);
},
() => console.log('getProduct() success'));
}
此外,在模板html上,不需要在每个
或
上绑定值
属性。您可以将它们全部删除。这是因为,您已经在使用patchValue
更新值
<div class="form-group">
<label for="name">Name</label>
<input class="form-control" formControlName="name" id="name" type="text">
</div>
<div class="form-group">
<label for="description">Description</label>
<input class="form-control" formControlName="description" height="100" id="description" required type="text" width="200">
</div>
你忽略了反应形式和角度的整体原理。真相在模型中,而不是在视图中。如果希望表单控件具有值,则将该值存储在此表单控件的模型中(即,设置表单控件对象的值)。您不使用value=“{{product.id}}”
。修改模型会修改视图。在输入中输入某些内容会修改模型。请参阅(我链接到了一个特定的部分,但您最好阅读整个指南)不使用ngModel
双向绑定的任何原因?我是新来的,所以如果这是明显的/不明显的,请原谅helpful@AndrewAllenngModel用于模板驱动的表单。“在使用被动窗体时,您不使用它。@jbnize对不起,我复制了OP的代码,因为我是懒惰的AF。将删除它。我想我尝试了与您的解决方案类似的版本。”。让我再试一次。我们如何处理选择下拉列表{currency.name}
在本例中,我需要遍历选项并将currency.id
设置为选项值。我应该在哪里做这个?用HTML还是用组件?我认为这不可能用HTML来表达。请让我知道。它应该是[value]=“currency.id”
。2.此选择框的FormControl应包含所选值,即应选择的区域的ID。@Jadda很乐意提供帮助!是的,这是正确的。您需要将其绑定到值
属性,该属性可以是字符串或数字。如果需要将其绑定到对象,则需要使用ngValue
而不是value
<div class="form-group">
<label for="name">Name</label>
<input class="form-control" formControlName="name" id="name" type="text">
</div>
<div class="form-group">
<label for="description">Description</label>
<input class="form-control" formControlName="description" height="100" id="description" required type="text" width="200">
</div>
updateProduct() {
const id = this.route.snapshot.paramMap.get('id');
const url = SERVER_URL + PRODUCT_API_URL + 'update';
//console.log(this.productFrom.value)
const product = this.productForm.value
this.productService.updateProduct(url, product).subscribe(
value => {
console.log('Successfully updated product');
}, error1 => {
console.log('Failed to update product');
},
() => {
this.router.navigate(['/product/list']);
});
}