BŁĄD Błąd: brak metody dostępu do wartości dla formantu formularza z nieokreślonym atrybutem nazwy na przełączniku

104

Oto mój komponent w Angular 4:

@Component( {
    selector: 'input-extra-field',
    template: `
            <div class="form-group" [formGroup]="formGroup" >
                <switch [attr.title]="field.etiquette" 
                    [attr.value]="field.valeur" [(ngModel)]="field.valeur"
                    [formControl]="fieldControl" [attr.id]="name" [attr.disabled]="disabled">
                </switch>
                <error-messages [control]="name"></error-messages>
            </div>
    `
} )

Oto moja klasa:

export class SwitchExtraField extends ExtraField {
    @Input() field: ExtraFormField;
    @Input() entity: { fields: Object };
    @Input() formGroup: FormGroup;

    constructor( formDir: NgForm ) {
        super( null, null, formDir );
    }

    get disabled(): string {
        if ( this.field && !!this.field.saisissable && !this.field.saisissable )     {
            return 'disabled';
        }
        return null;
    }
}

Oto błąd, który otrzymuję podczas kompilacji:

ERROR Error: No value accessor for form control with unspecified name attribute
    at _throwError (forms.es5.js:1918)
    at setUpControl (forms.es5.js:1828)
    at FormControlDirective.webpackJsonp.../../../forms/@angular/forms.es5.js.FormControlDirective.ngOnChanges (forms.es5.js:4617)

Kiedy zmieniam przełącznik elementu na wejście, to działa, wiedząc, że używam tej samej struktury do innych komponentów i działa dobrze.

Pozwać
źródło
To prawdopodobnie może ci pomóc: stackoverflow.com/questions/46708080/…
Dinistro

Odpowiedzi:

156

Naprawiłem ten błąd, dodając name="fieldName" ngDefaultControlatrybuty do elementu, który zawiera [(ngModel)]atrybut.

Pierre-Alexis Ciavaldini
źródło
34
Pewne dodatkowe wyjaśnienie uczyniłoby to lepszą odpowiedzią. Gdzie ngDefaultControlna przykład znalazłeś dokumentację ?
isherwood,
16
Myślę, że name="fieldname"nie jest to konieczne, ale ngDefaultControlrozwiązuje problem.
michaeak
6
Więcej wyjaśnień znajduje się tutaj. stackoverflow.com/questions/46465891/…
Jestem nidhin
Dodanie „ngDefaultControl” (w atrybucie z dyrektywą * ngFor) rozwiązało mój podobny problem.
Davidson Lima
2
dla mnie naprawiłem to, importując pakiet modułów dla elementu używanego w grupie formularzy (np. AngularEditorModule) w celu rozpoznania kontrolki w szablonie i ngDefaultControl będzie mieć do niego dostęp. Odkryłem to podczas testowania jednostkowego.
aj idź
101

Miałem ten sam problem, a problem polegał na tym, że mój komponent podrzędny miał @inputnazwany formControl.

Musiałem więc tylko zmienić:

<my-component [formControl]="formControl"><my-component/>

do:

<my-component [control]="control"><my-component/>

ts:

@Input()
control:FormControl;
Eduardo Vargas
źródło
1
Działa z Angular 10, jak powiedziano w poprzednim komentarzu, naprawdę trudno jest go wyśledzić, jednak później ma sens, aby „formControl” nie było używane jako składnik @Input nazwa właściwości z powodu potencjalnego konfliktu przestrzeni nazw innym rozwiązaniem nazewnictwa może być zmiana nazwy pola _formControl, które jest zasilane przez wystąpienie FormControl.
Thomas
41

Otrzymałem również ten błąd podczas pisania niestandardowego komponentu kontroli formularza w Angular 7. Jednak żadna z odpowiedzi nie ma zastosowania do Angular 7.

W moim przypadku do @Componentdekoratora należało dodać :

  providers: [
    {
      provide: NG_VALUE_ACCESSOR,
      useExisting: forwardRef(() => MyCustomComponent),  // replace name as appropriate
      multi: true
    }
  ]

To jest przypadek „Nie wiem, dlaczego to działa, ale działa”. Określić to kiepskim projektem / wdrożeniem ze strony Angulara.

theMayer
źródło
6
Ten fragment kodu informuje warstwę iniekcji zależności Angulara, że ​​klasa powinna zostać zwrócona, gdy inne klasy (np. Dyrektywa formControlName) proszą ją o token NG_VALUE_ACCESSOR. Bez tego, angular nie miałby możliwości dowiedzenia się, że twoja klasa jest niestandardową kontrolką formularza (wszystkie informacje o interfejsach itp. Są usuwane podczas transpilacji)
Max Mumford
20

