Both examples work in Chrome and Opera, but fail in Firefox 56.0.
I want to set the files
FileList of a form\'s file inpu
The ability to set a FileList as the input.files
property programmatically has been added as an PR to the specs three months ago, even if webkit allow this for years. Firefox has landed a patch in its next stable version, 57 and Edge is probably still working on it (I don't have an account to see the progress).It seems it has now landed in Edge too.
The main use case for this feature is to allow DataTransfer.files
from e.g a drag&drop event or a paste one to be added to an field. As such, only a FileList is allowed (and
null
to clear the input).
So in the case exposed in the body of your question, I don't really see the point of using this feature between two fields.
If you want to keep in memory selected FileList, you can always convert it as an Array of files.
If you want to be able to move your filled input in a later on, you can do it directly with the inputElement and DOM methods.
And if you need to workaround the limitations this new feature leverages, you can always fill an FormData with the DataTransfer's files and send this FormData through xhr instead of using the default HTML form method.
And Since I first missed the real use-case, in the codepen, here is an possible implementation to workaround the drag&drop issue you are facing, even on older browsers that didn't support this new feature.
This uses an hidden input in the dropZone, which will catch the dropped files directly.
// called when the input hidden in the dropZone changes
function handleDroppedChange(evt) {
this.removeEventListener('drop', handleDroppedChange); // only once
// create a new hidden input
var clone = this.cloneNode();
clone.addEventListener('change', handleDroppedChange);
clone.addEventListener('change', handleBasicChange);
this.parentNode.insertBefore(clone, this);
// replace the visible one with the current hidden one
var form = document.querySelector('form');
var previous = form.querySelector('input[type=file]');
form.insertBefore(this, previous);
form.removeChild(previous);
this.id = previous.id; // for the
#dropzone {
display: inline-block;
padding: 25px;
border: 8px dashed #b11;
position: relative;
}
#dropzone.drag {
border-color: #f74;
}
#dropzone>input{
opacity: 0;
position: absolute;
height: 100%;
width: 100%;
left: 0;
top: 0;
/* below rules avoid clicks on hidden input */
pointer-events: none;
}
#dropzone.drag>input{
pointer-events: all;
}