| | |
| | | <template> |
| | | <div class="upload-audio-container"> |
| | | <div class="left"> |
| | | <el-form :inline="true" class="demo-form-inline"> |
| | | <el-form-item label=""> |
| | | <el-input v-model.lazy="keyword" placeholder="请输入搜索内容" suffix-icon="el-icon-search" size="small"></el-input> |
| | | </el-form-item> |
| | | <el-form-item> |
| | | <el-button type="primary" @click="manyAnalysisAudio" icon="el-icon-video-play" plain size="mini">批量分析</el-button> |
| | | <el-button type="danger" @click="deleteManyAudio" icon="el-icon-delete" plain size="mini">批量删除</el-button> |
| | | <el-upload |
| | | style="display: inline-block;margin-left: 10px" |
| | | action="/api-sa/v1/audio/upload" |
| | | :on-change="selFile" |
| | | accept=".mp3,.wav" |
| | | :show-file-list="false" |
| | | :on-success="upSuccess" |
| | | > |
| | | <el-button size="small" type="primary">点击上传</el-button> |
| | | </el-upload> |
| | | </el-form-item> |
| | | </el-form> |
| | | </div> |
| | | <div class="right"> |
| | | <el-tabs v-model="activeName"> |
| | | <el-tab-pane label="已上传" name="first"> |
| | | <div> |
| | | <el-table :data="pageInfo.audioList" border @selection-change="selAudio"> |
| | | <el-table-column label='全选' type="selection" align="center" /> |
| | | <el-table-column prop="name" label="文件名" min-width="200px" align="center" /> |
| | | <el-table-column prop="size" label="大小" align="center" /> |
| | | <el-table-column prop="occurrenceTime" label="上传时间" align="center" /> |
| | | <el-table-column prop="audioStatus" label="处理状态" align="center" > |
| | | <template slot-scope="scope"> |
| | | <span v-if="scope.row.audioStatus===0" style="color:wheat">上传中</span> |
| | | <span v-else-if="scope.row.audioStatus===1" style="color: blue">上传成功</span> |
| | | <span v-else-if="scope.row.audioStatus===2" style="color: cyan">处理中</span> |
| | | <span v-else-if="scope.row.audioStatus===3" style="color: green">处理完成</span> |
| | | <span v-else-if="scope.row.audioStatus===4" style="color: red">处理失败</span> |
| | | </template> |
| | | </el-table-column> |
| | | <el-table-column label="操作" align="center" > |
| | | <template slot-scope="scope"> |
| | | <el-button icon="el-icon-video-play" @click="analysisAudio(scope.row.ID)" type="text"></el-button> |
| | | <el-button icon="el-icon-delete" type="text" @click="deleteAudio(scope.row.ID)"></el-button> |
| | | </template> |
| | | </el-table-column> |
| | | </el-table> |
| | | <div class="pagination"> |
| | | <div class="total">共计{{pageInfo.total}}条记录 第{{pageData.page}}/{{lastPage}}页</div> |
| | | <div class="page"> |
| | | <el-pagination |
| | | background |
| | | @size-change="handleSizeChange" |
| | | @current-change="handleCurrentChange" |
| | | :current-page.sync="pageData.page" |
| | | :page-size="pageData.pageSize" |
| | | layout="prev, pager, next,sizes, jumper" |
| | | :total="pageInfo.total"> |
| | | </el-pagination> |
| | | </div> |
| | | </div> |
| | | <el-row type="flex" justify="center"> |
| | | <el-col :span="23"> |
| | | <el-card style="margin-top: 20px;height: 85vh"> |
| | | <div class="left"> |
| | | <el-form :inline="true" class="demo-form-inline"> |
| | | <el-form-item label=""> |
| | | <el-input v-model.lazy="keyword" placeholder="请输入搜索内容" suffix-icon="el-icon-search" size="small"></el-input> |
| | | </el-form-item> |
| | | <el-form-item> |
| | | <el-button type="primary" @click="manyAnalysisAudio" icon="el-icon-video-play" plain size="mini">批量分析</el-button> |
| | | <el-button type="danger" @click="deleteManyAudio" icon="el-icon-delete" plain size="mini">批量删除</el-button> |
| | | <el-upload |
| | | style="display: inline-block;margin-left: 10px" |
| | | action="#" |
| | | :auto-upload="false" |
| | | :on-change="selFile" |
| | | accept=".mp3,.wav" |
| | | :show-file-list="false" |
| | | :on-success="upSuccess" |
| | | > |
| | | <el-button size="small" type="primary">点击上传</el-button> |
| | | </el-upload> |
| | | </el-form-item> |
| | | </el-form> |
| | | </div> |
| | | </el-tab-pane> |
| | | <el-tab-pane label="正在上传" name="second"> |
| | | <!-- <el-skeleton style="width: 100%" :loading="isUpload" animated> |
| | | <template slot="template"> |
| | | <div style="padding: 14px;"> |
| | | <el-skeleton-item variant="h3" style="width: 100%;height: 40px" /> |
| | | </div> |
| | | </template> |
| | | </el-skeleton>--> |
| | | <div> |
| | | <el-skeleton animated :loading="isUpload"> |
| | | <template slot="template"> |
| | | <div style="padding: 14px;"> |
| | | <el-skeleton-item style="width: 100%;height: 40px" /> |
| | | <div class="right"> |
| | | <el-tabs v-model="activeName"> |
| | | <el-tab-pane label="已上传" name="first"> |
| | | <div> |
| | | <el-table :data="pageInfo.audioList" |
| | | border @selection-change="selAudio" |
| | | > |
| | | <el-table-column :selectable="selectable" label='全选' type="selection" align="center" /> |
| | | <el-table-column prop="name" label="文件名" min-width="200px" align="center" /> |
| | | <el-table-column prop="size" label="大小" align="center" /> |
| | | <el-table-column prop="occurrenceTime" label="上传时间" align="center" /> |
| | | <el-table-column prop="audioStatus" label="处理状态" align="center" > |
| | | <template slot-scope="scope"> |
| | | <span v-if="scope.row.audioStatus===0" style="color:wheat">上传中</span> |
| | | <span v-else-if="scope.row.audioStatus===1" style="color: blue">上传成功</span> |
| | | <span v-else-if="scope.row.audioStatus===2" style="color: cyan">处理中</span> |
| | | <span v-else-if="scope.row.audioStatus===3" style="color: green">处理完成</span> |
| | | <span v-else-if="scope.row.audioStatus===4" style="color: red">处理失败</span> |
| | | </template> |
| | | </el-table-column> |
| | | <el-table-column label="操作" align="center" > |
| | | <template slot-scope="scope"> |
| | | <el-tooltip class="item" effect="dark" content="下载" placement="bottom"> |
| | | <el-button icon="el-icon-download" @click="downloadAudio(scope.row.ID)" type="text"></el-button> |
| | | </el-tooltip> |
| | | <el-tooltip class="item" effect="dark" content="分析" placement="bottom"> |
| | | <el-button icon="el-icon-video-play" @click="analysisAudio(scope.row.ID)" type="text"></el-button> |
| | | </el-tooltip> |
| | | <el-tooltip v-if="scope.row.audioStatus!==3" class="item" effect="dark" content="删除" placement="bottom"> |
| | | <el-button icon="el-icon-delete" type="text" @click="deleteAudio(scope.row.ID)"></el-button> |
| | | </el-tooltip> |
| | | </template> |
| | | </el-table-column> |
| | | </el-table> |
| | | <div class="pagination"> |
| | | <div class="total">共计{{pageInfo.total}}条记录 第{{pageData.page}}/{{lastPage}}页</div> |
| | | <div class="page"> |
| | | <el-pagination |
| | | background |
| | | @size-change="handleSizeChange" |
| | | @current-change="handleCurrentChange" |
| | | :current-page.sync="pageData.page" |
| | | :page-size="pageData.pageSize" |
| | | layout="prev, pager, next,sizes, jumper" |
| | | :total="pageInfo.total"> |
| | | </el-pagination> |
| | | </div> |
| | | </div> |
| | | </div> |
| | | </template> |
| | | </el-skeleton> |
| | | </el-tab-pane> |
| | | <el-tab-pane label="正在上传" name="second"> |
| | | <!-- <el-skeleton style="width: 100%" :loading="isUpload" animated> |
| | | <template slot="template"> |
| | | <div style="padding: 14px;"> |
| | | <el-skeleton-item variant="h3" style="width: 100%;height: 40px" /> |
| | | </div> |
| | | </template> |
| | | </el-skeleton>--> |
| | | <div v-if="progressLoad"> |
| | | <div style="padding: 14px;" class="right-progress"> |
| | | <div class="p-left">上传速度:{{ this.speed }}</div> |
| | | <div class="p-right">预计时间:{{ this.leftTime }}</div> |
| | | </div> |
| | | <el-progress :color="customColors" :text-inside="true" :stroke-width="26" :percentage="percentage"></el-progress> |
| | | </div> |
| | | </el-tab-pane> |
| | | </el-tabs> |
| | | </div> |
| | | </el-tab-pane> |
| | | </el-tabs> |
| | | </div> |
| | | </el-card> |
| | | </el-col> |
| | | </el-row> |
| | | </div> |
| | | </template> |
| | | |
| | | <script> |
| | | import {audioListApi,processAudioApi,deleteAudioApi,batchProcessAudioApi,batchDeleteAudioApi} from '@/api'; |
| | | import {request} from "@/utils"; |
| | | import axios from 'axios'; |
| | | let timer= null; |
| | | export default { |
| | | name: "index", |
| | | data(){ |
| | | return { |
| | | percentage:0, |
| | | speed:0, |
| | | leftTime:0, |
| | | progressLoad:false, |
| | | isUpload:false, |
| | | activeName:'first', |
| | | keyword:'', |
| | |
| | | total:0 |
| | | }, |
| | | pageData:{page:1,pageSize:10}, |
| | | ids:[] |
| | | ids:[], |
| | | customColors: [ |
| | | {color: '#f56c6c', percentage: 20}, |
| | | {color: '#e6a23c', percentage: 40}, |
| | | {color: '#5cb87a', percentage: 60} |
| | | ] |
| | | } |
| | | }, |
| | | watch:{ |
| | |
| | | return Math.ceil(this.pageInfo.total/this.pageData.pageSize) |
| | | } |
| | | }, |
| | | beforeDestroy(){ |
| | | if(timer){ |
| | | window.clearInterval(timer); |
| | | } |
| | | }, |
| | | methods:{ |
| | | selectable(row){ |
| | | if(row.audioStatus===3){ |
| | | return false |
| | | }else{ |
| | | return true; |
| | | } |
| | | }, |
| | | async downloadAudio(id){ |
| | | window.location.href=`http://smartai.com:7013/api-sa/v1/audio/download?id=${id}` |
| | | }, |
| | | upSuccess({code}){ |
| | | if(code===200){ |
| | | this.$message.success('上传成功'); |
| | |
| | | this.isUpload=false; |
| | | }); |
| | | }, |
| | | selFile(file,fileList){ |
| | | async selFile(_,fileList){ |
| | | this.activeName='second'; |
| | | this.isUpload=true; |
| | | if(fileList.length>0){ |
| | | const file = fileList[0].raw; |
| | | const formData = new FormData(); |
| | | formData.append("file", file); |
| | | this.progressLoad = true; |
| | | this.percentage=0; |
| | | let lastTime = 0; // 上一次计算时间 |
| | | let lastSize = 0; // 上一次计算的文件大小 |
| | | try{ |
| | | const {code} = await axios.post("/api-sa/v1/audio/upload", formData, |
| | | { |
| | | onUploadProgress: (progressEvent) => { |
| | | console.log(progressEvent); |
| | | /*验证数据*/ |
| | | if (lastTime === 0) { |
| | | lastTime = new Date().getTime(); |
| | | lastSize = progressEvent.loaded; |
| | | return; |
| | | } |
| | | /*计算间隔*/ |
| | | let nowTime = new Date().getTime(); |
| | | let intervalTime = (nowTime - lastTime) / 1000; // 时间单位为毫秒,需转化为秒 |
| | | let intervalSize = progressEvent.loaded - lastSize; |
| | | /*重新赋值以便于下次计算*/ |
| | | lastTime = nowTime; |
| | | lastSize = progressEvent.loaded; |
| | | /*计算速度*/ |
| | | let speed = (intervalSize / intervalTime)/10; |
| | | let bSpeed = speed; // 保存以b/s为单位的速度值,方便计算剩余时间 |
| | | let units = "b/s"; // 单位名称 |
| | | if (speed / 1024 > 1) { |
| | | speed = speed / 1024; |
| | | units = "k/s"; |
| | | } |
| | | if (speed / 1024 > 1) { |
| | | speed = speed / 1024; |
| | | units = "M/s"; |
| | | } |
| | | let leftTime = (progressEvent.total) / bSpeed; |
| | | /*计算进度*/ |
| | | if(timer){ |
| | | window.clearInterval(timer); |
| | | } |
| | | timer=window.setInterval(()=>{ |
| | | if(this.percentage>=90){ |
| | | window.clearInterval(timer); |
| | | timer=null; |
| | | } |
| | | this.percentage+=parseInt(Math.random()*10); |
| | | speed=(Math.random()*500+500).toFixed(2) |
| | | this.speed = speed + "k/s"; |
| | | this.leftTime=(lastSize/speed/1000).toFixed(2)+ "秒"; |
| | | },500); |
| | | //= parseInt((progressEvent.loaded / progressEvent.total) * 100)-1; |
| | | // this.speed = speed.toFixed(2) + units; |
| | | //this.leftTime = leftTime.toFixed(2) + "秒"; |
| | | } |
| | | }); |
| | | if (code === 200) { |
| | | this.$message({ |
| | | message: "上传成功", |
| | | type: "success" |
| | | }); |
| | | } else { |
| | | this.$message({ |
| | | message: "上传失败", |
| | | type: "error", |
| | | }); |
| | | } |
| | | this.$nextTick(()=>{ |
| | | this.progressLoad = false; |
| | | this.percentage=100; |
| | | window.clearInterval(timer); |
| | | this.queryAudioList(); |
| | | }); |
| | | }catch (error) { |
| | | console.log(error); |
| | | } |
| | | } |
| | | }, |
| | | selAudio(rows){ |
| | | this.ids=rows.map(item=>item.ID); |
| | |
| | | this.pageInfo.audioList=data; |
| | | this.pageInfo.total=total; |
| | | } |
| | | /*this.pageInfo.audioList=[ |
| | | {filename:'0_20240519_xx_01.mp3',size:'879.88k',uploadAt:'2024-05-10 10:10:10',status:0}, |
| | | {filename:'0_20240519_xx_02.mp3',size:'879.88k',uploadAt:'2024-05-10 10:10:10',status:1}, |
| | | {filename:'0_20240519_xx_03.mp3',size:'879.88k',uploadAt:'2024-05-10 10:10:10',status:0}, |
| | | {filename:'0_20240519_xx_04.mp3',size:'879.88k',uploadAt:'2024-05-10 10:10:10',status:1}, |
| | | {filename:'0_20240519_xx_05.mp3',size:'879.88k',uploadAt:'2024-05-10 10:10:10',status:2}, |
| | | {filename:'0_20240519_xx_06.mp3',size:'879.88k',uploadAt:'2024-05-10 10:10:10',status:2}, |
| | | ]*/ |
| | | }, |
| | | analysisAudio(id){ |
| | | this.$confirm('是否进行音频分析, 是否继续?', '提示', { |
| | |
| | | position: relative; |
| | | top:-60px; |
| | | } |
| | | .right-progress{ |
| | | display: flex; |
| | | justify-content: space-around; |
| | | .p-left{ |
| | | width: 85%; |
| | | text-align: center; |
| | | position: relative; |
| | | left: 20px; |
| | | } |
| | | .p-right{ |
| | | width: 15%; |
| | | text-align: left; |
| | | } |
| | | } |
| | | .pagination{ |
| | | display: flex; |
| | | justify-content: space-between; |