Angular 2 two way binding using ngModel is not working
Asked Answered
B

15

123

Can't bind to 'ngModel' since it isn't a know property of the 'input' element and there are no matching directives with a corresponding property

Note: im using alpha.31

import { Component, View, bootstrap } from 'angular2/angular2'

@Component({
    selector: 'data-bind'
})
@View({
    template:`
        <input id="name" type="text" 
            [ng-model]="name" 
            (ng-model)="name = $event" />
        {{ name }}
    ` 
})
class DataBinding { 
    name: string;

    constructor(){
        this.name = 'Jose';
    }
}

bootstrap(DataBinding);
Bayonet answered 25/7, 2015 at 7:1 Comment(0)
R
185

Angular has released its final version on 15th of September. Unlike Angular 1 you can use ngModel directive in Angular 2 for two way data binding, but you need write it in a bit different way like [(ngModel)] (Banana in a box syntax). Almost all angular2 core directives doesn't support kebab-case now instead you should use camelCase.

Now ngModel directive belongs to FormsModule, that's why you should import the FormsModule from @angular/forms module inside imports metadata option of AppModule(NgModule). Thereafter you can use ngModel directive inside on your page.

app/app.component.ts

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

@Component({
  selector: 'my-app',
  template: `<h1>My First Angular 2 App</h1>
    <input type="text" [(ngModel)]="myModel"/>
    {{myModel}}
  `
})
export class AppComponent { 
  myModel: any;
}

app/app.module.ts

import { NgModule }      from '@angular/core';
import { BrowserModule } from '@angular/platform-browser';
import { FormsModule } from '@angular/forms';
import { AppComponent }   from './app.component';

@NgModule({
  imports:      [ BrowserModule, FormsModule ], //< added FormsModule here
  declarations: [ AppComponent ],
  bootstrap:    [ AppComponent ]
})

export class AppModule { }

app/main.ts

import { platformBrowserDynamic } from '@angular/platform-browser-dynamic';
import { AppModule } from './app.module';

const platform = platformBrowserDynamic();
platform.bootstrapModule(AppModule);

Demo Plunkr

Rondon answered 25/7, 2015 at 9:8 Comment(1)
Thank you for Banana in a box syntax - now I'll never forget which one goes on the outside!Bick
T
57

Key Points:

  1. ngModel in angular2 is valid only if the FormsModule is available as a part of your AppModule.

  2. ng-model is syntatically wrong.

  3. square braces [..] refers to the property binding.
  4. circle braces (..) refers to the event binding.
  5. when square and circle braces are put together as [(..)] refers two way binding, commonly called banana box.

So, to fix your error.

Step 1: Importing FormsModule

import {FormsModule} from '@angular/forms'

Step 2: Add it to imports array of your AppModule as

imports :[ ... , FormsModule ]

Step 3: Change ng-model as ngModel with banana boxes as

 <input id="name" type="text" [(ngModel)]="name" />

Note: Also, you can handle the two way databinding separately as well as below

<input id="name" type="text" [ngModel]="name" (ngModelChange)="valueChange($event)"/>

valueChange(value){

}
Touching answered 4/3, 2017 at 20:14 Comment(0)
D
35

In my case, I was missing a "name" attribute on my input element.

Dibranchiate answered 29/11, 2019 at 0:41 Comment(2)
Good lord!! Thanks.Laurencelaurene
This was my problem tooDogie
B
9

As per Angular2 final, you do not even have to import FORM_DIRECTIVES as suggested above by many. However, the syntax has been changed as kebab-case was dropped for the betterment.

Just replace ng-model with ngModel and wrap it in a box of bananas. But you have spilt the code into two files now:

app.ts:

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

@Component({
  selector: 'ng-app',
  template: `
    <input id="name" type="text" [(ngModel)]="name"  />
    {{ name }}
  `
})
export class DataBindingComponent {
  name: string;

  constructor() {
    this.name = 'Jose';
  }
}

app.module.ts:

import { NgModule } from '@angular/core';
import { FormsModule } from '@angular/forms';
import { BrowserModule } from '@angular/platform-browser';
import { platformBrowserDynamic } from '@angular/platform-browser-dynamic';
import { DataBindingComponent } from './app'; //app.ts above

@NgModule({
  declarations: [DataBindingComponent],
  imports:      [BrowserModule, FormsModule],
  bootstrap:    [DataBindingComponent]
})
export default class MyAppModule {}

platformBrowserDynamic().bootstrapModule(MyAppModule);
Bernal answered 7/2, 2016 at 8:59 Comment(0)
D
8

The answer that helped me: The directive [(ngModel)]= not working anymore in rc5

