Search code examples
angular6angular-formsangular-formbuilder

Dynamic Form Creation in angular 6


I am trying to get started with creating a dynamic form in Angular 2, and I am using the setup from the Angular documentation . I didn't have any issues with their setup, which just hard codes the data in the service as apposed to an api call. My issue is that when I try to use an api call the values my dynamic form creation is failing.

The data is coming in from the api call successfully. I believe my issue is that [questions] is binding before the data is ready. Can someone tell me a better way to do this or please provide any suggestions to what I'm doing wrong please? Is there a way I could set the properties in the api first?

Here below my approcah looks like :

TS FILE

 export class DynamicFormComponent implements OnInit {

 @Input() questions: QuestionBase<any>[] = [];
 form: FormGroup;
 payLoad = '';

 constructor(private qcs: QuestionControlService ,private dy :QuestionService) {  }

 ngOnInit() {
this.questions=this.dy.getDataFromService();
this.form = this.qcs.toFormGroup(this.questions);
 }

onSubmit() {
 this.payLoad = JSON.stringify(this.form.value);
 }
 }

HTML

    <div>
      <form (ngSubmit)="onSubmit()" [formGroup]="form" *ngIf="isFormReady">

        <div *ngFor="let question of questions" class="form-row">
         <app-question [question]="question" [form]="form"></app-question>
        </div>
        <div class="form-row">
         <button type="submit" [disabled]="!form.valid">Save</button>
        </div>
      </form>
     <div *ngIf="payLoad" class="form-row">
       <strong>Saved the following values</strong><br>{{payLoad}}
     </div>
   </div>
##QUESTIONSERVICE.TS

getDataFromService(){
let questions: QuestionBase<any>[]=[];
this.auth.dynamicFormData().subscribe(
    (result) => {
        let data=result;
        for(var i=0;i<data.length;i++){
            questions.push(new TextboxQuestion(data[i]));
        }

    }); 
return questions.sort((a, b) => a.order - b.order);
}
}

RESULT DATA FROM API IS

[{"value":"Sireesha_0","key":"firstName_0","label":"First Name_0","required":true,"order":1,"controlType":"text"},{"value":"Sireesha_1","key":"firstName_1","label":"First Name_1","required":true,"order":1,"controlType":"text"}]

ERRORS

An error occurred: Cannot read property 'valid' of undefined

Error encountered in Error Interceptors TypeError: Cannot read property 'valid' of undefined at DynamicFormQuestionComponent.get [as isValid] (dynamic-form-question.component.ts:13)


Solution

  • I have changed my code like below and it's working good.

    html

      <form (ngSubmit)="onSubmit()" [formGroup]="form" *ngIf="isFormReady">
    
        <div *ngFor="let question of questions" class="form-row">
         <app-question [question]="question" [form]="form"></app-question>
        </div>
        <div class="form-row">
         <button type="submit" [disabled]="!form.valid">Save</button>
        </div>
      </form>
    

    ts

     isFormReady:booelan;
    
    ngOnInit() {
      this.questions=this.dy.getDataFromService();
    }
    
    
    getDataFromService(){
      let questions: QuestionBase<any>[]=[];
      this.auth.dynamicFormData().subscribe(
      (result) => {
        let data=result;
        for(var i=0;i<data.length;i++){
            questions.push(new TextboxQuestion(data[i]));
        }
    
     }); 
      this.form = this.qcs.toFormGroup(this.questions);
      this.isFormReady=true;
    return questions.sort((a, b) => a.order - b.order);
     }