StdMultiFilesUpload.vue 4.4 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153
  1. <template>
  2. <div>
  3. <a-upload
  4. :before-upload="beforeUpload"
  5. :multiple="true"
  6. :show-upload-list="true"
  7. :file-list="uploadList"
  8. :remove="remove"
  9. >
  10. <a-button :disabled="disabled">
  11. <a-icon type="upload"/>
  12. 选择文件
  13. </a-button>
  14. </a-upload>
  15. <a-progress
  16. v-if="show_progress"
  17. :stroke-color="{
  18. from: '#108ee9',
  19. to: '#87d068',
  20. }"
  21. :percent="progress"
  22. />
  23. <a-button
  24. type="primary"
  25. :disabled="uploadList.length === 0 && !id"
  26. :loading="uploading"
  27. style="margin: 16px 0"
  28. @click="upload"
  29. v-if="id"
  30. >
  31. {{ uploading ? '上传中' : '开始上传' }}
  32. </a-button>
  33. <p style="margin: 15px 0" v-for="file in uploaded" :key="file.id">
  34. <a-icon type="paper-clip" style="margin-right: 5px"/>
  35. <a :href="server + '/' + file.path" target="_blank" @click="()=>{}">{{ getFileName(file.path) }}</a>
  36. <a-popconfirm
  37. title="确定要删除文件吗"
  38. ok-text="确认"
  39. cancel-text="取消"
  40. @confirm="deleteFile(file.id)"
  41. style="float: right"
  42. >
  43. <a-button type="link">删除</a-button>
  44. </a-popconfirm>
  45. </p>
  46. </div>
  47. </template>
  48. <script>
  49. export default {
  50. name: 'StdMultiFilesUpload',
  51. props: {
  52. api: Function,
  53. id: {
  54. type: Number,
  55. default: null
  56. },
  57. fileList: {
  58. default: null
  59. },
  60. autoUpload: {
  61. type: Boolean,
  62. default: false
  63. },
  64. api_delete: {
  65. type: Function,
  66. default: null
  67. },
  68. disabled: {
  69. type: Boolean,
  70. default: false
  71. }
  72. },
  73. watch: {
  74. fileList() {
  75. this.uploaded = this.fileList
  76. }
  77. },
  78. data() {
  79. return {
  80. show_progress: false,
  81. uploadList: [],
  82. uploaded: this.fileList,
  83. lastFileTime: 0,
  84. server: process.env['VUE_APP_API_UPLOAD_ROOT'],
  85. uploading: false,
  86. progress: 0
  87. }
  88. },
  89. model: {
  90. prop: 'fileUrl',
  91. event: 'changeFileUrl'
  92. },
  93. methods: {
  94. async upload() {
  95. if (this.uploadList.length) {
  96. this.uploading = true
  97. this.show_progress = true
  98. this.progress = 0
  99. let formData = new FormData()
  100. this.uploadList.forEach(v => {
  101. formData.append('file[]', v)
  102. })
  103. this.visible = false
  104. this.uploading = true
  105. this.$message.info('正在上传附件, 请不要关闭本页')
  106. let config = {
  107. onUploadProgress: (progressEvent) => {
  108. // 使用本地 progress 事件
  109. if (progressEvent.lengthComputable) {
  110. this.progress = Math.round((progressEvent.loaded / progressEvent.total) * 100) // 使用某种 UI 进度条组件会用到的百分比
  111. }
  112. }
  113. }
  114. return this.api(this.id, formData, config).then(r => {
  115. this.uploadList = []
  116. this.uploaded = [...this.uploaded, ...r]
  117. this.uploading = false
  118. this.$emit('uploaded', r)
  119. this.uploading = false
  120. this.orig = false
  121. this.$message.success('上传成功')
  122. }).catch(e => {
  123. this.$message.error(e.message ? e.message : '上传失败')
  124. })
  125. }
  126. },
  127. beforeUpload(file) {
  128. this.uploadList.push(file)
  129. return false
  130. },
  131. deleteFile(file_id) {
  132. this.api_delete(this.id, file_id).then(r => {
  133. this.uploaded = r
  134. })
  135. },
  136. getFileName(path) {
  137. // 从15开始找
  138. const idx = path.indexOf('/', 15)
  139. return path.substring(idx + 1)
  140. },
  141. remove(r) {
  142. this.uploadList = this.uploadList.filter(value => {
  143. return value !== r
  144. })
  145. },
  146. }
  147. }
  148. </script>
  149. <style scoped>
  150. </style>