Home > Software design >  VueJS file upload field cannot be reset
VueJS file upload field cannot be reset

Time:04-22

In my vuejs application, I have a modal to insert some user data with a file upload.

I should be able to clear all the form fields once when an user successfully upload any content.

All my fields get reset apart from the file upload field.

It will remained as it is.

Inside my form.vue, for the file upload I have

<div >
            <dashboard-input-label
              identifier="document"
              :settings="{ help: true, helpDirection: 'left' }"
            >
              Upload document
              <template slot="helpText">
                Maximum filesize is 5 MB. The default allowed file extensions
                are: pdf, jpeg and png.
              </template>
            </dashboard-input-label>
            <validator-v2
              :identifier="identifier"
              name="document_file"
              :rules="{ required: { message: 'Document is required.' } }"
            >
              <custom-file-upload
                ref="documentDocument"
                v-model="documentFile"
                :max-upload-file-size="5"
                name="document_file"
              ></custom-file-upload>
            </validator-v2>
          </div>

and following is my button

<loading-button ref="submitBtn" size="normal">
              Save & Add new
            </loading-button> 

This is my submitBtn method,

storeDocumentAndAddNew() {
      this.isAddNew = true
      const loader = this.$refs.submitBtn
      this.storeDocument(loader)
    },

And for the field reset I have followings,

reset() {
      this.documentName= null
      this.dateOfIssue= null
      this.expiryDate= null
      this.documentNumber = null
      this.doesNotHaveDocumentNumber = false
      this.doesNotExpire = false
      this.documentFile = null
      this.doesOptIn = false
      this.isAddNew = false
      this.documentFile = ''
      this.$refs.documentDocument.value = null
    },

Once I hit submit, every field get reset except this file upload field.

Following is my custom-file-upload.vue component

<template>
    <div>

        <div >

            <div @click="selectFile" >

                <p >
                    <span >
                        <span v-if="filename !== null">{{ filename | limitString }} </span>
                        <span  v-else><slot
                            name="currentFile"></slot></span>
                    </span>

                    <span >
                        <svg xmlns="http://www.w3.org/2000/svg" width="24" height="24" viewBox="0 0 24 24" fill="none"
                             stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round"
                             ><path d="M21 15v4a2 2 0 0 1-2 2H5a2 2 0 0 1-2-2v-4"></path><polyline
                            points="17 8 12 3 7 8"></polyline><line x1="12" y1="3" x2="12" y2="15"></line></svg>
                    </span>

                </p>

                <input @change="showFileName" ref="fileInput" type="file" :name="name">
                <div >
                    <toastr-alert @hidden="resetToastrMessage" v-if="message !== ''" :message="message"
                                  :type="type"></toastr-alert>
                </div>
            </div>
        </div>

    </div>

</template> 

Even though I've used, this.$refs.documentDocument.value = null it's not clearing my file upload field....

Update

I have used @wendt88's answer and then the file is removed. But the previously uploaded, document's name will be remained there as it is..As an example, if I tried to upload a document called, dummy.pdf, it'll show the dummy.pdf text even after a successful submission...

Now my reset looks likes this,

reset() {
      this.documentName= null
      this.dateOfIssue= null
      this.expiryDate= null
      this.documentNumber = null
      this.doesNotHaveDocumentNumber = false
      this.doesNotExpire = false
      this.documentFile = null
      this.doesOptIn = false
      this.isAddNew = false
      this.$refs.documentDocument.$refs.fileInput.value = null
    },

Following is my complete custom-file-upload.vue

<template>
    <div>

        <div >

            <div @click="selectFile" >

                <p >
                    <span >
                        <span v-if="filename !== null">{{ filename | limitString }} </span>
                        <span  v-else><slot
                            name="currentFile"></slot></span>
                    </span>

                    <span >
                        <svg xmlns="http://www.w3.org/2000/svg" width="24" height="24" viewBox="0 0 24 24" fill="none"
                             stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round"
                             ><path d="M21 15v4a2 2 0 0 1-2 2H5a2 2 0 0 1-2-2v-4"></path><polyline
                            points="17 8 12 3 7 8"></polyline><line x1="12" y1="3" x2="12" y2="15"></line></svg>
                    </span>

                </p>

                <input @change="showFileName" ref="fileInput" type="file" :name="name">
                <div >
                    <toastr-alert @hidden="resetToastrMessage" v-if="message !== ''" :message="message"
                                  :type="type"></toastr-alert>
                </div>
            </div>
        </div>

    </div>

</template>
<style lang="scss" scoped>
.custom-file-upload input {
    position: absolute;
    cursor: pointer;
    height: 0;
    width: 0;
    opacity: 0;
}

.cs--file-upload-current-file {
    max-width: 220px;
}

label {
    font-weight: 400 !important;
}


</style>
<script>
// Mixins
import HasToastrMessage from '@/Mixins/HasToastrMessage.js';

// Helper
import Helper from '@/Support/Helper.js';

export default {
    mixins: [HasToastrMessage],
    props: ['name', 'value', 'maxUploadFileSize'],

    data() {
        return {
            file: null,
            filename: null,
            message: "",
            type: "",
            fileSize: 0,
            maxFileSize: 10,
            validFileTypes: [
                'application/pdf',
                'image/jpeg',
                'image/png'
            ]
        }
    },

    mounted() {
        if (Helper.isset(this.maxUploadFileSize)) {
            this.maxFileSize = this.maxUploadFileSize;
        }
    },

    methods: {


        showFileName(e) {
            this.filename = collect(e.target.value.split('\\')).last();
            let file = e.target.files[0];
            let fileSize = file.size / 1000000;

            if (fileSize > this.maxFileSize) {
                this.showToastrErrorMessage(`The uploaded file is too big. Max size: ${this.maxFileSize} MB.`);
                this.$refs.fileInput.value = null
                this.filename = null
            } else if (!this.validFileTypes.includes(file.type)) {
                this.showToastrErrorMessage(`The uploaded file is invalid. Please upload valid type.`);
                this.$refs.fileInput.value = null
                this.filename = null
            } else if (this.filename) {
                this.file = file
                this.showToastrSuccessMessage(`Your file is successfully uploaded.`);
                this.$emit('uploaded')
            } else {
                this.showToastrErrorMessage(`Your file could not be uploaded. Please try again.`);
            }
        },

        resetToastrMessage() {
            this.message = "";
            this.type = "";
        },

        selectFile() {
            this.$refs.fileInput.click();
        },
    }

}

</script>

CodePudding user response:

this.$refs.documentDocument is a vue component, to clear it´s value property use this.$set(this.$refs.documentDocument, 'value', null) -> https://v2.vuejs.org/v2/guide/reactivity.html otherwise documentDocument does not know that you have changed it´s value

but if you want to clear the file input value, run (https://stackoverflow.com/a/16222877/1826106):

this.$refs.documentDocument.$refs.fileInput.value = null;
this.$set(this.$refs.documentDocument, 'filename', null);
  • Related