首页 文章

如何在模板驱动器Angular表单中消除'No value accessor for form control'

提问于
浏览
0

我在https://angular.io/api/forms/NgModelGroup使用官方发布的文档示例代码

虽然我发现我仍然有没有使用ngModelGroup指令的问题

form.component.ts

import {Component} from '@angular/core';
import {NgForm} from '@angular/forms';

@Component({
 selector: 'example-app',

template: `
<form #f="ngForm" (ngSubmit)="onSubmit(f)">
  <p *ngIf="nameCtrl.invalid">Name is invalid.</p>

  <div ngModelGroup="name" #nameCtrl="ngModelGroup">
    <input name="first" [ngModel]="name.first" minlength="2">
    <input name="last" [ngModel]="name.last" required>
  </div>

  <input name="email" ngModel> 
  <button>Submit</button>
</form>

<button (click)="setValue()">Set value</button>
`,
})
export class FormComponent {
name = {first: 'Nancy', last: 'Drew'};

onSubmit(f: NgForm) {
console.log(f.value);  // {name: {first: 'Nancy', last: 'Drew'}, email: ''}
console.log(f.valid);  // true
}

setValue() { this.name = {first: 'Bess', last: 'Marvin'}; }
}

app.module.ts

import { BrowserModule } from '@angular/platform-browser';
import { NgModule } from '@angular/core';
import { NgForm, NgModelGroup, NgModel } from '@angular/forms';
import { AppComponent } from './app.component';
import { FormComponent } from './form/form.component';


@NgModule({
declarations: [
AppComponent,
FormComponent,
NgForm,NgModelGroup,NgModel

],
imports: [
BrowserModule,
],
providers: [],
bootstrap: [AppComponent]
})
export class AppModule { }

app.component.html <example-app></example-app>

并在控制台中收到此错误:未捕获(在承诺中):错误:

错误错误:未捕获(在承诺中):错误:没有带路径的表单控件的值访问器:'name - > first'错误:没有用于路径的表单控件的值访问器:'name - > first'at _throwError(forms.es5 .js:1918)at setUpControl(forms.es5.js:1828)at forms.es5.js:3955 at ZoneDelegate.webpackJsonp ... / .. / .. / .. / zone.js / dist / zone.js位于ZoneDelegate.webpackJsonp的Object.onInvoke(core.es5.js:3890)的.ZoneDelegate.invoke(zone.js:392)... / .. / .. / .. / zone.js / dist / zone.js .ZoneDelegate.invoke(zone.js:391)在Zone.webpackJsonp ... / .. / .. / .. / zone.js / dist / zone.js.Zone.run(zone.js:142)at zone .js:844 at ZoneDelegate.webpackJsonp ... / .. / .. / .. / zone.js / dist / zone.js.ZoneDelegate.invokeTask(zone.js:425)at Object.onInvokeTask(core.es5 . js:3881)在_throwError(forms.es5.js:1918)at setUpControl(forms.es5.js:1828)at forms.es5.js:3955 at ZoneDelegate.webpackJsonp ... / .. / .. / .. /zone.js/dist/zone.js.ZoneDelegate.invoke(zone.js:392)位于ZoneDelegate.webpackJsonp的Object.onInvoke(core.es5.js:3890)... / .. / .. / .. / Z Zone.webpackJsonp中的one.js / dist / zone.js.ZoneDelegate.invoke(zone.js:391)... / .. / .. / .. / zone.js / dist / zone.js.Zone.run zone.js上的(zone.js:142):ZoneDelegate.webpackJsonp中的844 ... / .. / .. / .. / zone.js / dist / zone.js.ZoneDelegate.invokeTask(zone.js:425)在Object.onInvokeTask(core.es5.js:3881)at zonePrise(zone.js:795)at zone.js:847 at ZoneDelegate.webpackJsonp ... / .. / .. / .. / zone.js / dist /zone.js.ZoneDelegate.invokeTask(zone.js:425)位于ZoneDelegate.webpackJsonp的Object.onInvokeTask(core.es5.js:3881)... / .. / .. / .. / zone.js / dist Zone.webpackJsonp中的/zone.js.ZoneDelegate.invokeTask(zone.js:424)... / .. / .. / .. / zone.js / dist / zone.js.Zone.runTask(zone.js: 192)在drainMicroTaskQueue(zone.js:602)at

@ angular / cli:1.3.2

节点:6.11.0

os:win32 x64

@ angular / animations:4.3.6

@ angular / common:4.3.6

@ angular / compiler:4.3.6

@ angular / core:4.3.6

@ angular / forms:4.3.6

@ angular / http:4.3.6

@ angular / platform-browser:4.3.6

@ angular / platform-browser-dynamic:4.3.6

@ angular / router:4.3.6

@ angular / cli:1.3.2

@ angular / compiler-cli:4.3.6

@ angular / language-service:4.3.6

2 回答

  • 0

    如果您要在自定义组件中使用NgForm,NgModel和其他此类内容,则需要将FormsModule导入到声明组件的NgModule中 . 顺便说一句,您的链接提供了您需要导入的模块名称(FormsModule) . 此外,您不需要分别声明指令NgForm,NgModelGroup和NgModel,因为它们已经在FormsModule中声明 .

    所以,你的模块应该是这样的:

    import { BrowserModule } from '@angular/platform-browser';
    import { NgModule } from '@angular/core';
    import { FormsModule } from '@angular/forms';
    import { AppComponent } from './app.component';
    import { FormComponent } from './form/form.component';
    
    @NgModule({
        declarations: [
            AppComponent,
            FormComponent
        ],
        imports: [
            BrowserModule,
            FormsModule // <-- this is what you need to do
        ],
        providers: [],
        bootstrap: [AppComponent]
    })
    export class AppModule { }
    

    Explanation of this exact error

    实际上,错误几乎是不言自明的 . 你需要提供一些实现ControlValueAccessor接口的东西(在你的特定情况下会使用DefaultValueAccessor),因为你把它放在输入 requires 它的NgModel上 . 实现ControlValueAccessor的类实际上是将值放在DOM元素中并处理来自它的用户输入 . 这是不同类型的DOM用户输入元素的角度抽象 - 单选按钮,复选框,文本输入和选择,仅举几例 . 因此,由于您没有提供任何实现此接口的内容(并使用NG_VALUE_ACCESSOR标记提供所述实现),因此角度注入器会因为这个原因而无法实例化NgModel . 但是如果您导入FormsModule,那么您将立即得到所有这些东西,因为这个模块提供了几个开箱即用的值访问器,没有额外的声明 .

  • 0

    将FormsModule添加到app.module.ts中的imports数组解决了这个问题:

    imports: [
        BrowserModule,
        FormsModule // <-- this is what you need to do
    ],
    

相关问题