【问题标题】:What is the easiest way to make editForm in Angular?在 Angular 中制作 editForm 的最简单方法是什么?
【发布时间】:2020-10-23 17:21:08
【问题描述】:

在我的数据库中,我有很多用户,他们有很多食谱。 每个食谱都有一些属性和成分集合。 下面是截图

Recipe with all properties

因此,当用户在页面上显示要编辑的配方时,应该出现(表单)带有加载当前数据的配方。这是一种工作,因为我可以看到数据,但我认为它没有做好。

我的表格在没有数组(成分)的情况下可以正常工作。你能告诉我应该如何在我的编辑表单中添加成分吗?

如果您看到我的代码并给我反馈和提示我应该改变什么,我将不胜感激。

export class RecipeEditComponent implements OnInit {
  @ViewChild('editForm') editForm: NgForm;
  recipe: IRecipe;
  photos: IPhoto[] = [];
  ingredients: IIngredient[] = [];
  uploader: FileUploader;
  hasBaseDropZoneOver = false;
  baseUrl = environment.apiUrl;
  
  currentMain: IPhoto;
  constructor(private route: ActivatedRoute, private recipeService: RecipeService,
    private toastr: ToastrService) { }

  ngOnInit(): void {
    this.loadRecipe();  
  }

  loadRecipe() {
    this.recipeService.getRecipe(this.route.snapshot.params.id).subscribe(recipe => {
      this.recipe = recipe;
      this.initializeUploader();
    })
  }
  updateRecipe(id: number) {
    this.recipeService.editRecipe(id, this.recipe).subscribe(next => {
      this.toastr.success('Recipe updated successfully');
      this.editForm.reset(this.recipe);
    }, error => {
      this.toastr.error(error);
    });
  }

}

HTML

<div class="container mt-4 border" *ngIf="recipe">
    <form #editForm="ngForm" id="editForm" (ngSubmit)="updateRecipe(recipe.id)" >
      <h5 class=" text-center mt-2">Recipe details:</h5>
        <div class="form-group mt-3">
          <label for="city">Name</label>
          <input class="form-control" type="text" name="name" [(ngModel)]="recipe.name">
        </div>
        <div class="form-group">
          <app-ingredient-editor [ingredients] = "recipe.ingredients"></app-ingredient-editor>
          <div *ngFor="let ingredient of recipe.ingredients; let i = index">

            <input class="form-control" type="text" name="{{ingredient.name}}" [(ngModel)]="ingredient.name">
            <input class="form-control" type="text" name="{{ingredient.amount}}" [(ngModel)]="ingredient.amount">
          </div>
        </div>
        <div class="form-group">
          <br>
          <p>Add recipes</p>
        </div>
      <h5 class=" text-center mt-4">Description</h5>
        <angular-editor cols=100% rows="6" [placeholder]="'Your description'" [(ngModel)]="recipe.description"  name="description"></angular-editor>
    </form>  

    <button [disabled]="!editForm.dirty" form="editForm" class="btn btn-success btn-block mb-5 mt-5">Save changes</button>
  </div>

现在看起来像:

Form on page

当我在控制台上更改时删除成分名称时出现以下错误:

recipe-edit.component.html:12 ERROR Error: If ngModel is used within a form tag, either the name attribute must be set or the form
      control must be defined as 'standalone' in ngModelOptions.

问题是那部分代码:

 <div *ngFor="let ingredient of recipe.ingredients; let i = index">
    
                <input class="form-control" type="text" name="{{ingredient.name}}" [(ngModel)]="ingredient.name">
                <input class="form-control" type="text" name="{{ingredient.amount}}" [(ngModel)]="ingredient.amount">
              </div>
            </div>

但我不知道如何使它工作..

如何在模板驱动的表单中添加数组? 就我而言,我需要显示当前成分并能够对其进行编辑。

我尝试过这样的事情:

<input class="form-control" type="text" name="ingredient[i].name" [(ngModel)]="ingredient[i].name">
            <input class="form-control" type="text" name="ingredient[i].amount" [(ngModel)]="ingredient[i].amount">

但是 id 不起作用

【问题讨论】:

    标签: javascript angular typescript


    【解决方案1】:

    问题是必须定义表单上的属性name,以便 Angular 知道要更新哪个输入。您将 name 绑定到可编辑模型设置的同一属性,这意味着用户可以编辑它并实际上删除它,这不好。

    解决方案是将其更改为不变的唯一值。这应该有效:

    <div *ngFor="let ingredient of recipe.ingredients; let i = index">
        <input class="form-control" type="text" name="name{{ingredient.id}}" [(ngModel)]="ingredient.name">
        <input class="form-control" type="text" name="amount{{ingredient.id}}" [(ngModel)]="ingredient.amount">
      </div>
    </div>
    

    stackblitz 的链接显示它正在工作:https://stackblitz.com/edit/angular-10-base-template-q243lw?file=src%2Fapp%2Fapp.component.html

    编辑:修复原始帖子中的错误并添加指向 stackblitz 的链接

    【讨论】:

    • 目前我有 2 种成分。如果我在页面上使用您的解决方案,我只有 4 个字段和金额? “您将名称绑定到可编辑模型设置的相同属性,这意味着用户可以编辑它并实际上删除它。-这就是我想要做的!
    • 我不明白您的用户为什么需要编辑输入字段的名称。这只是一个标识符,因此 Angular 知道要更新哪个字段。重要的是编辑值,这是通过 ngmodel 完成的
    • 好的,我在原来的帖子中发现了这个错误。每个字段都需要一个唯一的 ID,我为 name 和 amount 字段分配了相同的 ID。我更新了我的答案,其中包括一个指向 stackblitz 的链接,显示它正在工作
    • 您的解决方案解决了这个问题,但是当我在该方法中更新配方时执行 this.editForm.reset(this.recipe) 并且表单正在重置。值:名称、描述可见,但包含成分的字段为空。你知道为什么吗?
    • reset 将清除所有输入。名称和描述不会被清除,因为它们不是输入,它们只是代码中的硬编码文本。我想我不太确定想要的效果是什么
    猜你喜欢
    • 2021-12-09
    • 1970-01-01
    • 2010-11-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多