File upload from <input type="file">
I think that it's not supported. If you have a look at this DefaultValueAccessor
directive (see https://github.com/angular/angular/blob/master/modules/angular2/src/common/forms/directives/default_value_accessor.ts#L23). You will see that the value used to update the bound element is $event.target.value
.
This doesn't apply in the case of inputs with type file
since the file object can be reached $event.srcElement.files
instead.
For more details, you can have a look at this plunkr: https://plnkr.co/edit/ozZqbxIorjQW15BrDFrg?p=info:
@Component({ selector: 'my-app', template: ` <div> <input type="file" (change)="onChange($event)"/> </div> `, providers: [ UploadService ]})export class AppComponent { onChange(event) { var files = event.srcElement.files; console.log(files); }}
@Component({ selector: 'my-app', template: ` <div> <input name="file" type="file" (change)="onChange($event)"/> </div> `, providers: [ UploadService ]})export class AppComponent { file: File; onChange(event: EventTarget) { let eventObj: MSInputMethodContext = <MSInputMethodContext> event; let target: HTMLInputElement = <HTMLInputElement> eventObj.target; let files: FileList = target.files; this.file = files[0]; console.log(this.file); } doAnythingWithFile() { }}
There is a slightly better way to access attached files. You could use template reference variable to get an instance of the input element.
Here is an example based on the first answer:
@Component({ selector: 'my-app', template: ` <div> <input type="file" #file (change)="onChange(file.files)"/> </div> `, providers: [ UploadService ]})export class AppComponent { onChange(files) { console.log(files); }}
Here is an example app to demonstrate this in action.
Template reference variables might be useful, e.g. you could access them via @ViewChild directly in the controller.