Ver Fonte

feat: electron添加文件上传功能&world生成过程上传map.stl文件

HeWang há 9 meses atrás
pai
commit
b8b1bce026
3 ficheiros alterados com 75 adições e 13 exclusões
  1. 36 2
      electron/main.js
  2. 2 1
      electron/preload.js
  3. 37 10
      src/views/ReportView.vue

+ 36 - 2
electron/main.js

@@ -6,6 +6,7 @@ import fs from 'fs';
 import axios from 'axios';
 import {resolve} from "node:dns";
 import {execSync} from "node:child_process";
+import * as url from "node:url";
 
 
 const __filename = fileURLToPath(import.meta.url);
@@ -124,7 +125,7 @@ ipcMain.handle('dialog:open', async (event, options = {}) => {
 
 ipcMain.on('docker-import', (event, filePath, tag) => {
     const command = 'bash /home/cicv/work/pji_desktop/docker_import/run_docker_import.sh ' + filePath + ' pji_nav ' + tag
-    console.log('导入算法镜像文件:', command);
+    console.log('Docker import command:', command);
     exec(command, (error, stdout, stderr) => {
         if (error) {
             console.error(`exec error: ${error}`);
@@ -261,7 +262,7 @@ ipcMain.handle('download-file', async (event, { url, fileName, savePath, overwri
 });
 
 
-// 监听从渲染进程传来的删除文件请求
+// 删除文件
 ipcMain.on('delete-file', (event, {fileName, savePath}) => {
     const filePath = path.join(savePath, fileName);
     // 检查文件是否存在
@@ -280,4 +281,37 @@ ipcMain.on('delete-file', (event, {fileName, savePath}) => {
     }
 });
 
+// 上传文件
+ipcMain.on('upload-file', (event, {filePath, uploadUrl}) => {
+    if (!fs.existsSync(filePath)) {
+        console.log("File does not exist");
+        event.reply('upload-file-response', { success: false, message: 'File does not exist' });
+        return;
+    }
+    // 读取文件
+    fs.readFile(filePath, async (err, data) => {
+        if(err) {
+            console.log("Error reading file:", err);
+            event.reply('upload-file-response', { success: false, message: err.message });
+            return;
+        }
 
+        // 创建formData对象
+        const formData = new FormData();
+        formData.append('file', new Blob([data]), path.basename(filePath));
+
+        try {
+            // 使用axios上传文件
+            const response = await axios.post(uploadUrl, formData, {
+                headers: {
+                    'Content-Type': 'multipart/form-data'
+                }
+            })
+            console.log('response', response)
+            event.reply('upload-file-response', { success: true, message: 'File uploaded successfully' });
+        } catch (err) {
+            console.log("Error uploading file:", err);
+            event.reply('upload-file-response', { success: false, message: err.message });
+        }
+    })
+});

+ 2 - 1
electron/preload.js

@@ -68,7 +68,8 @@ contextBridge.exposeInMainWorld('electronAPI', {
     },
     deleteFile: (fileName, savePath) => ipcRenderer.send('delete-file', {fileName, savePath}),
     onDeleteFileResponse: (callback) => ipcRenderer.once('delete-file-response', callback),
-
+    uploadFile: (filePath, uploadUrl) => ipcRenderer.send('upload-file', {filePath, uploadUrl}),
+    onUploadFileResponse: (callback) => ipcRenderer.once('upload-file-response', callback),
 });
 
 

+ 37 - 10
src/views/ReportView.vue

@@ -178,7 +178,7 @@
                 v-if="world_active == 2"
                 ref="upload"
                 class="upload-demo"
-                :action="uploadUrl"
+                :action="worldUploadUrl"
                 :limit="1"
                 :before-upload="beforeUpload"
                 :on-exceed="handleExceed"
@@ -274,7 +274,8 @@ const worldDialogVisible = ref(false)
 const simulationDialogVisible = ref(false)
 
 const upload = ref<UploadInstance>()
-const uploadUrl = ref<string>()
+const worldUploadUrl = ref<string>()
+const stlUploadUrl = ref<string>()
 
 const selectImageName = ref("")
 const imageNames = ref([])
@@ -325,14 +326,36 @@ const errorMessage = (response) => {
 
 //上传文件成功
 const uploadSuccess = (response, file, fileList) => {
-  world_active.value = 3
-  ElMessage({
-    message: "文件上传成功,请关闭对话框",
-    type: "success",
-    offset: 60
+  // 继续上传map.stl文件
+  uploadStlFile(() => {
+    // 更新步骤条状态
+    world_active.value = 3
+    ElMessage({
+      message: "文件上传成功,请关闭对话框",
+      type: "success",
+      offset: 60
+    })
   })
 }
 
+const uploadStlFile = (callback) => {
+  // stl文件路径
+  const filePath =  "/home/cicv/work/pji_desktop/simulation/catkin_map2gazebo/src/models/map/meshes/map.stl"
+  if(stlUploadUrl.value !== "") { // 上传路径不为空
+    // 执行脚本 - 上传文件
+    window.electronAPI.uploadFile(filePath, stlUploadUrl.value);
+    // 监听脚本执行状态
+    window.electronAPI.onUploadFileResponse( (event, result) => {
+      if (result.success) { // 脚本执行成功
+        console.log('Script execution completed successfully.')
+        callback()
+      } else { // 脚本执行失败
+        console.error('Script execution failed.');
+      }
+    })
+  }
+}
+
 const getDockerImages = (filter_prefix) => {
   axios.get('/docker/v1.43/images/json').then(function (response) {
     // console.log(response.data);
@@ -512,10 +535,14 @@ const generateWorld = async (row) => {
   console.log("id", id)
 
   // 拼接world文件上传url
-  uploadUrl.value = "http://127.0.0.1:8888/world/upload/worldfile?equipmentNo=" + equipmentNo + "&sceneNo=" + sceneNo
-  console.log("uploadUrl.value=" + uploadUrl.value)
+  worldUploadUrl.value = "http://127.0.0.1:8888/world/upload/worldfile?equipmentNo=" + equipmentNo + "&sceneNo=" + sceneNo
+  console.log("worldUploadUrl.value=" + worldUploadUrl.value)
+
+  // 拼接map.stl文件上传url
+  stlUploadUrl.value = "http://127.0.0.1:8888/world/upload/stlfile?equipmentNo=" + equipmentNo + "&sceneNo=" + sceneNo
+  console.log("stlUploadUrl.value=" + stlUploadUrl.value)
 
-  console.log("Starting download: map.bag...")
+  console.log("Downloading file: map.bag...")
   // 开启对话框
   worldDialogVisible.value = true