Miałem też ten sam błąd, kątowy 7

 <button (click)="Addcity(city.name)" [(ngModel)]="city.name"  class="dropdown-item fontstyle"
     *ngFor="let city of Cities; let i = index">
      {{city.name}}
 </button>

Właśnie dodałem ngDefaultControl

   <button (click)="Addcity(city.name)" [(ngModel)]="city.name"  ngDefaultControl class="dropdown-item fontstyle"
 *ngFor="let city of Cities; let i = index">
  {{city.name}}

Nadeem Qasmi
źródło
8

Miałem ten sam błąd - przypadkowo przywiązałem [(ngModel)] do mojego mat-form-fieldzamiast inputelementu.

Chris Fremgen
źródło
7

Otrzymałem ten komunikat o błędzie w moich testach jednostkowych z Jasmine. Dodałem ngDefaultControl atrybut elementu niestandardowego (w moim przypadku to był kanciasty materiał przełącznik suwakowy) i to rozwiąże problem.

<mat-slide-toggle formControlName="extraCheese">
  Extra Cheese
</mat-slide-toggle>

Zmień powyższy element, aby zawierał atrybut ngDefaultControl

<mat-slide-toggle ngDefaultControl formControlName="extraCheese">
 Extra Cheese
</mat-slide-toggle>
Sudharshan
źródło
6

Napotkałem ten błąd podczas uruchamiania przypadków Karma Unit Test Dodanie MatSelectModule w imporcie rozwiązuje problem

imports: [
        HttpClientTestingModule,
        FormsModule,
        MatTableModule,
        MatSelectModule,
        NoopAnimationsModule
      ],
Dan Patil
źródło
Tylko jeśli masz zainstalowany „Angular Material”, w przeciwnym razie nie potrzebujesz tego.
Mikefox2k
6

To trochę głupie, ale otrzymałem ten komunikat o błędzie przez przypadkowe użycie [formControl]zamiast [formGroup]. Spójrz tutaj:

ŹLE

@Component({
  selector: 'app-application-purpose',
  template: `
    <div [formControl]="formGroup"> <!-- '[formControl]' IS THE WRONG ATTRIBUTE -->
      <input formControlName="formGroupProperty" />
    </div>
  `
})
export class MyComponent implements OnInit {
  formGroup: FormGroup

  constructor(
    private formBuilder: FormBuilder
  ) { }

  ngOnInit() {
    this.formGroup = this.formBuilder.group({
      formGroupProperty: ''
    })
  }
}

DOBRZE

@Component({
  selector: 'app-application-purpose',
  template: `
    <div [formGroup]="formGroup"> <!-- '[formGroup]' IS THE RIGHT ATTRIBUTE -->
      <input formControlName="formGroupProperty" />
    </div>
  `
})
export class MyComponent implements OnInit {
  formGroup: FormGroup

  constructor(
    private formBuilder: FormBuilder
  ) { }

  ngOnInit() {
    this.formGroup = this.formBuilder.group({
      formGroupProperty: ''
    })
  }
}
Trevor
źródło
5

W moim przypadku wstawiłem [(ngModel)] na etykiecie, a nie na wejściu. Jest też zastrzeżenie, próbowałem uruchomić poprawnie powyższy błąd we wskazanym wierszu, ale błąd nie zniknął. Jeśli są inne miejsca, w których popełniłeś ten sam błąd, nadal rzuca ci ten sam błąd w tej samej linii

Nishanth Subramanya
źródło
1
To jest dobra odpowiedź. Niektóre komponenty (select, radio, itp.) Możesz poślizgnąć się i przykleić ngModel w złym miejscu. Komunikat o błędzie niewiele pomaga.
AndrewBenjamin,
3

W moim przypadku użyłem dyrektywy, ale nie zaimportowałem jej do mojego pliku module.ts. Import naprawił to.

Andris
źródło
Dzięki, ale musiałem też zrestartować, ng serveaby odświeżyć import
FindOutIslamNow
2

Miałem ten sam błąd, miałem pole wejściowe nazwane controlw moim niestandardowym komponencie formularza, ale przypadkowo przekazałem kontrolę w danych wejściowych o nazwie formControl. Mam nadzieję, że nikt nie napotka tego problemu.

Nikhil Arora
źródło
2

W moim przypadku było to tak głupie, jak zarejestrowanie nowego komponentu dla DI w moich app.module.tsdeklaracjach, ale nie w eksporcie.

Wikooo
źródło
2

W moim przypadku dzieje się to w moim udostępnionym module i musiałem dodać do @NgModule:

...
  imports: [
    CommonModule,
    FormsModule,
    ReactiveFormsModule,
    IonicModule
  ],
...
Pei
źródło
2

Otrzymałem również ten błąd, gdy nazwałem jeden z moich danych wejściowych komponentu „formControl”. Prawdopodobnie jest zarezerwowany na coś innego. Jeśli chcesz przekazać obiekt FormControl między komponentami, użyj go w ten sposób:

