Dynamically set input values in form using FormBuilder

Hi,

I have a number of forms in my app that I need to pre-populate with values from when the user signed in or registered. I can get these values to show in the view by using value="{{first name}}" etc on each input, but I cannot get form builder to see these values when submitting the form. Any advice would be appreciated.

Maintenance.ts:

export class MaintenancePage {

 maintenance: any;
 complaint: any;
 userdata: any;
 development: any;
 unit_name: any;
 type: any;
 token: any;
 firstname: any;
 lastname: any;
 email: any;
 cell: any;
 development_id: any;

constructor(
public navCtrl: NavController, 
private formBuilder: FormBuilder,
public platform: Platform,
public actionsheetCtrl: ActionSheetController,
private userData: UserData,
private developmentService: DevelopmentService,
) {}

ionViewDidLoad() {
  this.getUserData();

  this.maintenance = this.formBuilder.group ({
    firstname: [this.userdata.firstname],
    lastname: [''],
    email: [''],
    cell: [''],
    development: [''],	
    complaint: ['', Validators.required],
    token: [this.userData.usertoken],
    type: ['maintenance'],
});
  console.log(this.maintenance.value);
}

getUserData() {
 this.userData.getUserData().then((userdata) => {
  this.userdata = userdata;
  this.firstname = userdata.firstname;
  this.lastname = userdata.lastname;
  this.email = userdata.email;
  this.cell = userdata.cell;
  this.unit_name = userdata.unit_name;
  this.loadDevelopments(userdata.development_id);
});
}

And Maintenance.html:

<ion-content id="maintenance-bg-img">
<ion-grid padding>
<form [formGroup]="maintenance" (ngSubmit)="maintenanceForm()">
  <ion-item class="item">
    <ion-label floating>First Name</ion-label>
    <ion-input type="text" formControlName="firstname" value="{{firstname}}" readonly></ion-input>
  </ion-item>
  <ion-item class="item">
    <ion-label floating>Last Name</ion-label>
    <ion-input type="text" formControlName="lastname"  value="{{lastname}}"></ion-input>
  </ion-item>
  <ion-item class="item">
    <ion-label floating>Email Addess</ion-label>
    <ion-input type="email" formControlName="email" value="{{email}}"></ion-input>
  </ion-item>
  <ion-item class="item">
    <ion-label floating>Cell Number</ion-label>
    <ion-input type="text" formControlName="cell" value="{{cell}}"></ion-input>
  </ion-item>
  <ion-item class="item">
    <ion-label floating>Address</ion-label>
    <ion-input type="text" formControlName="development"  value="Unit {{unit_name}}, {{development}}"></ion-input>
  </ion-item>
  <ion-item class="item">
    <ion-label floating>Complaint</ion-label>
    <ion-textarea type="text" formControlName="complaint"></ion-textarea>
  </ion-item>
  <ion-item class="hidden">
    <ion-textarea type="text" formControlName="token" value="{{token}}"></ion-textarea>
  </ion-item>
  <button ion-button color="dark" clear block type="submit" [disabled]="!maintenance.valid" id="maintenance-btn">Send your request</button>
  </form>

So, I can see the values I want in the form, but cannot get them passed into the form builder instance in order to post them to an external api. And when I try this.userdata.firstname it just returns inline template:11:7 caused by: formGroup expects a FormGroup instance. Please pass one in.

I too am curious about this. Did you ever find an answer?

Can you elaborate more on what your problem is, because OP has two totally different ones.

I was actually able to figure it out. I was (it seems) doing same thing as OP in order to get the values showing up in my form. I was using the value="{{name}} but my form was not recognizing that there was a value there. This caused my validator to say the field was not filled in–even though there was text pre-populated.

Did some more searching and found out that you can pre-populate input values when you’re creating the FormBuilder.group

so my non-working .ts code was:
this.form = formBuilder.group({ name: ["", Validators.required], ... //other form inputs });
and the input value population was in the HTML file

I now put
this.form = formBuilder.group({ name: [this.person.name, Validators.required], ... //other form inputs });

and all seems to be working as expected. So long story short, just had to move my pre-populating of the input value to the .ts file instead of in the HTML

Glad it’s working. OP didn’t have the proper defaults at the time the form is built, because they are coming in in a later-resolving promise. It’s possible to use setValue on the control at a later time to deal with that. OP’s other problem is direct access of children of the controls array from the template: that causes fits with the template compiler, and should be replaced by get().

this.maintenance.controls[“firstname”].setValue(this.firstname);
this.maintenance.setValidators(Validators.compose([Validators.required]));
this.maintenance.enable();

use of setValue() should resolve your problem.

Thanks, it’s work for me… :slight_smile:

@ksertronics it works, thank you!! :zombie:

setValue :+1:

this.myForm.controls.MYINPUT.setValue('new value');