如何在不使用服务的情况下将子组件之间的反应式表单数据传递给父组件

Posted

技术标签:

【中文标题】如何在不使用服务的情况下将子组件之间的反应式表单数据传递给父组件【英文标题】:How to pass reactive form data between child to parent components with out using services 【发布时间】:2019-05-25 14:13:54 【问题描述】:

当我们点击父按钮时,我们希望使用父级的子响应式表单数据。目前我们正在使用 viewchild 来获取子组件引用。我们正在获取所有静态数据,但不是表单填充数据...................................................... ..................................................... ......

parent.component.ts
@ViewChild(DetailsComponent) childrenComponent: childrenComponent;

save()
let model=this.childrenComponent.buildDetailsModel();
/*here api to save model*/

children.component.ts
buildDetailsModel(): Details 
var a = 
  reportedToId: this.detailsForm.get('reportedTo').value,
  reportedOn: this.detailsForm.get('reportedTime').value,
  identifiedById: this.detailsForm.get('identifiedBy').value,
  identifiedOn: this.detailsForm.get('dateAndTimeIdentified').value,
  locationTypeId: this.detailsForm.get('locationType').value,
  addressId: this.detailsForm.get('locationAddress').value,
  AddressLine: this.detailsForm.get('locationOfAddress').value,
  description: this.detailsForm.get('description').value,
  PeopleExposed: this.dataSource
  ;
  return a;


parent.html 
<child></child>

child.html
<form [formGroup]="detailsForm">
  <div fxLayout="column wrap" fxLayoutGap="12px">

    <div fxLayout="column" fxLayout.lt-sm="column" fxLayout.lt-md="column" 
   fxLayoutGap="24px">

      <div fxFlex="row" fxLayoutGap="24px" fxLayout.lt-md="column">
        <div fxFlex="column">
          <mat-form-field>
            <mat-label>Reported To</mat-label>
            <mat-select matInput formControlName="reportedTo">
              <mat-option value="Test 1">Test 1</mat-option>
              <mat-option value="Test 2">Test 1</mat-option>
            </mat-select>
          </mat-form-field>


          <mat-form-field>
            <input matInput [matDatepicker]="reportedTime" placeholder="Date 
          and time reported" date="true" time="true" 
          formControlName="reportedTime">
            <mat-datepicker-toggle matSuffix [for]="reportedTime"></mat- 
           datepicker-toggle>
            <mat-datepicker #reportedTime></mat-datepicker>
          </mat-form-field>

          <mat-form-field>
            <mat-label>Identified by</mat-label>
            <mat-select matInput formControlName="identifiedBy">
              <mat-option value="Test 1">Test 1</mat-option>
              <mat-option value="Test 2">Test 1</mat-option>
            </mat-select>
          </mat-form-field>
        </div>

【问题讨论】:

你也可以分享你的html代码吗? 你能检查一次吗 【参考方案1】:

将您的子表单包裹在表单元素中,以便您可以从父表单提交您的子表单,然后在子组件中注入 FormGroupDirective 以获取父表单的引用

<form (ngSubmit)="save()" [formGroup]="detailsForm"> 
    <app-child></app-child>
    <button type="button">Save</button>
 </form>

然后使用controlContainer在子组件中提供已有的FormGroupDirective

childcomponent.ts

  form;
  constructor(private fb: FormBuilder, @Host() private parentFor: FormGroupDirective)  

  ngOnInit() 
    this.form = this.parentFor.form;
    //Add FormControl as per your need
    this.form.addControl('child', this.fb.group(
      name: "",
      email: ""
    ))

  

child.component.html

<form formGroupName="child">
  <input formControlName="name">
  <input formControlName="email">
</form>

例如:https://stackblitz.com/edit/angular-xusdev

【讨论】:

这是有效的。但是我怎样才能获得其他属性(除了表单字段)?由于我们在子组件中也使用了响应式表单字段和模板驱动的表单字段。【参考方案2】:

如果使用“referenceVariable”,您可以访问“child”的所有公共变量和函数

<button (click)="click(mychild)"></button>
<child #mychild></child>

click(mychild.any)

   console.log(mychild.detailsForm);

无论如何,我认为您想要一个属于表单的孩子。为此,您可以在孩子中使用 viewProviders

viewProviders: [
    
      provide: ControlContainer,
      useExisting: FormGroupDirective
    
  ]

如link 所示

【讨论】:

以上是关于如何在不使用服务的情况下将子组件之间的反应式表单数据传递给父组件的主要内容,如果未能解决你的问题,请参考以下文章

如何在不从当前活动选项卡中获取焦点的情况下将子窗口添加到 QMdiArea(设置为 TAB 模式)?

如何在不使用任何浏览器相关组件的情况下将数据发布到另一个网站?

在根元素内反应混合组件和 html

我们是不是可以在不使用 Datepicker 的情况下将材质 UI 选择器中的 Calendar 组件用作独立组件 - 如果可以,如何?

如何在不使用角度的ng的情况下将输入值从父组件传递给子组件?

如何在不使用 span 标签的情况下将颜色赋予 *