Ошибка "mat-form-field must contain a MatFormFieldControl" в Angular Material
Причина ошибки
Ошибка возникает, потому что Angular Material требует, чтобы внутри <mat-form-field> находился элемент с директивой MatFormFieldControl. Обычно это <input> или <textarea> с атрибутом matInput. Без этой директивы Angular Material не может связать поле ввода с формой и управлять его отображением.
В вашем коде отсутствует директива matInput на элементе <input>. Вот исправленный шаблон:
<mat-form-field appearance="outline">
<mat-label>Email</mat-label>
<input matInput type="email" placeholder="Введите email">
</mat-form-field>
Полное решение
Чтобы избежать этой ошибки в будущем, следуйте этим шагам:
- Импортируйте необходимые модули:
MatFormFieldModuleиMatInputModule(как вы уже сделали). - Добавьте директиву
matInputк каждому<input>или<textarea>внутри<mat-form-field>. - Убедитесь, что компонент использует
BrowserAnimationsModule(илиNoopAnimationsModule) для работы анимаций Angular Material.
Пример исправленного компонента
Вот полный рабочий пример login.component.ts:
import { Component } from '@angular/core';
@Component({
selector: 'app-login',
template: `
<mat-form-field appearance="outline">
<mat-label>Email</mat-label>
<input matInput type="email" placeholder="Введите email">
</mat-form-field>
<mat-form-field appearance="outline">
<mat-label>Пароль</mat-label>
<input matInput type="password" placeholder="Введите пароль">
</mat-form-field>
`,
styleUrls: ['./login.component.css']
})
export class LoginComponent {}
Дополнительные советы
- Используйте
matNativeControlдля нативных элементов — если вы хотите использовать стандартные HTML-элементы без Material-стилей, но с контролем формы. - Проверьте версии пакетов — убедитесь, что
@angular/materialи@angular/cdkсовместимы с вашей версией Angular. - Очистите кэш — иногда помогает перезапуск сервера разработки (
ng serve) после установки новых пакетов.
После добавления matInput ошибка исчезнет, и форма будет работать корректно.
Альтернативный подход: использование FormControl
Если вы используете реактивные формы Angular, убедитесь, что вы также импортировали ReactiveFormsModule и привязали formControl к элементу <input> с директивой matInput.
Пример:
// В модуле
import { ReactiveFormsModule } from '@angular/forms';
@NgModule({
imports: [ReactiveFormsModule, MatFormFieldModule, MatInputModule]
})
export class AppModule {}
// В компоненте
import { FormControl } from '@angular/forms';
@Component({
template: `
<mat-form-field>
<mat-label>Email</mat-label>
<input matInput [formControl]="emailControl">
</mat-form-field>
`
})
export class LoginComponent {
emailControl = new FormControl('');
}
Такой подход даёт больше возможностей для валидации и управления состоянием формы.