Commit 61ec95a3 by haojie

文件切割

parent 76ce2739
...@@ -17,6 +17,7 @@ ...@@ -17,6 +17,7 @@
"test": "echo \"no test specified,work in process\"" "test": "echo \"no test specified,work in process\""
}, },
"dependencies": { "dependencies": {
"audiobuffer-to-wav": "^1.0.0",
"dayjs": "^1.10.6", "dayjs": "^1.10.6",
"default-passive-events": "^2.0.0", "default-passive-events": "^2.0.0",
"js-cookie": "^3.0.1", "js-cookie": "^3.0.1",
......
...@@ -7,6 +7,8 @@ import { useStore } from 'vuex'; ...@@ -7,6 +7,8 @@ import { useStore } from 'vuex';
import config from '@/config/style'; import config from '@/config/style';
import { useREM } from '@/utils/rem'; import { useREM } from '@/utils/rem';
import { devicePixelRatio } from '@/utils/init'; import { devicePixelRatio } from '@/utils/init';
import { injectWindow } from './utils/pyqt';
import { show_message } from './utils/tool';
// 注册rem事件 // 注册rem事件
useREM(); useREM();
...@@ -26,10 +28,26 @@ const mode = computed(() => { ...@@ -26,10 +28,26 @@ const mode = computed(() => {
// document.removeEventListener('contextmenu', contextMenuListener); // document.removeEventListener('contextmenu', contextMenuListener);
// }; // };
const onMessage = (params: string) => {
console.log('接收到值了');
console.log(params);
if (typeof params === 'string') {
params = JSON.parse(params);
}
if (Object.keys(params).length) {
show_message(params.value, params.type);
} else {
console.log('没有数据');
}
};
onMounted(() => { onMounted(() => {
store.dispatch('setting/changeTheme', { ...config }); store.dispatch('setting/changeTheme', { ...config });
devicePixelRatio(); devicePixelRatio();
// 全局注入showMessage提示
injectWindow('onMessage', onMessage);
// 阻止右键事件 // 阻止右键事件
// document.addEventListener('contextmenu', contextMenuListener); // document.addEventListener('contextmenu', contextMenuListener);
}); });
......
...@@ -8,7 +8,7 @@ ...@@ -8,7 +8,7 @@
ref="videoFirst" ref="videoFirst"
class="video-default" class="video-default"
:src="item.url" :src="item.url"
:loop="loop" :loop="getLoopStatus(item)"
@canplay="mainVideoCanplay(index)" @canplay="mainVideoCanplay(index)"
@ended="firstVideoEnded(index)" @ended="firstVideoEnded(index)"
></video> ></video>
...@@ -107,6 +107,17 @@ const secondVideoVolume = ref(initVolume); ...@@ -107,6 +107,17 @@ const secondVideoVolume = ref(initVolume);
let interval = null; let interval = null;
// 是否循环播放
const getLoopStatus = (item: any) => {
if (loop.value) {
return true;
} else {
return false;
// loop为false
// if
}
};
// 离开前先关闭弹窗 // 离开前先关闭弹窗
onBeforeRouteLeave((to, from, next) => { onBeforeRouteLeave((to, from, next) => {
confirmVisible.value = false; confirmVisible.value = false;
...@@ -160,7 +171,22 @@ const mainVideoPlayStatus = (index: number) => { ...@@ -160,7 +171,22 @@ const mainVideoPlayStatus = (index: number) => {
// 下一个要播放的视频 // 下一个要播放的视频
const nextVideoToPlay = () => { const nextVideoToPlay = () => {
const { mainVideoList } = props; const { mainVideoList } = props;
return mainVideoList.findIndex((item: any) => item.url && !item.playEnd && !item.play); if (!loop.value) {
// 找到下一个要播放的
let nextIndex = mainVideoList.findIndex((item: any) => item.url && !item.playEnd && !item.play);
if (nextIndex !== -1) {
console.log('开始播放下一个主视频');
mainVideoPlayStatus(nextIndex);
videoFirst.value[nextIndex].play();
// 更新当前正在播放的video标签下标
emit('update:playMainIndex', nextIndex);
} else {
console.log(props.mainVideoList);
console.log('未找到下一条视频');
}
} else {
console.log('循环播放不需要找下一个视频');
}
}; };
// 主视频播放完毕 // 主视频播放完毕
...@@ -186,22 +212,7 @@ const firstVideoEnded = (index: number) => { ...@@ -186,22 +212,7 @@ const firstVideoEnded = (index: number) => {
videoValue: true, videoValue: true,
}); });
if (!loop.value) { nextVideoToPlay();
// 找到下一个要播放的
let nextIndex = nextVideoToPlay();
if (nextIndex !== -1) {
console.log('开始播放下一个主视频');
mainVideoPlayStatus(nextIndex);
videoFirst.value[nextIndex].play();
// 更新当前正在播放的video标签下标
emit('update:playMainIndex', nextIndex);
} else {
console.log(props.mainVideoList);
console.log('未找到下一条视频');
}
} else {
console.log('循环播放不需要找下一个视频');
}
} }
}; };
......
...@@ -24,6 +24,8 @@ ...@@ -24,6 +24,8 @@
.custom-real-upload-component { .custom-real-upload-component {
width: 572px; width: 572px;
height: 200px; height: 200px;
overflow-y: auto;
overflow-x: hidden;
.t-upload { .t-upload {
width: 100%; width: 100%;
height: 100%; height: 100%;
......
...@@ -50,7 +50,7 @@ export default defineComponent({ ...@@ -50,7 +50,7 @@ export default defineComponent({
const openpercentage = () => { const openpercentage = () => {
percentageInterval = setInterval(() => { percentageInterval = setInterval(() => {
fileList.value.forEach((item: any) => { fileList.value.forEach((item: any) => {
if (item.progress < 100 && !item.status) { if (item.progress < 99 && !item.status) {
item.progress += 1; item.progress += 1;
} }
}); });
...@@ -349,7 +349,7 @@ export default defineComponent({ ...@@ -349,7 +349,7 @@ export default defineComponent({
return () => ( return () => (
<div class="custom-multiple-upload"> <div class="custom-multiple-upload">
<div class="real-upload-content"> <div class="real-upload-content">
<div class="custom-real-upload-component"> <div class="custom-real-upload-component narrow-scrollbar">
<div v-show={Curfile.status == 0 || !fileList.value.length}>{notUploadHtml()}</div> <div v-show={Curfile.status == 0 || !fileList.value.length}>{notUploadHtml()}</div>
<div v-show={Curfile.status != 0}>{UploadingHtml()}</div> <div v-show={Curfile.status != 0}>{UploadingHtml()}</div>
</div> </div>
......
...@@ -15,7 +15,8 @@ export default function () { ...@@ -15,7 +15,8 @@ export default function () {
const currentConfuseId = ref(''); const currentConfuseId = ref('');
const openConfuseInterval = () => { const openConfuseInterval = () => {
confuseInterval.value = window.setTimeout(() => { console.log('开启轮询,洗稿回调');
confuseInterval.value = window.setInterval(() => {
currentStartConfuseBack(currentConfuseId.value); currentStartConfuseBack(currentConfuseId.value);
}, 3000); }, 3000);
}; };
...@@ -33,6 +34,7 @@ export default function () { ...@@ -33,6 +34,7 @@ export default function () {
// //
let res: any = await liveContentRegenerate(data); let res: any = await liveContentRegenerate(data);
if (res.code == 0) { if (res.code == 0) {
console.log('洗稿提交成功');
// 打开定时器 // 打开定时器
openConfuseInterval(); openConfuseInterval();
} }
...@@ -48,8 +50,12 @@ export default function () { ...@@ -48,8 +50,12 @@ export default function () {
task_id: id, task_id: id,
}); });
if (res.code == 0 && res.data.length) { if (res.code == 0 && res.data.length) {
console.log('洗稿回调成功');
closeConfuseInterval(); closeConfuseInterval();
confuseList.value = res.data; confuseList.value = res.data;
} else {
console.log('洗稿还没有回调', id);
console.log(res.data);
} }
} catch (e) { } catch (e) {
console.log(e); console.log(e);
......
...@@ -272,11 +272,12 @@ export const processTextCallback = () => { ...@@ -272,11 +272,12 @@ export const processTextCallback = () => {
let file = await audioMerge(list); let file = await audioMerge(list);
if (file) { if (file) {
// 开始切割 // 开始切割
let split_list = await splitAudio(file, 5 * 1024 * 1024); let split_list = await splitAudio(file, 300);
// 合并后的文件上传
if (split_list && split_list.length) { if (split_list && split_list.length) {
let result = await uploadToAly(split_list); let result = await uploadToAly(split_list);
console.log('上传完毕'); console.log('上传完毕');
console.log(result.length); console.log(result);
// 是否一维数组 // 是否一维数组
if (dimensional) { if (dimensional) {
return result; return result;
...@@ -285,6 +286,7 @@ export const processTextCallback = () => { ...@@ -285,6 +286,7 @@ export const processTextCallback = () => {
} }
} }
} else { } else {
console.log('没有文件');
} }
}; };
...@@ -394,6 +396,7 @@ export const processTextCallback = () => { ...@@ -394,6 +396,7 @@ export const processTextCallback = () => {
if (createLiveInfo.value[createLiveKeys.isDisorganize]) { if (createLiveInfo.value[createLiveKeys.isDisorganize]) {
await startConfuse(); await startConfuse();
} else { } else {
console.log('不用洗稿');
loading.value = false; loading.value = false;
submitSuccessed(); submitSuccessed();
} }
...@@ -466,5 +469,6 @@ export const processTextCallback = () => { ...@@ -466,5 +469,6 @@ export const processTextCallback = () => {
currentConfuseId, currentConfuseId,
confuseList, confuseList,
currentStartConfuse, currentStartConfuse,
audioStart,
}; };
}; };
...@@ -23,7 +23,7 @@ import { onBeforeUnmount, onMounted, ref, watch } from 'vue'; ...@@ -23,7 +23,7 @@ import { onBeforeUnmount, onMounted, ref, watch } from 'vue';
import AddVideoPlay from '@/components/AddVideoPlay.vue'; import AddVideoPlay from '@/components/AddVideoPlay.vue';
import { getLiveDetail, closeLiveTask } from '@/utils/api/userApi'; import { getLiveDetail, closeLiveTask } from '@/utils/api/userApi';
import { useRoute, useRouter } from 'vue-router'; import { useRoute, useRouter } from 'vue-router';
import { show_message, isDev, DataType } from '@/utils/tool'; import { show_message, isDev, DataType, randomInt, randomIntFormList } from '@/utils/tool';
import { callPyjsInWindow, injectWindow } from '@/utils/pyqt'; import { callPyjsInWindow, injectWindow } from '@/utils/pyqt';
import { getliveTaskReply, getUserCookie, liveTts, getLiveTaskInfo, liveTaskRegenerate } from '@/utils/api/userApi'; import { getliveTaskReply, getUserCookie, liveTts, getLiveTaskInfo, liveTaskRegenerate } from '@/utils/api/userApi';
import routerConfig from '@/router/tool'; import routerConfig from '@/router/tool';
...@@ -98,6 +98,7 @@ const mainVideoList = ref([ ...@@ -98,6 +98,7 @@ const mainVideoList = ref([
show: true, show: true,
total: 0, total: 0,
videoIndex: null, videoIndex: null,
loop: false,
}, },
{ {
name: 'mainVideo2', name: 'mainVideo2',
...@@ -109,6 +110,7 @@ const mainVideoList = ref([ ...@@ -109,6 +110,7 @@ const mainVideoList = ref([
show: false, show: false,
total: 0, total: 0,
videoIndex: null, videoIndex: null,
loop: false,
}, },
]); ]);
...@@ -193,6 +195,61 @@ const submitConfuse = async () => { ...@@ -193,6 +195,61 @@ const submitConfuse = async () => {
} }
}; };
// 找一个已经播放完毕的视频,加入video标签中
const findOneVideoInit = () => {
// 是否需要执行
let status = false;
let videoTagIndex = mainVideoList.value.findIndex((item: any, index: number) => index !== currentPlayMainIndex.value);
if (videoTagIndex !== -1) {
let hideVideo = mainVideoList.value[videoTagIndex];
// 隐藏的视频已经播放结束
if (!hideVideo.play && hideVideo.playEnd) {
status = true;
}
}
// start
if (status) {
// 当前显示的视频
let item = mainVideoList.value[currentPlayMainIndex.value];
// 主视频列表中的行
let videoInfo = realVideoList.value[item.videoIndex];
// 找到所有已经播放完毕的主视频
let playEndVideos = realVideoList.value.map((row: any, index: number) => {
if (row.remove && item.result && item.status) {
return index;
}
});
console.log(playEndVideos);
if (playEndVideos.length) {
if (playEndVideos.length === 1) {
console.log('只有一条视频播放完毕,重新播放该视频');
// 循环播放
item.loop = true;
} else {
// 多条视频
// 随机下标
let num = randomIntFormList(playEndVideos);
console.log(`初始化第${num}个视频`);
// 链接是否一致
if (realVideoList.value[num].result === item.url) {
// 循环播放
item.loop = true;
console.log('链接一致,等待重新播放');
} else {
// 更新当前视频标签的链接和状态
item.play = false;
item.playEnd = false;
item.videoIndex = num;
item.url = realVideoList.value[num].result;
console.log('成功加入队列');
}
}
} else {
console.log('主视频列表中没有已经播放完毕的视频');
}
}
};
// 当前播放进度变化 // 当前播放进度变化
const currentTimeChange = (index: number, value: number) => { const currentTimeChange = (index: number, value: number) => {
let row = mainVideoList.value[index]; let row = mainVideoList.value[index];
...@@ -209,11 +266,17 @@ const currentTimeChange = (index: number, value: number) => { ...@@ -209,11 +266,17 @@ const currentTimeChange = (index: number, value: number) => {
liveDetail.value.is_disorganize && liveDetail.value.is_disorganize &&
liveDetail.value.type == scriptTypeText liveDetail.value.type == scriptTypeText
) { ) {
console.log(row.videoIndex, '当前videoIndex');
currentVideoRow.confuse = CONFUSE_STATUS.CONFUSE_STATUS_PROGRESS; currentVideoRow.confuse = CONFUSE_STATUS.CONFUSE_STATUS_PROGRESS;
console.log('直播开始洗稿'); console.log('直播开始洗稿');
// 开始洗稿 // 开始洗稿
submitConfuse(); submitConfuse();
} }
// 判断是否需要取之前的主视频
if (currentEsidueTime < 20 && typeof currentPlayMainIndex.value === 'number') {
// findOneVideoInit();
}
}; };
// 互动视频播放结束 // 互动视频播放结束
......
...@@ -162,6 +162,7 @@ ...@@ -162,6 +162,7 @@
v-model="mp3UrlList" v-model="mp3UrlList"
:config="ossConfig" :config="ossConfig"
label="选择音频" label="选择音频"
accept="wav"
@change="createUploadFile" @change="createUploadFile"
></MultipleUpload> ></MultipleUpload>
</div> </div>
...@@ -508,6 +509,7 @@ watch( ...@@ -508,6 +509,7 @@ watch(
currentOption.value = scriptTypeText; currentOption.value = scriptTypeText;
audioScriptList.value = []; audioScriptList.value = [];
textScriptList.value = []; textScriptList.value = [];
isDisorganize.value = false;
scriptTypeChange(scriptTypeText + ''); scriptTypeChange(scriptTypeText + '');
}, },
); );
......
...@@ -85,8 +85,19 @@ import { useLiveInfoSubmit } from '@/hooks/useStoreCommit'; ...@@ -85,8 +85,19 @@ import { useLiveInfoSubmit } from '@/hooks/useStoreCommit';
import { processTextCallback } from '@/hooks/useScript'; import { processTextCallback } from '@/hooks/useScript';
import CustomException from '@/utils/error'; import CustomException from '@/utils/error';
import { v4 } from 'uuid'; import { v4 } from 'uuid';
const { loading, initNum, currentSetp, openInterval, filterFiled, backHome, submitSuccessed, submit, initCreateStore } = import { splitAudio, splitFile } from '@/utils/audio';
processTextCallback(); const {
loading,
initNum,
currentSetp,
audioStart,
openInterval,
filterFiled,
backHome,
submitSuccessed,
submit,
initCreateStore,
} = processTextCallback();
const [commitInfo] = useLiveInfoSubmit(); const [commitInfo] = useLiveInfoSubmit();
const store = useStore(); const store = useStore();
...@@ -356,8 +367,7 @@ const editAudioSave = async () => { ...@@ -356,8 +367,7 @@ const editAudioSave = async () => {
id: route.query.id, id: route.query.id,
}); });
} }
// 回首页 submitSuccessed('');
backHome();
} }
loading.value = false; loading.value = false;
} catch (e) { } catch (e) {
...@@ -492,8 +502,23 @@ onBeforeMount(() => { ...@@ -492,8 +502,23 @@ onBeforeMount(() => {
}); });
// 缓存进入 // 缓存进入
onActivated(() => { onActivated(async () => {
enterPageEvent(); enterPageEvent();
// 测试
let list = [
// 小文件
'http://nls-cloud-cn-shanghai.oss-cn-shanghai.aliyuncs.com/jupiter-flow/tmp/e56d8750eb3a44f9930f73703489acb1.wav?Expires=1692087730&OSSAccessKeyId=LTAIUpwNp2H7pBG5&Signature=FtKSld5Dn55po9GyTm%2BefRKmPqw%3D',
'http://nls-cloud-cn-shanghai.oss-cn-shanghai.aliyuncs.com/jupiter-flow/tmp/e56d8750eb3a44f9930f73703489acb1.wav?Expires=1692087730&OSSAccessKeyId=LTAIUpwNp2H7pBG5&Signature=FtKSld5Dn55po9GyTm%2BefRKmPqw%3D',
'http://nls-cloud-cn-shanghai.oss-cn-shanghai.aliyuncs.com/jupiter-flow/tmp/e56d8750eb3a44f9930f73703489acb1.wav?Expires=1692087730&OSSAccessKeyId=LTAIUpwNp2H7pBG5&Signature=FtKSld5Dn55po9GyTm%2BefRKmPqw%3D',
'http://nls-cloud-cn-shanghai.oss-cn-shanghai.aliyuncs.com/jupiter-flow/tmp/e56d8750eb3a44f9930f73703489acb1.wav?Expires=1692087730&OSSAccessKeyId=LTAIUpwNp2H7pBG5&Signature=FtKSld5Dn55po9GyTm%2BefRKmPqw%3D',
// 大文件
// 'http://yunyi-live.oss-cn-hangzhou.aliyuncs.com/upload/15/2023-08-072cfde637-5487-47fc-9cea-3e984b92ee6f.wav',
];
audioStart(list);
// list = await splitFile(list[0], 300);
console.log(list);
}); });
// 路由离开前保存query // 路由离开前保存query
......
...@@ -27,7 +27,7 @@ ...@@ -27,7 +27,7 @@
</template> </template>
<div class="digtal-people-hover-tool"> <div class="digtal-people-hover-tool">
<Button size="13" theme="dark" @click="onEdit(item)">编辑</Button> <Button size="13" theme="dark" @click="onEdit(item)">编辑</Button>
<Button size="13" theme="dark">下载</Button> <Button size="13" theme="dark" @click="downLoadVideo(item)">下载</Button>
<Button size="13" theme="dark" @click="onDelete(item)">删除</Button> <Button size="13" theme="dark" @click="onDelete(item)">删除</Button>
</div> </div>
</div> </div>
...@@ -66,8 +66,8 @@ import Button from '@/components/Button.vue'; ...@@ -66,8 +66,8 @@ import Button from '@/components/Button.vue';
import { useRouter } from 'vue-router'; import { useRouter } from 'vue-router';
import routerConfig from '@/router/tool'; import routerConfig from '@/router/tool';
import { onUpdateLiveTask } from '@/service/Common'; import { onUpdateLiveTask } from '@/service/Common';
import { getLiveTask, deleteLiveTask } from '@/utils/api/userApi'; import { getLiveTask, deleteLiveTask, liveVideoDownload } from '@/utils/api/userApi';
import { isDev, show_message } from '@/utils/tool'; import { downloadFiles, isDev, show_message } from '@/utils/tool';
import { callPyjsInWindow, injectWindow } from '@/utils/pyqt'; import { callPyjsInWindow, injectWindow } from '@/utils/pyqt';
import { jumpToCreateLivePage } from '@/router/jump'; import { jumpToCreateLivePage } from '@/router/jump';
...@@ -110,6 +110,39 @@ const beforePageJump = (item: any) => { ...@@ -110,6 +110,39 @@ const beforePageJump = (item: any) => {
return params; return params;
}; };
const getVideoList = async (id: any) => {
try {
let res: any = await liveVideoDownload(id);
if (res.code == 0) {
let list = [];
res.data.forEach((item: any) => {
list.push(item.url);
});
return list;
}
return false;
} catch (e) {
console.log(e);
return false;
}
};
// 下载数字人视频
const downLoadVideo = async (item: any) => {
let list = await getVideoList(item.id);
if (list) {
// downloadFiles(list);
// 通知python合并视频并
callPyjsInWindow('downLoadVideoToLocal', {
list: list,
id: item.id,
});
show_message('正在下载中,请等待', 'info');
} else {
show_message('没有视频');
}
};
const startLive = (item: any) => { const startLive = (item: any) => {
let params = beforePageJump(item); let params = beforePageJump(item);
if (params) { if (params) {
......
...@@ -369,3 +369,14 @@ export const liveTaskRegenerate = (id: any, data: any) => { ...@@ -369,3 +369,14 @@ export const liveTaskRegenerate = (id: any, data: any) => {
}, },
}); });
}; };
// 直播下载
export const liveVideoDownload = (id: any) => {
const header = getHeader();
return request.get(`/api/live/task/${id}/download`, {
params: {},
headers: {
...header,
},
});
};
import { show_message } from './tool'; import { alyOssUpload, getFileSuffix, show_message } from './tool';
import { v4 } from 'uuid'; import { v4 } from 'uuid';
import audiobufferToWav from 'audiobuffer-to-wav';
import request from '@/utils/upLoadRequest';
export const createAudioContext = () => { export const createAudioContext = () => {
return new (window.AudioContext || window.webkitAudioContext)(); return new (window.AudioContext || window.webkitAudioContext)();
}; };
...@@ -36,8 +38,8 @@ export async function audioMerge(filePaths) { ...@@ -36,8 +38,8 @@ export async function audioMerge(filePaths) {
// 使用 Promise 依次解码和添加音频数据到 buffers 数组 // 使用 Promise 依次解码和添加音频数据到 buffers 数组
await Promise.all( await Promise.all(
filePaths.map(async (filePath) => { filePaths.map(async (filePath) => {
const response = await fetch(filePath); const response = await request.get(filePath, { responseType: 'arraybuffer' });
const arrayBuffer = await response.arrayBuffer(); const arrayBuffer = response;
const audioBuffer = await audioContext.decodeAudioData(arrayBuffer); const audioBuffer = await audioContext.decodeAudioData(arrayBuffer);
return audioBuffer; return audioBuffer;
...@@ -73,6 +75,7 @@ export async function audioMerge(filePaths) { ...@@ -73,6 +75,7 @@ export async function audioMerge(filePaths) {
// 导出合并后的音频数据为 WAV 文件 // 导出合并后的音频数据为 WAV 文件
const mergedData = exportBufferAsWav(mergedBuffer); const mergedData = exportBufferAsWav(mergedBuffer);
const blob = new Blob([mergedData], { type: 'audio/wav' }); const blob = new Blob([mergedData], { type: 'audio/wav' });
console.log('合并完成', blob);
return blob; return blob;
} catch (error) { } catch (error) {
console.error('音频文件合并失败:', error); console.error('音频文件合并失败:', error);
...@@ -80,54 +83,98 @@ export async function audioMerge(filePaths) { ...@@ -80,54 +83,98 @@ export async function audioMerge(filePaths) {
} }
// 切割音频文件 // 切割音频文件
export async function splitAudio(fileBlob: Blob, splitSize: number) { // export async function splitAudio(fileBlob: Blob, splitSize: number) {
if (fileBlob.size < splitSize) { // if (fileBlob.size < splitSize) {
return [fileBlob]; // return [fileBlob];
} // }
try { // try {
const MAX_CHUNK_SIZE = splitSize; // const MAX_CHUNK_SIZE = splitSize;
const newChunks = []; // const newChunks = [];
const asyncReadFile = (file, offset) => { // const asyncReadFile = (file, offset) => {
return new Promise((resolve, reject) => { // return new Promise((resolve, reject) => {
const reader = new FileReader(); // const reader = new FileReader();
reader.onload = (event) => { // reader.onload = (event) => {
const binaryData = event.target.result; // const binaryData = event.target.result;
const chunkName = v4(); // const chunkName = v4();
const binaryFile = new File([binaryData], chunkName, { type: file.type }); // const binaryFile = new File([binaryData], chunkName, { type: file.type });
resolve(binaryFile); // resolve(binaryFile);
}; // };
reader.onerror = () => { // reader.onerror = () => {
reject(new Error('File read error.')); // reject(new Error('File read error.'));
}; // };
const chunk = file.slice(offset, offset + MAX_CHUNK_SIZE); // const chunk = file.slice(offset, offset + MAX_CHUNK_SIZE);
reader.readAsArrayBuffer(chunk); // reader.readAsArrayBuffer(chunk);
}); // });
}; // };
for (const file of [fileBlob]) { // for (const file of [fileBlob]) {
const fileSize = file.size; // const fileSize = file.size;
let offset = 0; // let offset = 0;
while (offset < fileSize) { // while (offset < fileSize) {
const chunkSize = Math.min(MAX_CHUNK_SIZE, fileSize - offset); // const chunkSize = Math.min(MAX_CHUNK_SIZE, fileSize - offset);
const binaryFile = await asyncReadFile(file, offset); // const binaryFile = await asyncReadFile(file, offset);
newChunks.push(binaryFile); // newChunks.push(binaryFile);
offset += chunkSize; // offset += chunkSize;
} // }
// }
// console.log('切割后的文件', newChunks);
// return newChunks;
// } catch (e) {
// show_message('音频切割失败');
// }
// }
export const splitAudio = async (audioBlob: Blob, duration: number) => {
const audioContext = new AudioContext();
const audioBufferList = [];
// 将 audioBlob 转换成 ArrayBuffer
const arrayBuffer = await audioBlob.arrayBuffer();
// 解码音频文件
const audioBuffer = await audioContext.decodeAudioData(arrayBuffer);
// 计算需要切割的片段数量
const totalSegments = Math.ceil(audioBuffer.duration / duration);
for (let i = 0; i < totalSegments; i++) {
// 计算切割起点和终点的时间
const startTime = i * duration;
const endTime = Math.min(startTime + duration, audioBuffer.duration);
// 计算切割起点和终点的音频帧位置
const startFrame = Math.floor(startTime * audioBuffer.sampleRate);
const endFrame = Math.floor(endTime * audioBuffer.sampleRate);
// 计算切割后的音频帧数量
const frameCount = endFrame - startFrame;
// 创建一个新的 AudioBuffer 来存储切割后的音频数据
const slicedBuffer = audioContext.createBuffer(audioBuffer.numberOfChannels, frameCount, audioBuffer.sampleRate);
// 复制切割后的音频数据到新的 AudioBuffer 中
for (let channel = 0; channel < audioBuffer.numberOfChannels; channel++) {
const sourceData = audioBuffer.getChannelData(channel).subarray(startFrame, endFrame);
slicedBuffer.copyToChannel(sourceData, channel);
} }
return newChunks;
} catch (e) { // 将切割后的音频 Buffer 添加到列表中
show_message('音频切割失败'); const wavData = audiobufferToWav(slicedBuffer);
const blob = new Blob([wavData], { type: 'audio/wav' });
audioBufferList.push(blob);
} }
}
return audioBufferList;
};
// 导出音频缓冲区为 WAV 文件 // 导出音频缓冲区为 WAV 文件
function exportBufferAsWav(audioBuffer) { function exportBufferAsWav(audioBuffer) {
......
...@@ -2,27 +2,44 @@ import axios from 'axios'; ...@@ -2,27 +2,44 @@ import axios from 'axios';
import { store } from '@/store/index'; import { store } from '@/store/index';
import router from '@/router'; import router from '@/router';
import { show_message, isDev } from './tool'; import { show_message, isDev } from './tool';
import { callPyjsInWindow } from './pyqt';
const error_messaage = '请求错误'; const error_messaage = '请求错误';
const getBaseUrl = () => { const getBaseUrl = async () => {
if (isDev()) { if (isDev()) {
// //
// return 'http://156.247.11.21:92/'; // return 'http://156.247.11.21:92/';
return ''; return '';
} }
return 'http://video-assistant.test'; // 默认线上地址
// return 'http://156.247.11.21:92/'; let defaultUrl = 'http://video-assistant.test';
// 从python获取请求地址
try {
const url = await callPyjsInWindow('getDomain', '', true);
if (url) {
console.log('获取到线上地址了', url);
return url;
}
return defaultUrl;
} catch (e) {
console.log('获取域名失败');
console.log(e);
return defaultUrl;
}
}; };
const instance = axios.create({ const instance = axios.create({
baseURL: getBaseUrl(), baseURL: '',
// withCredentials: false, // withCredentials: false,
withCredentials: isDev() ? true : false, withCredentials: isDev() ? true : false,
}); });
// 请求头 // 请求拦截
instance.interceptors.request.use((config) => { instance.interceptors.request.use(async (config) => {
const baseUrl = await getBaseUrl();
// 更新请求的baseURL
config.baseURL = baseUrl;
return config; return config;
}); });
......
import { MessagePlugin, RequestMethodResponse } from 'tdesign-vue-next'; import { MessagePlugin, RequestMethodResponse } from 'tdesign-vue-next';
import request from '@/utils/upLoadRequest'; import request from '@/utils/upLoadRequest';
// import JSZip from 'jszip';
// import { saveAs } from 'file-saver';
/** /**
* 函数节流处理 * 函数节流处理
...@@ -282,3 +284,58 @@ export const dimensionalConvert = (list: any[]) => { ...@@ -282,3 +284,58 @@ export const dimensionalConvert = (list: any[]) => {
} }
return convertList; return convertList;
}; };
export const getFile = (url: string) => {
return new Promise((resolve, reject) => {
request
.get(url, {
responseType: 'blob',
})
.then((res) => {
resolve(res);
})
.catch((error) => {
reject(error);
});
});
};
// 用户下载文件
// export const downloadFiles = (list: string[]) => {
// let zip = new JSZip();
// const promises = [];
// for (const item of list) {
// const promise = getFile(item).then((data) => {
// // 获取文件名和后缀
// const filenameWithExtension = item.substring(item.lastIndexOf('/') + 1); // 获取完整文件名(包括后缀)
// const filename = filenameWithExtension.substring(0, filenameWithExtension.lastIndexOf('.')); // 提取文件名
// const extension = filenameWithExtension.substring(filenameWithExtension.lastIndexOf('.') + 1); // 提取后缀
// // 下载文件, 并存成ArrayBuffer对象
// zip.file(filename + `.${extension}`, data, { binary: true }); // 逐个添加文件,需要加后缀".png"
// });
// promises.push(promise);
// }
// let zipname = 'video.zip';
// Promise.all(promises)
// .then((res) => {
// zip.generateAsync({ type: 'blob' }).then((content) => {
// // 生成二进制流
// saveAs(content, zipname); // 利用file-saver保存文件 自定义文件名
// show_message('导出成功', 'success');
// });
// })
// .catch((res) => {
// show_message('导出失败');
// });
// };
// 取随机值
export const randomInt = (min: number, max: number) => {
return Math.floor(Math.random() * (max - min + 1)) + min;
};
// 从数组中随机取一个值
export const randomIntFormList = (list: any[]) => {
let index = randomInt(0, list.length - 1);
return list[index];
};
...@@ -12,8 +12,6 @@ import path from 'path'; ...@@ -12,8 +12,6 @@ import path from 'path';
import eslintPlugin from 'vite-plugin-eslint'; import eslintPlugin from 'vite-plugin-eslint';
export default defineConfig(({ command, mode }) => { export default defineConfig(({ command, mode }) => {
// https://m.coinwg.com 测试服务器
// https://tidrk.com/
let api = 'http://video-assistant.test'; let api = 'http://video-assistant.test';
return { return {
base: './', base: './',
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment