#angular #angular-template-form
Вопрос:
Как и сказано в названии, если я помещаю ввод в свой пользовательский компонент, он не воспринимается шаблонной формой Angular. Вот stackblitz
Вот некоторый код из StackBlitz
app.component.html
<div ngForm #myForm="ngForm">
<app-custom-textbox
customName="wrappedInput"
customValue="wrapped"
></app-custom-textbox>
<hr />
<input name="noWrapper" [(ngModel)]="message" />
</div>
<hr />
<p>myForm.value is below:</p>
{{ myForm.value | json }}
custom-textbox.component.html
<p>My custom textbox component</p>
<input type="textbox" name="{{ customName }}" [(ngModel)]="customValue" />
пользовательский-textbox.component.ts
import { Component, Input } from '@angular/core';
@Component({
selector: 'app-custom-textbox',
templateUrl: './custom-textbox.component.html',
})
export class CustomTextboxComponent {
@Input() customName: string = '';
@Input() customValue: string = '';
}
Я ожидаю увидеть оба wrappedInput
и noWrapper
свойства в myForm.value
выходных данных, но только noWrapper
подбирается.
Ответ №1:
Необходимо реализовать ControlValueAccessor для CustomTextBoxComponent, как показано ниже: ~
import { Component, forwardRef, Input } from '@angular/core';
import { ControlValueAccessor, NG_VALUE_ACCESSOR } from '@angular/forms';
@Component({
selector: 'app-custom-textbox',
templateUrl: './custom-textbox.component.html',
providers: [
{
provide: NG_VALUE_ACCESSOR,
useExisting: forwardRef(() => CustomTextboxComponent),
multi: true,
}
],
})
export class CustomTextboxComponent implements ControlValueAccessor {
@Input() customValue: string = '';
propagateChange = (_: any) => {};
public onTouched: any = () => {};
writeValue(obj: any): void {
this.customValue = obj;
}
registerOnChange(fn: any): void {
this.propagateChange = fn;
}
registerOnTouched(fn: any): void {
this.onTouched = fn;
}
onModelChange(val: any) {
this.propagateChange(val);
}
}
Комментарии:
1. Редактируемая ссылка StackBlitz: stackblitz.com/edit/angular-ivy-uittkj