我正在尝试创建一个在angular formGroup中使用的自定义组件。
以下是我想要使用此自定义组件的方法:
<form [formGroup]="form">
...
<app-date-picker formControlName="dateStart"
[isConsultation]="isConsultation"
[label]="'Du'"
[(ngModel)]="agenda.datDeb">
</app-date-picker>
...
</form>
问题:在主要组件(包含此表单)中,当我的自定义组件中的值发生更改(包含MdDatePicker)时,模型不会更新。虽然我使用的是ControlValueAccessor。
我的客户组件的HTML模板:
<div class="">
<span *ngIf="label">{{label}} :</span>
<md-form-field class="" [ngClass]="isConsultation ? 'no-icon' : 'container-input-date'">
<input mdInput
[mdDatepicker]="pickerDebut"
class="consultation"
[(ngModel)]="theDate">
<md-datepicker-toggle mdSuffix [for]="pickerDebut"></md-datepicker-toggle>
<md-datepicker #pickerDebut></md-datepicker>
</md-form-field>
</div>
此后,您可以阅读我的组件的打字稿代码:
import {Component, Input, ViewChild, forwardRef} from '@angular/core';
import {
NgModel,
ControlValueAccessor,
NG_VALUE_ACCESSOR,
NG_VALIDATORS,
FormControl,
} from "@angular/forms";
export function validateDateInputFormat(c: FormControl) {
// Error content in case input date format is not valid
let err = {
formatError: {
given: c.value,
acceptedFormat: 'dd/MM/yyyy'
}
};
console.log('VALIDATE => c : ', c);
// Control logiq
// return c.value == null ? null : (String(c.value).match(date_regexp)) ? null : err;
return null;
}
@Component({
selector: 'app-date-picker',
templateUrl: './date-picker.component.html',
styleUrls: ['./date-picker.component.scss'],
providers: [
{
provide: NG_VALUE_ACCESSOR,
useExisting: forwardRef(() => DatePickerComponent),
multi: true
},
{
provide: NG_VALIDATORS,
useValue: validateDateInputFormat,
multi: true
}
]
})
export class DatePickerComponent implements ControlValueAccessor {
@Input()
label : string;
@Input()
isConsultation : boolean;
@ViewChild(NgModel) _theDate: NgModel;
constructor() { }
propagateChange = (_: any) => {};
onTouched: any = () => { };
writeValue(obj: any): void {
console.log('writeValue => obj : ', obj);
if (obj) {
this._theDate = obj;
}
}
registerOnChange(fn: any): void {
this.onChange = fn;
console.log('registerOnChange => fn : ', fn);
}
registerOnTouched(fn: any): void {
this.onTouched = fn;
console.log('registerOnTouched => fn : ', fn);
}
onChange(event){
console.log('onChange(event) - event => ', event );
this.propagateChange(event.target.value);
}
get theDate() {
console.log('get theDate()');
return this._theDate;
}
set theDate(val) {
console.log('set theDate(val) - val => ', val );
this._theDate = val;
this.propagateChange(val);
}
}
我在这里做错了什么?
答案 0 :(得分:0)
我设法克服了这一点。
这是答案。
第一个问题:
@ViewChild(NgModel) _theDate: NgModel;
我转变为
private _theDate : string;
第二个问题:
onChange方法没用。我删除了它,下面是我的组件的最终TS代码:
import {Component, Input, ViewChild, forwardRef} from '@angular/core';
import {
NgModel,
ControlValueAccessor,
NG_VALUE_ACCESSOR,
NG_VALIDATORS,
FormControl,
} from "@angular/forms";
export function validateDateInputFormat(c: FormControl) {
// Error content in case input date format is not valid
let err = {
formatError: {
given: c.value,
acceptedFormat: 'dd/MM/yyyy'
}
};
console.log('VALIDATE => c : ', c);
// Control logiq
// return c.value == null ? null : (String(c.value).match(date_regexp)) ? null : err;
return null;
}
@Component({
selector: 'app-date-picker',
templateUrl: './date-picker.component.html',
styleUrls: ['./date-picker.component.scss'],
providers: [
{
provide: NG_VALUE_ACCESSOR,
useExisting: forwardRef(() => DatePickerComponent),
multi: true
},
{
provide: NG_VALIDATORS,
useValue: validateDateInputFormat,
multi: true
}
]
})
export class DatePickerComponent implements ControlValueAccessor {
@Input()
label : string;
@Input()
isConsultation : boolean;
private _theDate: string;
constructor() { }
propagateChange = (_: any) => {};
onTouched: any = () => { };
writeValue(obj: any): void {
console.log('writeValue => obj : ', obj);
if (obj) {
this._theDate = obj;
}
}
registerOnChange(fn: any): void {
this.propagateChange= fn;
console.log('registerOnChange => fn : ', fn);
}
registerOnTouched(fn: any): void {
this.onTouched = fn;
console.log('registerOnTouched => fn : ', fn);
}
get theDate() {
console.log('get theDate()');
return this._theDate;
}
set theDate(val) {
console.log('set theDate(val) - val => ', val );
this._theDate = val;
this.propagateChange(val);
}
}