Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Angular Material Date Picker cannot be dynamically named

I am generating a form dynamically and I need to name my controls according to the model.

I am working with Angular 5 and Angular-Material 5.

However, I am unable to name the date picker (Mat-DatePicker) dynamically as I get the following error.

InstrumentSearchComponent.html:27 ERROR TypeError: this._datepicker._registerInput is not a function

This is how I tried to create my control with dynamic name which resulted in the above error.

 <mat-form-field>
                        <input matInput [matDatepicker]="dynamicName" placeholder="{{ dynamicLabel }}">
                        <mat-datepicker-toggle matSuffix [for]="dynamicName"></mat-datepicker-toggle>
                        <mat-datepicker #{{dynamicName}}></mat-datepicker>
                    </mat-form-field>

Both dynamicName and dynamicLabel defined in the associated TS file and coming from the model I defined for the fields.

If I remove the dynamic names and replace them all with static names such as datePicker1 or picker1 then it all works but I am then struggling to combine the statically named control and bind it to my model.

example of statically named control which works.

 <mat-form-field>
                        <input matInput [matDatepicker]="picker" placeholder="{{ dynamicLabel }}">
                        <mat-datepicker-toggle matSuffix [for]="picker"></mat-datepicker-toggle>
                        <mat-datepicker #picker></mat-datepicker>
                    </mat-form-field>

Any suggestions guys? Thanks

like image 630
Robert Dinaro Avatar asked Feb 18 '18 17:02

Robert Dinaro


1 Answers

When one assigns #identifier to a particular element in the angular template, one is simply creating a local variable with that name. Hence it wont matter even if you use the same name as the scope of it is just limited for that loop cycle.

Assuming you are creating a form dynamically based on some data in an array formData

formData = [
    {
       id=0,
       type="date-picker",
       label= "label 1"
    }, 
    ...
]

Below code should do your job in this case.

<mat-form-field *ngFor="let field of formData">
    <input matInput [matDatepicker]="picker" placeholder="{{ field.Label }}">
    <mat-datepicker-toggle matSuffix [for]="picker"></mat-datepicker-toggle>
    <mat-datepicker #picker></mat-datepicker>
</mat-form-field>

As each loop runs #picker is reinitialised with new input element which inturn is passed to [matDatepicker]

This is same as reinitialising a variable in a for loop.

for(let i = 0; i < formData.length ; i++ ){

    // assume <mat-datepicker #picker></mat-datepicker> similar to below line of code.

    let picker = document.createElement("INPUT");
}
like image 92
Naresh Pingale Avatar answered Oct 14 '22 11:10

Naresh Pingale