To sum it up: input fields now require property name in the form.

Desmonddesmoulins answered 23/1, 2017 at 12:34 Comment(2)
Yes, I had the same problem. I put the name attribute in input and workedSosna
what the actual heck? why does it even need that attribute? this was the most unexpected solution for me.Poodle
E
8

Note : To allow the ngModel exists Independently inside reactive form, we have to use ngModelOptions as follows:

 [ngModelOptions]="{ standalone: true }"

For Example :

 <mat-form-field appearance="outline" class="w-100">
            <input
              matInput 
              [(ngModel)]="accountType"
              [ngModelOptions]="{ standalone: true }"
            />
 </mat-form-field>
Electro answered 12/2, 2021 at 7:28 Comment(0)
B
4

In the app.module.ts

import { FormsModule } from '@angular/forms';

Later in the @NgModule decorator's import:

@NgModule({
imports: [
BrowserModule,
FormsModule
]

})
Broyles answered 10/4, 2017 at 15:57 Comment(0)
R
3

Angular 2 Beta

This answer is for those who use Javascript for angularJS v.2.0 Beta.

To use ngModel in your view you should tell the angular's compiler that you are using a directive called ngModel.

How?

To use ngModel there are two libraries in angular2 Beta, and they are ng.common.FORM_DIRECTIVES and ng.common.NgModel.

Actually ng.common.FORM_DIRECTIVES is nothing but group of directives which are useful when you are creating a form. It includes NgModel directive also.

app.myApp = ng.core.Component({
    selector: 'my-app',
    templateUrl: 'App/Pages/myApp.html',
    directives: [ng.common.NgModel] // specify all your directives here
}).Class({
    constructor: function () {
        this.myVar = {};
        this.myVar.text = "Testing";
    },

});
Representational answered 19/1, 2016 at 4:6 Comment(2)
FYI NgModel is in FORM_DIRECTIVES, so you could also: directives: [ng.common.FORM_DIRECTIVES]Doone
@PeterJ.Hart, Actually ng.common.NgModel contains the defenition for the directive ngModel. ng.common.FORM_DIRECTIVES is grouping some directive's including ngModel which are useful if forms. So we don't want to include each and every directive's for the form just include ng.common.FORM_DIRECTIVESRepresentational
C
2

These things are missing/ Wrong:

  • Import FormsModule in imports array of module (ngModel requires FormsModule)
  • ngModel is written as: [(ngModel)]="modelName"

This way, It will work fine!

Cognition answered 16/6, 2021 at 11:24 Comment(0)
S
1

For newer versions of Angular:

  1. -write it as [(ngModel)] = yourSearch

  2. declare a empty variable(property) named as yourSearch in .ts file

  3. add FormsModule in app.module.ts file from - @angular/forms;

  4. if your application is running, then restart it as you made changes in its module.ts file

Sour answered 30/11, 2020 at 7:39 Comment(0)
S
1

if you are using lazy loading module, you need to import ngModule and formModule in the current module. example:

//shared.module.ts
import { NgModule } from '@angular/core';
import {FormsModule} from '@angular/forms'

imports: [
    FormsModule,]
Stallworth answered 7/10, 2021 at 21:57 Comment(0)
E
0

instead of ng-model you can use this code:

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

@Component({
  selector: 'my-app',
  template: `<input #box (keyup)="0">
    <p>{{box.value}}</p>`,
})
export class AppComponent  {}

inside your app.component.ts

Ensilage answered 7/2, 2017 at 9:30 Comment(0)
P
0

Add below code to following files.

app.component.ts

<input type="text" [(ngModel)]="fname" >
{{fname}}
export class appcomponent {
fname:any;
}

app.module.ts

import {FormsModule} from '@angular/forms';
@NgModule({
imports: [ BrowserModule,FormsModule ],
declarations: [ AppComponent],
bootstrap:    [ AppComponent ]
})

Hope this helps

Publicize answered 9/10, 2018 at 8:40 Comment(0)
F
0

import FormsModule in your AppModule to work with two way binding [(ngModel)] with your

Foreland answered 12/5, 2020 at 8:16 Comment(1)
When possible, please make an effort to provide additional explanation instead of just code. Such answers tend to be more useful as they help members of the community and especially new developers better understand the reasoning of the solution, and can help prevent the need to address follow-up questions.Omniumgatherum
S
0

Adding a name property solved the problem for me

Stabilizer answered 31/1, 2023 at 19:51 Comment(1)
Your answer could be improved with additional supporting information. Please edit to add further details, such as citations or documentation, so that others can confirm that your answer is correct. You can find more information on how to write good answers in the help center.Selwin

© 2022 - 2024 — McMap. All rights reserved.