Angular只读文本框用mat-form-field报错:需包含MatFormFieldControl
问题场景
想要用mat-form-field包裹只读textarea展示消息,同时利用mat-form-field的样式和功能,最初写了以下代码:
HTML代码:
<mat-form-field appearance="fill" style="width:2400px"> <mat-label>Some messages from somewhere</mat-label> <textarea cdkTextareaAutosize cdkAutosizeMinRows="6" [formControl]="some_message"></textarea> </mat-form-field>
TS代码:
some_message = new FormControl();
运行后触发报错:Error: mat-form-field must contain a MatFormFieldControl,尝试直接在textarea标签内写内容的写法也失败,但给textarea添加MatInput指令后就能正常运行,想知道原因。
核心原因
mat-form-field是Angular Material的表单容器组件,它的设计要求内部必须包含实现了MatFormFieldControl接口的控件。原生textarea本身并没有实现这个接口,只是普通的表单元素,没法和mat-form-field进行交互适配——比如标签浮动、表单状态同步、样式统一这些mat-form-field的核心功能,都依赖这个接口的实现。
你给textarea绑定formControl只是完成了Angular表单层面的数据绑定,但这和mat-form-field要求的控件适配是两回事,所以会触发报错。而MatInput指令的作用,就是给原生的input/textarea注入MatFormFieldControl接口的实现,让它们能和mat-form-field完美集成。
正确实现代码
要实现只读展示的需求,只需要给textarea加上matInput指令,再设置readonly属性即可:
<mat-form-field appearance="fill" style="width:2400px"> <mat-label>Some messages from somewhere</mat-label> <textarea matInput cdkTextareaAutosize cdkAutosizeMinRows="6" [formControl]="some_message" readonly ></textarea> </mat-form-field>
TS代码保持不变(可直接初始化默认值):
some_message = new FormControl('需要展示的消息内容');
补充说明
如果只是单纯展示文本,也可以不用mat-form-field,直接给原生textarea加样式就行,但既然要利用mat-form-field的多功能性(比如统一的表单样式、标签交互等),添加MatInput是必不可少的前提。
内容的提问来源于stack exchange,提问作者xymzh

