Angular 5 模型在事件完成后更新



>问题

我正在使用角度 5 并构建了一个具有 3 个控件的组件

<ss-multiselect-dropdown id="type" formControlName="type" (ngModelChange)="onChange('type')"></ss-multiselect-dropdown>
<input id="caption" type='text' formControlName='caption' (input)="onChange('caption')" />
<custom-uploader formControlName="url" (input)="onChange('url')"></custom-uploader>

ss-multiselect-dropdowninput调用onChange时 模型在单步执行onChange方法时显示预期值。但是,当通过custom-uploader调用onChange时,旧值(在调用onChange之前存在的值(仍应用于模型。

需要明确的是:

期望值是指我为该控件选择或输入的值

我试过改变

<custom-uploader formControlName="url" (input)="onChange('url')"></custom-uploader>

<custom-uploader formControlName="url" (change)="onChange('url')"></custom-uploader>

<custom-uploader formControlName="url" (ngModelChange)="onChange('url')"></custom-uploader>

似乎模型在onChange完成后会更新。我做错了什么?

代码

custom-uploader.component.html

<div class="form-group">
<div class="input-group file-upload">
<input type="file" (change)="fileChange(input)" #input class="file-upload-btn"/>
<input type="text" class="form-control" placeholder="Choose a file..." value="{{file}}">
<i class="fa fa-times delete-file" (click)="removeFile()" *ngIf="file"></i>
<span class="input-group-btn">
<button class="btn btn-primary" type="button"><i class="fa fa-upload"></i></button>
</span>
</div>
</div>

custom-uploader.component.ts

import { Component, ViewEncapsulation, ChangeDetectorRef, ViewChild, Output, EventEmitter, forwardRef, SimpleChanges, OnChanges } from '@angular/core';
import { NG_VALUE_ACCESSOR, ControlValueAccessor, NG_VALIDATORS } from '@angular/forms';
import { Ng2ImgMaxService } from 'ng2-img-max';
@Component({
selector: 'custom-uploader',
encapsulation: ViewEncapsulation.None,
templateUrl: './file-uploader.component.html',
styleUrls: ['./file-uploader.component.scss'],
providers: [ 
{ provide: NG_VALUE_ACCESSOR, useExisting: forwardRef(() => FileUploaderComponent), multi: true }
]
})
export class FileUploaderComponent implements OnChanges, ControlValueAccessor  {
@ViewChild('input') fileUploaderInput: any;
public file:any;
public propagateChange = (_: any) => {};
constructor(
private _changeDetectorRef: ChangeDetectorRef,
private _ng2ImgMaxService: Ng2ImgMaxService
) { }   
writeValue(obj: any): void 
{ 
this.file = obj;
this._changeDetectorRef.detectChanges();
}
registerOnChange(fn: any): void {
this.propagateChange = fn;
}
registerOnTouched(fn: any): void { }
setDisabledState?(isDisabled: boolean): void { }
ngOnChanges(changes: SimpleChanges): void { }
fileChange(input){
const reader = new FileReader();
if (input.files.length) {       
this.file = input.files[0].name;     
this.propagateChange(this.file);   
this.fileUploaderInput.nativeElement.value = "";    
}
}
removeFile():void{
this.file = '';
this.propagateChange(this.file);       
}
}

(change)这样的括号语法是指在值更改时发出事件的EventEmitter。你必须自己在FileUploaderComponent中实现它,就像这样:

@Output() change = new EventEmitter<string>();
...
fileChange(input){
const reader = new FileReader();
if (input.files.length) {
this.file = input.files[0].name;
this.change.next(this.file);
...  
}
}

然后在哪里实例化它:

模板:

<custom-uploader formControlName="url" (change)="onChange($event)"></custom-uploader>

打字稿:

onChange(fileName: string) {
//Whatever you want to do with the fileName
}

最新更新