@Input() control: FormControl;

nie tak jak to:

@Input() formControl: FormControl;

Dziwne - ale działa :)

Paweł
źródło
0

Miałem ten sam błąd, ale w moim przypadku najwyraźniej był to problem z synchronizacją, w momencie renderowania komponentów html.

Postępowałem zgodnie z niektórymi rozwiązaniami zaproponowanymi na tej stronie, ale którekolwiek z nich zadziałało, przynajmniej nie do końca.

To, co faktycznie rozwiązało mój błąd, to napisanie poniższego fragmentu kodu wewnątrz tagu ojca html elementów.

Byłem związany ze zmienną.

Kod:

    *ngIf="variable-name"

Błąd był spowodowany najwyraźniej próbą wyrenderowania strony przez projekt, najwyraźniej w momencie oceny zmiennej projekt po prostu nie mógł znaleźć jej wartości. Dzięki powyższemu fragmentowi kodu upewnij się, że przed wyrenderowaniem strony zapytasz, czy zmienna została zainicjowana.

To jest mój kod component.ts:

import { Component, OnInit } from '@angular/core';
import { InvitationService } from 'src/app/service/invitation.service';
import { BusinessService } from 'src/app/service/business.service';
import { Invitation } from 'src/app/_models/invitation';
import { forEach } from '@angular/router/src/utils/collection';

@Component({
  selector: 'app-invitation-details',
  templateUrl: './invitation-details.component.html',
  styleUrls: ['./invitation-details.component.scss']
})
export class InvitationDetailsComponent implements OnInit {
  invitationsList: any;
  currentInvitation: any;
  business: any;
  invitationId: number;
  invitation: Invitation;

  constructor(private InvitationService: InvitationService, private BusinessService: 
BusinessService) { 
this.invitationId = 1; //prueba temporal con invitacion 1
this.getInvitations();
this.getInvitationById(this.invitationId);
  }

   ngOnInit() {

  }

  getInvitations() {
    this.InvitationService.getAllInvitation().subscribe(result => {
      this.invitationsList = result;
      console.log(result);
    }, error => {
      console.log(JSON.stringify(error));
    });
  }

  getInvitationById(invitationId:number){
    this.InvitationService.getInvitationById(invitationId).subscribe(result => {
      this.currentInvitation = result;
      console.log(result);
      //this.business=this.currentInvitation['business'];
       //console.log(this.currentInvitation['business']); 
     }, error => {
     console.log(JSON.stringify(error));
    });
  }
      ...

Oto moje znaczniki HTML:

<div class="container-fluid mt--7">
  <div class="row">
    <div class="container col-xl-10 col-lg-8">
      <div class="card card-stats ">
        <div class="card-body container-fluid form-check-inline" 
         *ngIf="currentInvitation">
          <div class="col-4">
             ...

Mam nadzieję, że to może być pomocne.

NUKE
źródło
ten link ma podobny problem :, stackoverflow.com/q/49409674/8992452 być może pomoże w rozwiązaniu problemu
NUKE
0

Czy próbowałeś przenieść swój plik [(ngModel)]do divzamiast switchw HTML? W moim kodzie pojawił się ten sam błąd, ponieważ powiązałem model z a <mat-option>zamiast a <mat-select>. Chociaż nie używam kontroli formularzy.

mneumann
źródło
0

W moim przypadku był to element component.member, który nie istniał np

[formControl]="personId"

Dodanie go do deklaracji klasy naprawiło to

this.personId = new FormControl(...)
Stefan Michev
źródło
0

W moim przypadku błąd został wywołany przez zduplikowanie importu komponentu w module.

Aleks Grunwald
źródło
0

#Tło

  • NativeScript 6.0

W moim przypadku błąd został wywołany przez zmianę tagu elementu z na błąd. Wewnątrz <TextView an [(ngModel)] = "nazwa". została zdefiniowana.

Po usunięciu błędu [(ngModel)] = "nazwa" zniknął.

Chris S.
źródło
0

Miałem do czynienia z tym problemem podczas przeprowadzania testów jednostkowych. Aby to naprawić, dodałem MatSlideToggleModule do importu w moim pliku spect.ts.

Jadamae77
źródło
-1

w moim przypadku miałem <TEXTAREA>tag ze starego html podczas konwersji na kątowy. Musiałem się zmienić <textarea>.

Feng Zhang
źródło
Nie głosowałem przeciw, ale to NIGDY nie powinno być przyczyną.
FindOutIslamNow
-1

Ten błąd występuje również, jeśli spróbujesz dodać ngModel do elementów innych niż wejściowe, takich jak opcje menu rozwijanego lub przycisku radiowego. W moim przypadku dodałem ngModel do opcji ion-select zamiast ion-select.

Santhosh Sandy
źródło