99

I'm trying to use <mat-form-field> in an Angular project using Material2 but I've hit a wall.

Getting the error message below.

Uncaught Error: Template parse errors:
'mat-form-field' is not a known element:
1. If 'mat-form-field' is an Angular component, then verify that it is part of this module.
2. If 'mat-form-field' is a Web Component then add 'CUSTOM_ELEMENTS_SCHEMA' to the '@NgModule.schemas' of this component to suppress this message. ("[ERROR ->]<mat-form-field>
  <input matInput placeholder="Simple placeholder" required>
</mat-form-field>"): ng:///MaterialModule/SearchComponent.html@0:0
    at syntaxError (compiler.js:485)
    at TemplateParser.parse (compiler.js:24660)
    at JitCompiler._parseTemplate (compiler.js:34471)
    at JitCompiler._compileTemplate (compiler.js:34446)
    at eval (compiler.js:34347)
    at Set.forEach (<anonymous>)
    at JitCompiler._compileComponents (compiler.js:34347)
    at eval (compiler.js:34217)
    at Object.then (compiler.js:474)
    at JitCompiler._compileModuleAndComponents (compiler.js:34216)

This is my code I've got.

app.module.ts

import { BrowserModule } from '@angular/platform-browser';
import { NgModule, CUSTOM_ELEMENTS_SCHEMA } from '@angular/core';
import { FormGroup, FormControl, FormsModule, ReactiveFormsModule } from '@angular/forms';

import { HttpModule } from '@angular/http';
import { HttpClientModule } from '@angular/common/http';

import {
  MatButtonModule,
  MatFormFieldModule,
  MatInputModule,
  MatRippleModule
} from '@angular/material';
import { BrowserAnimationsModule } from '@angular/platform-browser/animations';

import { AppComponent } from './app.component';
import { YahooService } from './yahoo.service';
import { SearchComponent } from './search/search.component';

@NgModule({
  exports: [
    MatButtonModule,
    MatFormFieldModule,
    MatInputModule,
    MatRippleModule,
  ],
  declarations: [
    SearchComponent,
  ],
})
export class MaterialModule {};

@NgModule({
  declarations: [
    AppComponent
  ],
  imports: [
    MaterialModule,
    BrowserModule,
    BrowserAnimationsModule,
    FormsModule,
    HttpModule,
    HttpClientModule,
  ],
  providers: [
    YahooService,
  ],
  bootstrap: [
    AppComponent,
  ],
  schemas: [
    CUSTOM_ELEMENTS_SCHEMA,
  ],
})
export class AppModule { }

search.component.html

<mat-form-field>
   <input matInput placeholder="Simple placeholder" required>
</mat-form-field>

search.component.ts

import { Component, OnInit } from '@angular/core';
import { FormBuilder, FormGroup } from '@angular/forms';

@Component({
  selector: 'app-search',
  templateUrl: './search.component.html',
  styleUrls: ['./search.component.css']
})
export class SearchComponent implements OnInit {

  options: FormGroup;

  constructor(fb: FormBuilder) {
    this.options = fb.group({
      floatLabel: 'never',
    });
  }

  ngOnInit() {
  }

}

package.json

{
  "name": "forecast",
  "version": "0.0.0",
  "license": "MIT",
  "scripts": {
    "ng": "ng",
    "start": "ng serve",
    "build": "ng build",
    "test": "ng test",
    "lint": "ng lint",
    "e2e": "ng e2e"
  },
  "private": true,
  "dependencies": {
    "@angular-devkit/schematics": "0.0.40",
    "@angular/animations": "^5.1.3",
    "@angular/cdk": "^5.0.3",
    "@angular/common": "^5.1.3",
    "@angular/compiler": "^5.1.3",
    "@angular/core": "^5.1.3",
    "@angular/forms": "^5.1.3",
    "@angular/http": "^5.1.3",
    "@angular/material": "^5.0.3",
    "@angular/platform-browser": "^5.1.3",
    "@angular/platform-browser-dynamic": "^5.1.3",
    "@angular/router": "^5.1.3",
    "axios": "^0.17.1",
    "body-parser": "^1.18.2",
    "core-js": "^2.5.3",
    "express": "^4.16.2",
    "node-sass": "^4.7.2",
    "nodemon": "^1.14.7",
    "q": "^1.5.1",
    "rxjs": "^5.5.6",
    "zone.js": "^0.8.4"
  },
  "devDependencies": {
    "@angular/cli": "^1.6.3",
    "@angular/compiler-cli": "^5.1.3",
    "@types/jasmine": "2.5.38",
    "@types/node": "~6.0.60",
    "codelyzer": "~2.0.0",
    "jasmine-core": "~2.5.2",
    "jasmine-spec-reporter": "~3.2.0",
    "karma": "~1.4.1",
    "karma-chrome-launcher": "~2.0.0",
    "karma-cli": "~1.0.1",
    "karma-coverage-istanbul-reporter": "^0.2.0",
    "karma-jasmine": "~1.1.0",
    "karma-jasmine-html-reporter": "^0.2.2",
    "protractor": "~5.1.0",
    "ts-node": "~2.0.0",
    "tslint": "~4.5.0",
    "typescript": "~2.4.0"
  }
}
MathMax
  • 571
  • 7
  • 22

11 Answers11

136

You're only exporting it in your NgModule, you need to import it too

@NgModule({
  imports: [
    MatButtonModule,
    MatFormFieldModule,
    MatInputModule,
    MatRippleModule,
 ]
  exports: [
    MatButtonModule,
    MatFormFieldModule,
    MatInputModule,
    MatRippleModule,
  ],
  declarations: [
    SearchComponent,
  ],
})export class MaterialModule {};

better yet

const modules = [
        MatButtonModule,
        MatFormFieldModule,
        MatInputModule,
        MatRippleModule
];

@NgModule({
  imports: [...modules],
  exports: [...modules]
  ,
})export class MaterialModule {};

update

You're declaring component (SearchComponent) depending on Angular Material before all Angular dependency are imported

Like BrowserAnimationsModule

Try moving it to MaterialModule, or before it

Iancovici
  • 5,574
  • 7
  • 39
  • 57
  • 1
    But, as far as I know, listing a module in `exports` does automatically import it into the module, as to avoid repeating code – Armen Vardanyan Jan 04 '18 at 17:16
  • 1
    @ArmenVardanyan Exporting from e.g. Module A makes it available to *other* modules that import Module A but not to Module A itself - It needs to import it too. – Kirk Larkin Jan 04 '18 at 17:43
  • 1
    @iancovici If I try to set up the `const modules` array, I get an error "cannot find (module name)" How do you use this? – Steve Jan 07 '19 at 15:49
  • 1
    FYI for those curious, three dots (…) in the code is either rest parameters or the spread operator. In this case, it's a "spread operator" and expands an array into a list. – konyak Jan 15 '20 at 15:56
  • Why is the second example with `[...modules]` better? – Oushima May 07 '22 at 14:06
18

You're trying to use the MatFormFieldComponent in SearchComponent but you're not importing the MatFormFieldModule (which exports MatFormFieldComponent); you only export it.

Your MaterialModule needs to import it.

@NgModule({
  imports: [
    MatFormFieldModule,
  ],
  exports: [
    MatButtonModule,
    MatFormFieldModule,
    MatInputModule,
    MatRippleModule,
  ],
  declarations: [
    SearchComponent,
  ],
})
export class MaterialModule { }
Lazar Ljubenović
  • 18,976
  • 10
  • 56
  • 91
15

When using the 'mat-form-field' MatInputModule needs to be imported also

import { 
    MatToolbarModule, 
    MatButtonModule,
    MatSidenavModule,
    MatIconModule,
    MatListModule ,
    MatStepperModule,
    MatInputModule
} from '@angular/material';
Miss Chanandler Bong
  • 4,081
  • 10
  • 26
  • 36
Prasanth Nath
  • 191
  • 1
  • 9
8

I had this problem too. It turned out I forgot to include one of the components in app.module.ts

Eric Aya
  • 69,473
  • 35
  • 181
  • 253
Mars Z
  • 91
  • 2
  • 2
  • 1
    ^ This. In my case, a dialog component was throwing the error (I manually created the dialog component). Imported and added the dialog component in the declarations array from app.module.ts (in my case) and problem was solved – Johnny Andrew Jan 11 '21 at 17:48
  • Something similar happened to me, but in my case I split a module into two modules, and forgot to remove some code that was launching a modal with a component that was not part of the module, just deleted that code and it works now. This helped me to realize that error, thanks. – Jorge Rivera Apr 14 '21 at 23:41
  • Thanks this saved me! In my case I created 2 components in the same file but imported only 1 in app.module. – Harshit Gangwar Mar 18 '23 at 09:40
8

Make sure that you've added import {MatInputModule} from '@angular/material/input'; as import statement.

Badri Paudel
  • 1,365
  • 18
  • 19
4

the problem is in the MatInputModule:

exports: [
    MatInputModule
  ]
Suraj Rao
  • 29,388
  • 11
  • 94
  • 103
Leo Lanese
  • 476
  • 4
  • 5
3

Check the namespace from where we are importing

import { MatDialogModule } from "@angular/material/dialog";
import { MatCardModule } from "@angular/material/card";
import { MatButtonModule } from "@angular/material/button";

After importing module path, Import components name in import array

  imports: [
      MatDialogModule,
      MatCardModule,
      MatButtonModule
]
Eng_Farghly
  • 1,987
  • 1
  • 23
  • 34
Alexander Zaldostanov
  • 2,907
  • 4
  • 30
  • 39
2

When using MatAutocompleteModule in your angular application, you need to import Input Module also in app.module.ts

Please import below:

import { MatInputModule } from '@angular/material';

2
@NgModule({
  declarations: [
    SearchComponent
  ],
  exports: [
    CommonModule,
    MatInputModule,
    MatButtonModule,
    MatCardModule,
    MatFormFieldModule,
    MatDialogModule,
  ]
})
export class MaterialModule { }

Also, do not forget to import the MaterialModule in the imports array of AppModule.

Monu Chaudhary
  • 360
  • 3
  • 9
0

In my case, this happened because I had copied the whole directory of a component that I had created from an old project into a new project and forgot to include my component in app.module.ts

(Hopefully this saves someone a lot of time.. as stackoverflow has done for me so many times:)

Alex
  • 1
0

I also encountered a similar problem. My problem was because I deleted a component from only directory and there was the component name in app.module's declarations. When I removed the component from app.module too, my problem was solved immediately. Hope it helps someone else.

Taha Körkem
  • 774
  • 2
  • 9
  • 23