.vue component
<template>
<div class="modal">
<div class="modal-dialog">
<div class="modal-content">
<div class="modal-header">
Loading Files
</div>
<div class="modal-body">
<input type='file' multiple='multiple' class='form-control' @change='changed'>
<div v-for='file in files'>
{{ file.name }} {{ formatSize(file.size) }}
</div>
<div class='alert alert-danger' v-if='error.files' v-for='err in error.files'>
{{ err }}
</div>
<div class='alert alert-danger' v-if='failed.length' v-for='f in failed'>
Failed to upload: {{ f }}
</div>
<template v-if='saved.length' v-for='f, index in saved'>
<div class='alert alert-info'>
{{ f.original_filename }}
<a href='#' class='badge badge-info pull-right' @click.native='delete(f, index)' title='Delete'>
<i class="fa fa-spinner fa-pulse fa-1x" v-if='f.isDeleting'></i>
<i class='fa fa-close' v-else></i>
</a>
</div>
<div class='alert alert-danger' v-if='f.isError'>
{{ f.isError }}
</div>
</template>
</div>
<div class="modal-footer">
<button type='button' class='btn btn-default' @click='handleOk' v-if='saved.length && !isUploading'>
OK
</button>
<button type="button" class="btn btn-default" @click="handleUpload">
<template v-if='isUploading'>
<i class="fa fa-spinner fa-pulse fa-1x"></i>
</template>
<template v-else>
Upload
</template>
</button>
<button type="button" class="btn btn-default" @click="handleCancel">Cancel</button>
</div>
</div>
</div>
</div>
</template>
<script>
export default {
props: {
propShow: {
required: true,
type: Boolean
}
},
data() {
return {
files: [],
saved: [],
failed: [],
isUploading: false,
modal: null,
input: null,
error: {},
}
},
watch: {
propShow: function(val, oldVal) {
if(val) {
this.modal.show('modal');
} else {
this.modal.hide('modal');
}
}
},
mounted() {
this.modal = $(this.$el);
this.input = this.modal.find('input[type=file]');
},
methods: {
changed(e) {
let files = e.target.files || e.dataTransfer.files;
this.files = files;
},
delete(f, index) {
f.isDeleting = true;
delete f.isError;
this.$set(this.saved, index, f);
this.doPostRequest('/file/' + f.id + '/delete', {}, (body) => {
f.isDeleting = false;
if(body.ok) {
for(let i = 0; i < this.saved.length; i++) {
if( this.saved[i].id === f.id ) {
this.saved.splice(i, 1);
}
}
} else {
f.isError = body.data.error;
this.$set(this.saved, index, f);
}
}, (body) => {
f.isDeleting = false;
});
},
handleOk() {
if( this.isUploading ) return;
this.$emit('ok', this.saved);
this.saved = [];
this.failed = [];
},
handleUpload() {
if( this.isUploading ) return;
this.isUploading = true;
let data = new FormData();
for(let i = 0; i < this.files.length; i++) {
data.append('files[]', this.files[i]);
}
this.error = {};
this.doPostRequest('/file/upload', data, (body) => {
if(body.ok) {
this.saved.push.apply(this.saved, body.data.saved);
this.failed.push.apply(this.failed, body.data.failed);
this.files = [];
this.input.val('');
} else {
this.error = body.data;
}
this.isUploading = false;
}, (body) => {
this.isUploading = false;
});
},
handleCancel() {
if( this.isUploading ) return;
this.files = [];
this.input.val('');
this.failed = [];
for(let i = 0; i < this.saved.length; i++) {
this.delete(this.saved[i], i);
}
this.saved = [];
this.$emit('cancel');
},
formatSize(size) {
if (size > 1024 * 1024 * 1024 * 1024) {
return (size / 1024 / 1024 / 1024 / 1024).toFixed(2) + ' TB';
} else if (size > 1024 * 1024 * 1024) {
return (size / 1024 / 1024 / 1024).toFixed(2) + ' GB';
} else if (size > 1024 * 1024) {
return (size / 1024 / 1024).toFixed(2) + ' MB';
} else if (size > 1024) {
return (size / 1024).toFixed(2) + ' KB';
}
return size.toString() + ' B';
}
}
}
When I click on '.fa-close' link (this part below) - it should trigger the delete
method, but it does not.
<div class='alert alert-info'>
{{ f.original_filename }}
<a href='#' class='badge badge-info pull-right' @click.native='delete(f, index)' title='Delete'>
<i class="fa fa-spinner fa-pulse fa-1x" v-if='f.isDeleting'></i>
<i class='fa fa-close' v-else></i>
</a>
</div>
In Chrome developer tools, I can see that the event handler is attached to this link.