角反应表单数组和表单组动态副本

时间:2018-12-23 14:31:32

标签: javascript angular typescript angular-reactive-forms

在我的角度应用程序中,我有一个“任务”对象数组。这就是我为其创建FormGroup的方式:

export class TasksComponents implements OnInit {
    loaded: boolean = false;
    form: FormGroup;
    taskTemplate: FormGroup;

    constructor(private api: ApiService, private fb: FormBuilder,
    private route: ActivatedRoute,) {

        this.taskTemplate = this.fb.group({
            uuid: [null],
            created: [null],
            modified: [null],
            process: [null],
            title: ['', [Validators.required]],
            time_value: ['', [Validators.required, Validators.min(1), Validators.max(1000)]],
            time_dir: ['BEFORE'],
            time_unit: ['DAYS'],
            // nested form array, you could also add a form group initially
            task_type: ['SEND_EMAIL'],
            config: this.emailTaskConfigTemplate
        });

    }

}

然后在我的ngOnInit中创建一个表单:

ngOnInit() {
    this.processForm = this.fb.group({
        uuid: [null],
        created: [null],
        modified: [null],
        author: [null],
        title: [''],
        tasks: this.fb.array([this.taskTemplate])
    });
}

我想允许用户动态添加新任务,所以我有一个方法:

addNewTask() {
    let control = <FormArray>this.processForm.controls.tasks;
    let cloned = _.cloneDeep(this.taskTemplate); //lodash's cloneDeep
    cloned.reset();
    control.push(cloned);
}

但是,它始终会添加新任务,并复制从第一个this.taskTemplate开始复制的所有字段。如果我使用lodash的cloneDeep并使用它创建新表单组,然后应用reset()方法,则该方法将重置所有任务,而不仅仅是新的任务。

如何创建一个空的FormGroup模板,然后直接推送它? 当然,我可以使用formGorup方法中的相同控件定义全新的addNewTask(),但这将违反DRY主体。

有没有更好的方法来实现这一目标?

1 个答案:

答案 0 :(得分:0)

您可以添加创建新FormGroup的辅助方法。

export class TasksComponents implements OnInit {
    loaded: boolean = false;
    form: FormGroup;

    constructor(private api: ApiService, private fb: FormBuilder,
            private route: ActivatedRoute,) { }

    private taskTemplate() {
        return this.fb.group({
            uuid: [null],
            created: [null],
            modified: [null],
            process: [null],
            title: ['', [Validators.required]],
            time_value: ['', [Validators.required, Validators.min(1), Validators.max(1000)]],
            time_dir: ['BEFORE'],
            time_unit: ['DAYS'],
            // nested form array, you could also add a form group initially
            task_type: ['SEND_EMAIL'],
            config: this.emailTaskConfigTemplate
        });
    }

    ngOnInit() {
        this.processForm = this.fb.group({
            uuid: [null],
            created: [null],
            modified: [null],
            author: [null],
            title: [''],
            tasks: this.fb.array([ this.taskTemplate() ]);
        });
    }

    addNewTask() {
        let control = <FormArray>this.processForm.controls.tasks;
        control.push(this.taskTemplate());
    }
}