Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Angular 7 Reactive forms "No value accessor for form control with unspecified name attribute"

I am using reactive forms and i seem to be having issues with what would seem random form fields. Any ideas as to why this is happening is apriciated.

I have just started using angular and material 7 if that helps

Interestingly enough adding and removing elements in the form causes issues with other elements.

ERROR Error: No value accessor for form control with unspecified name attribute

TS

export class VolunteerApplicationPersonalStepComponent implements OnInit 
{

  public readonly form: FormGroup;
    constructor(private fb: FormBuilder) {
        this.form = this.fb.group({
          businessTelephoneExt: [''],
          otherTelephone: [''],
          otherTelephoneExt: [''],
        });
      }
}

HTML

    <form [formGroup]="form">

     <mat-form-field>
        <input matInput i18n-placeholder placeholder="Business Extension"
               [formControl]="form.get('businessTelephoneExt')">
      </mat-form-field>

      <app-telephone-input i18n-placeholder placeholder="Other Telephone"
                           [formControl]="form.get('otherTelephone')">
      </app-telephone-input>

      <mat-form-field>
        <input matInput i18n-placeholder placeholder="Other Extension"
               [formControl]="form.get('otherTelephoneExt')">
      </mat-form-field>

      <br>

      <div class="group-margin group-min-width">
        <button mat-stroked-button color="primary" matStepperPrevious i18n>Previous</button>
        <button mat-raised-button color="primary" matStepperNext (click)="next()" i18n>Next</button>
      </div>
    </form>

enter image description here

as someone suggested .. formControlName="businessTelephoneExt"

enter image description here

App-Telephone Code (Note it used to have formControl NOT appFormControl)

export class TelephoneInputComponent implements OnInit {

  @Input() public required = false;
  @Input() public placeholder = '';
  @Input() public appFormControl: NgControl;

  constructor() {
  }

  public ngOnInit() {
  }
}



<mat-form-field>
  <input
    matInput
    type="tel"
    [required]="required"
    [placeholder]="placeholder"
    [formControl]="appFormControl">

  <mat-hint i18n>Please enter digits only</mat-hint>

  <mat-error
    *ngIf="appFormControl.hasError('phone')"
    i18n>Invalid phone (requires 10 digits)
  </mat-error>
</mat-form-field>
like image 398
Ricardo Saracino Avatar asked Dec 14 '18 16:12

Ricardo Saracino


People also ask

How do you resolve no value accessor for form control with name?

When you get the error No value accessor for form control with unspecified name attribute , there are generally two things that possibly has gone wrong: You are using ngModel with a third party control that doesn't register a NG_VALUE_ACCESSOR . In this case you need to use ngDefaultControl on the element.

What is Ng_value_accessor?

NG_VALUE_ACCESSORlinkUsed to provide a ControlValueAccessor for form controls.

What is ControlValueAccessor in angular?

Control Value Accessor is an interface that provides us the power to leverage the Angular forms API and create a communication between Angular Form API and the DOM element. It provides us many facilities in angular like we can create custom controls or custom component with the help of control value accessor interface.

What is the use of ngDefaultControl?

Third party controls require a ControlValueAccessor to function with angular forms. Many of them, like Polymer's <paper-input> , behave like the <input> native element and thus can use the DefaultValueAccessor . Adding an ngDefaultControl attribute will allow them to use that directive.


3 Answers

seems you cannot have a @Input() named formControl

like image 74
Ricardo Saracino Avatar answered Sep 19 '22 11:09

Ricardo Saracino


One little thing I see is this:

  <app-telephone-input i18n-placeholder placeholder="Other Telephone"
                       [formControl]="form.get('otherTelephone')">
  </app-telephone-input>

So it should be:

  <app-telephone-input i18n-placeholder placeholder="Other Telephone"
                       [appFormControl]="form.get('otherTelephone')">
  </app-telephone-input>

If you want to create a custom form controler you should implement ControlValueAccessor interface

ControlValueAccessor {
  writeValue(obj: any): void
  registerOnChange(fn: any): void
  registerOnTouched(fn: any): void
  ...
}

If you implement ControlValueAccessor interface only you can bind property formControl

like image 21
Indrakumara Avatar answered Sep 17 '22 11:09

Indrakumara


@ricardo's answer is not correct

You can have a @Input() named formControl when using the ControlValueAccessor interface, it is likely you have not added a NG_VALUE_ACCESSOR token to your providers. Something like:

export const VALUE_ACCESSOR: any = {
    provide: NG_VALUE_ACCESSOR,
    useExisting: forwardRef(() => MyComponent),
    multi: true,
};

@Component({
    selector: 'my-component',
    templateUrl: './my-component.component.html',
    styleUrls: ['./my-component.component.scss'],
    providers: [VALUE_ACCESSOR]
})
like image 30
Ben Taliadoros Avatar answered Sep 18 '22 11:09

Ben Taliadoros