【问题标题】:Angular Dynamic Components: How to Set and Get DataAngular 动态组件:如何设置和获取数据
【发布时间】:2020-04-01 08:40:26
【问题描述】:

我需要根据预先确定的类型动态地创建组件,并且能够设置和从中获取数据。 到目前为止,我能够创建和显示组件,但我不知道如何设置或从中获取数据。

这就是我添加和显示组件的方式:

app.component.ts:

export class AppComponent {

    components: any[] = [];

    constructor(private componentFactoryResolver: ComponentFactoryResolver) { }


    addField(type: string) {

        let component: any;

        switch (type) {

            case 'string':
                // how to set data in the created component??
                component = StringComponent;
                break;

            //...
        }

        const childComponent = this.componentFactoryResolver.resolveComponentFactory(component);
        this.components.push(childComponent);
    }

    getComponentData() {
        this.components.forEach(component => {
            // how to access the data from each component??
        });
    }
}

app.component.html:

<div class="col-12" cdkDropList (cdkDropListDropped)="drop($event)">
  <div cdkDrag *ngFor="let cmp of components">
    <div class="row">
      <div class="col-10">
        <app-string *ngIf="cmp.selector == 'app-string'"></app-string>
        <!-- (...) -->
      </div>
      <div class="col-2 field-btn pt-4">
        <button type="button" mdbBtn color="danger" mdbWavesEffect>
          <mdb-icon fas icon="times"></mdb-icon>
        </button>
        <button cdkDragHandle type="button" class="move" mdbBtn color="info" mdbWavesEffect>
          <mdb-icon fas icon="arrows-alt"></mdb-icon>
        </button>
      </div>
    </div>
  </div>
</div>

string.component.ts:

export class StringComponent implements OnInit {

  item = new Item();

  constructor() { }

  ngOnInit() {
  }
}

string.component.html:

<div class="form-row mb-3">
  <div class="form-group col-12 col-md-6">
    <label for="name">Field Name</label>
    <input mdbInput type="text" [(ngModel)]="item.value" class="form-control" id="name" placeholder="Field Name" (keyup)="onInputValueChange($event.target.value)">
  </div>

  <div class="form-group col-12 col-md-3">
    <label for="identifier">Identifier</label>
    <input mdbInput type="text" [(ngModel)]="item.id" class="form-control" id="identifier" placeholder="Autogenerated ID" disabled>
  </div>

  <div class="form-group col-12 col-md-3">
      <label for="type">Type</label>
      <input mdbInput type="text" class="form-control" id="type" placeholder="STRING" disabled>
    </div>
</div>

动态添加的组件列表结果:

我没有使用 ng-template 添加组件,因为我可以将它们拖放到父组件的 cdkDropList 容器中。

我想要实现的是在将组件添加到列表之前设置属性“item.type”的值,并能够在我填充它们的输入后获取每个组件的“item”属性。

设置和获取组件信息的最佳方法是什么?

更新:感谢@kari 的解决方案,我设法解决了我的问题。 结果如下:

【问题讨论】:

    标签: angular angular-dynamic-components


    【解决方案1】:

    我举例说明了如何使用@Input()@Output() 从动态组件中传递和检索数据:https://stackblitz.com/edit/angular-z6wssp

    我认为它会按照您想要的方式工作。

    我基本上建议你将组件数据都推送到你的组件数组中:

        compAndData.component = childComponent;
        compAndData.data = data;
        this.components.push(compAndData);
    

    然后将数据传递给组件中的@Input() 变量,并通过EventEmitterOutput() 检索更改:

    <app-string [data]="cmp.data" (changedData)="onCompDataChanged($event)" *ngIf="cmp.component.selector === 'app-string'"></app-string>
    

    尝试示例:更改字段名称,单击 GetComponentData 按钮并在控制台中检查检索到的数据。

    【讨论】:

    • 嗨@Kari,谢谢你的好建议和例子!我已经对其进行了测试,并且工作顺利。用结果更新了我的问题:)
    猜你喜欢
    • 1970-01-01
    • 2018-10-04
    • 2021-01-24
    • 2015-10-15
    • 1970-01-01
    • 2020-01-31
    • 2019-12-06
    • 2018-01-17
    • 2021-04-10
    相关资源
    最近更新 更多