How to reset selected file with input tag file type in Angular 2?

This is how my input tag looks like:

<input type="file" placeholder="File Name" name="filename" (change)="onChange($event)">
<button>Reset</button>

I want to reset the selected file in Angular 2. Help would be greatly appreciated. Let me know if you need more details.

P.S.

I could get file details from $event parameters and save it in a typescript variable, but this variable is not bound to the input tag.


Solution 1:

You can use ViewChild to access the input in your component. First, you need to add #someValue to your input so you can read it in the component:

<input #myInput type="file" placeholder="File Name" name="filename" (change)="onChange($event)">

Then in your component you need to import ViewChild from @angular/core:

import { ViewChild } from '@angular/core';

Then you use ViewChild to access the input from template:

@ViewChild('myInput')
myInputVariable: ElementRef;

Now you can use myInputVariable to reset the selected file because it's a reference to input with #myInput, for example create method reset() that will be called on click event of your button:

reset() {
    console.log(this.myInputVariable.nativeElement.files);
    this.myInputVariable.nativeElement.value = "";
    console.log(this.myInputVariable.nativeElement.files);
}

First console.log will print the file you selected, second console.log will print an empty array because this.myInputVariable.nativeElement.value = ""; deletes selected file(s) from the input. We have to use this.myInputVariable.nativeElement.value = ""; to reset the value of the input because input's FileList attribute is readonly, so it is impossible to just remove item from array. Here's working Plunker.

Solution 2:

Angular 5

html

<input type="file" #inputFile>

<button (click)="reset()">Reset</button>

template

@ViewChild('inputFile') myInputVariable: ElementRef;

reset() {
    this.myInputVariable.nativeElement.value = '';
}

Button is not required. You can reset it after change event, it is just for demonstration