【发布时间】:2021-01-02 00:22:06
【问题描述】:
我的目标:
我正在尝试使用清除按钮构建可重复使用的 mat-form-field。
我是如何努力实现目标的:
我创建了一个“mat-clearable-input”组件并像这样使用它:
<mat-clearable-input>
<mat-label>Put a Number here pls</mat-label>
<input matInput formControlName="number_form_control">
</mat-clearable-input>
mat-clearable-input.component.html
<mat-form-field>
<ng-content></ng-content>
</mat-form-field>
预期结果:
ng-content 标签获取标签和输入并将它们放入 mat-form-field 标签内。
实际结果:
Error: mat-form-field must contain a MatFormFieldControl.
at getMatFormFieldMissingControlError (form-field.js:226)
at MatFormField._validateControlChild (form-field.js:688)
at MatFormField.ngAfterContentChecked (form-field.js:558)
at callHook (core.js:2926)
at callHooks (core.js:2892)
at executeInitAndCheckHooks (core.js:2844)
at refreshView (core.js:7239)
at refreshComponent (core.js:8335)
at refreshChildComponents (core.js:6991)
at refreshView (core.js:7248)
我好像遗漏了一些东西,而且我没有正确使用 ng-content 标签。
我无法在 Angular 网站上找到 ng-content 标签的文档。
感谢您的帮助。
在下面回答后编辑
所以我尝试了这个建议的方法:
export class MatClearableInputComponent implements OnInit {
@ContentChild(MatFormFieldControl) _control: MatFormFieldControl<any>;
@ViewChild(MatFormField) _matFormField: MatFormField;
// see https://stackoverflow.com/questions/63898533/angular-ng-content-not-working-with-mat-form-field/
ngOnInit() {
this._matFormField._control = this._control;
}
}
不幸的是,当我尝试在表单中使用它时,它仍然失败并显示错误“错误:mat-form-field 必须包含 MatFormFieldControl。”
我尝试在表单中使用此组件的代码:
<mat-clearable-input>
<mat-label>Numero incarico</mat-label>
<buffered-input matInput formControlName="numero"></buffered-input>
</mat-clearable-input>
stackblitz 上的重现:https://stackblitz.com/edit/angular-material-starter-xypjc5?file=app/clearable-form-field/clearable-form-field.component.html
注意 mat-form-field 功能如何不起作用(没有轮廓,没有浮动标签),同时打开控制台,您会看到错误 Error: mat-form-field must contain a MatFormFieldControl。
选项 2 发布后编辑
我试过这样做:
<mat-form-field>
<input matInput hidden>
<ng-content></ng-content>
</mat-form-field>
它可以工作,但是当我在表单字段中添加一个 mat-label 时,如下所示:
<mat-clearable-input>
<mat-label>Numero incarico</mat-label>
<buffered-input matInput formControlName="numero"></buffered-input>
</mat-clearable-input>
标签永远不会浮动,它只是作为一个正常的跨度一直停留在那里。
所以我尝试将带有标签的内容子项分配给 this._matFormField._control._label,但这不起作用,因为 _label 是私有的并且没有设置器。
看起来我很不走运,如果不付出很多努力,这是无法在 Angular 中完成的。
如果您有任何进一步的想法,请随时 fork stackblitz 并尝试!
@evilstiefel 回答后编辑
该解决方案仅适用于原生 <input matInput>。
当我尝试用我的自定义输入组件替换它时,它不再起作用了。
工作设置:
<mat-form-field appClearable>
<mat-label>ID incarico</mat-label>
<input matInput formControlName="id">
</mat-form-field>
相同的设置,但使用我的自定义“缓冲输入”组件(不工作:()
<mat-form-field appClearable>
<mat-label>ID incarico</mat-label>
<buffered-input matInput formControlName="id"></buffered-input>
</mat-form-field>
当我单击清除按钮时,控制台会记录此错误:
TypeError: Cannot read property 'ngControl' of undefined
at ClearableDirective.clear (clearable.directive.ts:33)
at ClearButtonComponent.clearHost (clearable.directive.ts:55)
at ClearButtonComponent_Template_button_click_0_listener (clearable.directive.ts:47)
at executeListenerWithErrorHandling (core.js:14293)
at wrapListenerIn_markDirtyAndPreventDefault (core.js:14328)
at HTMLButtonElement.<anonymous> (platform-browser.js:582)
at ZoneDelegate.invokeTask (zone-evergreen.js:399)
at Object.onInvokeTask (core.js:27126)
at ZoneDelegate.invokeTask (zone-evergreen.js:398)
at Zone.runTask (zone-evergreen.js:167)
【问题讨论】:
-
如果你想在
mat-form-field中使用组件(在这种情况下,将mat-clearable-input放入其中)它必须实现MatFormFieldControl接口。看看the docs 看看怎么做。 -
@julianobrasil 谢谢,但这不是问题所在:在问题的代码 sn-p 中,我使用了带有 matInput 指令的输入标签,因此它应该在 mat-form-field 中工作.我不是在创建自定义组件。还要记住,如果我不使用 ng-content 并且我只是手动将输入标签放在那里,这段代码就可以工作
-
也许stackblitz会有所帮助
-
一个问题:它应该是什么样子?
-
@AndreEirico 喜欢本页的第一个示例material.angular.io/components/input/examples
标签: javascript angular angular-material