从子组件中获取数据以在父组件中传递事件

时间:2019-04-26 21:47:12

标签: angular

我需要以下问题的帮助。

我有一个包含n个子组件的父组件。

例如:

父项:

<div class="row">
  <div class="col-6">
    Form1
    <app-form-card></app-form-card>
  </div>
  <div class="col-6">
    Form2
    <app-form-card></app-form-card>
  </div>
  <div class="col-6">
    Form3
    <app-form-card></app-form-card>
  </div>
  <div class="col-6">
    Form4
    <app-form-card></app-form-card>
  </div>
</div>

<div class="row">
  <div class="col-12">
    <button (click)="onSubmit()">Submit</button>
  </div>
</div>

子组件:

<div class="row mb-5">
  <form [formGroup]="profileForm">
  <div class="col-12 mb-2">
    <input type="text" formControlName="user" placeholder="user" />
  </div>
  <div class="col-12 mb-2">
    <input type="password" formControlName="password" placeholder="password" />
  </div>
  </form>
</div>

我需要知道哪种方法是最佳的(优化,可维护性,可伸缩性,良好实践),方法是单击“提交”按钮以获取所有表单的所有数据。

我目前可以通过两种方式做到这一点。

1-使用ViewChildren获取孩子的参考。这样,我就可以访问所有数据和功能。

2-使用Behaivor Subject发送表格。

我想知道哪个是最佳的?

更新1

基于用户 ccamac

的响应的可行解决方案

父组件

  myGroup: FormGroup;

  constructor( private fb: FormBuilder ) {
    this.myGroup = this.fb.group({
      formArray: this.fb.array([
        new FormGroup({
          user: new FormControl('', Validators.required),
          pass: new FormControl('', Validators.required)
        }),
          new FormGroup({
          user: new FormControl('', Validators.required),
          pass: new FormControl('', Validators.required)
        })
      ])
    });
  }

父级组件的HTML

<form (ngSubmit)="onSubmit()" [formGroup]="myGroup" >
<div formArrayName="formArray">
  <div *ngFor="let item of myGroup.controls?.formArray?.controls; let i = index;">
      <div [formGroupName]="i">
          <input type="text" placeholder="Username" formControlName="user">
          <input type="password" placeholder="Password" formControlName="pass">
      </div>
  </div>
</div>
<button type="submit" [disabled]="!myGroup.valid">
  Submit
</button>
</form>

使用此解决方案不需要子组件。

此解决方案很好,因为它可维护且可扩展。

1 个答案:

答案 0 :(得分:1)

这是使用此处显示的https://angular.io/api/forms/FormArray

的FormArray的绝佳机会

FormArray的想法是它包含一个FormGroups数组(或者实际上是任何AbstractControl)。因此,它非常适合您要执行的操作,因为最终您会有一组FormGroups作为集合。这种方法的好处之一是FormArray仍然具有FromGroup的许多选项,包括检查所有子窗体的有效状态并立即获取所有错误。

下面是一种可以针对您的情况进行构建的方法。

父组件模板

<!-- parentFormArray is passed into the child components -->
<div class="row">
  <div class="col-6">
    Form1
    <app-form-card [parentFormArray]="form"></app-form-card>
  </div>
  <div class="col-6">
    Form2
    <app-form-card [parentFormArray]="form"></app-form-card>
  </div>
  <div class="col-6">
    Form3
    <app-form-card [parentFormArray]="form"></app-form-card>
  </div>
  <div class="col-6">
    Form4
    <app-form-card [parentFormArray]="form"></app-form-card>
  </div>
</div>

父组件类

export class ParentComponent implements OnInit {

    form: FormArray;

    constructor(
        private fb: FormBuilder,
    ) {}

    ngOnInit(): void {
        this.form = this.fb.array([]); // start the formArray off as a blank array
    }

子组件模板(此处无需更改)

<div class="row mb-5">
  <form [formGroup]="profileForm">
  <div class="col-12 mb-2">
    <input type="text" formControlName="user" placeholder="user" />
  </div>
  <div class="col-12 mb-2">
    <input type="password" formControlName="password" placeholder="password" />
  </div>
  </form>
</div>

子组件类

export class ChildComponent implements OnInit {

    @Input() parentFormArray: FormArray; // this was passed in from the parent

    profileForm: FormGroup; // not sure how this is being built out, but I'm sure you are handling it somewhere

    constructor(
        private fb: FormBuilder,
    ) {}

    ngOnInit(): void {
        // first do whatever code is needed to build out the profile form
        // then push it onto the parent form array
        this.parentFormArray.push(this.profileForm);
    }