Przeglądaj źródła

人员配置页面图片修改

zhangchen 2 miesięcy temu
rodzic
commit
6e77eb616e
1 zmienionych plików z 83 dodań i 27 usunięć
  1. 83 27
      src/views/storeDecoration/personnelConfig/index.vue

+ 83 - 27
src/views/storeDecoration/personnelConfig/index.vue

@@ -32,6 +32,9 @@
         :init-param="initParam"
         :data-callback="dataCallback"
       >
+        <template #empty>
+          <div class="personnel-config-empty">暂无数据</div>
+        </template>
         <template #operation="scope">
           <el-button type="primary" link @click="editPersonnel(scope.row, 0)"> 编辑 </el-button>
           <el-button
@@ -205,7 +208,7 @@
     </el-dialog>
 
     <!-- 新建/编辑人员弹窗 -->
-    <el-dialog v-model="dialogVisible" :title="dialogTitle" width="600px" @close="resetForm">
+    <el-dialog v-model="dialogVisible" :title="dialogTitle" width="720px" @close="resetForm">
       <el-form ref="formRef" :model="formData" :rules="rules" label-width="100px">
         <el-form-item label="头像*" prop="avatar">
           <UploadImg
@@ -225,25 +228,27 @@
           <el-input v-model="formData.position" placeholder="请输入" maxlength="50" clearable />
         </el-form-item>
         <el-form-item label="背景*" prop="backgroundImages">
-          <UploadImgs
-            :key="uploadComponentKey"
-            ref="backgroundImagesUploadRef"
-            v-model:image-url="formData.backgroundImages"
-            :limit="9"
-            :file-size="100"
-            :file-type="['image/jpeg', 'image/png', 'image/gif', 'image/webp', 'video/mp4']"
-            :width="'150px'"
-            :height="'150px'"
-            :border-radius="'8px'"
-            :api="handleCustomUpload"
-            :show-success-notification="false"
-            :on-success="handleBackgroundImageSuccess"
-            :on-video-preview="handleVideoPreviewInForm"
-          >
-            <template #tip>
-              <div class="upload-tip">上传图片或视频 ({{ formData.backgroundImages.length }}/9),单个文件不超过 100M</div>
-            </template>
-          </UploadImgs>
+          <div class="background-upload-three-col">
+            <UploadImgs
+              :key="uploadComponentKey"
+              ref="backgroundImagesUploadRef"
+              v-model:file-list="formData.backgroundImages"
+              :limit="9"
+              :file-size="100"
+              :file-type="['image/jpeg', 'image/png', 'image/gif', 'image/webp', 'video/mp4']"
+              :width="'150px'"
+              :height="'150px'"
+              :border-radius="'8px'"
+              :api="handleCustomUpload"
+              :show-success-notification="false"
+              :on-success="handleBackgroundImageSuccess"
+              :on-video-preview="handleVideoPreviewInForm"
+            >
+              <template #tip>
+                <div class="upload-tip">上传图片或视频 ({{ formData.backgroundImages.length }}/9),单个文件不超过 100M</div>
+              </template>
+            </UploadImgs>
+          </div>
         </el-form-item>
         <el-form-item label="擅长" prop="specialty">
           <el-input
@@ -739,6 +744,9 @@ const syncFileListFromComponent = async () => {
           .sort();
         const newUrls = validFiles.map((f: UploadUserFile) => f.url!.trim()).sort();
 
+        // 未传背景时不以组件内残留数据覆盖:表单为空且组件有项,说明是上次编辑的残留,不覆盖
+        if (formData.backgroundImages.length === 0 && validFiles.length > 0) return;
+
         // 如果不一致,更新 formData(直接使用组件内部的文件列表)
         if (JSON.stringify(currentUrls) !== JSON.stringify(newUrls)) {
           // 直接使用组件内部的文件列表,确保数据一致
@@ -975,6 +983,9 @@ watch(
                 const urlsChanged = JSON.stringify(currentUrls) !== JSON.stringify(lastFileListUrls);
                 const lengthChanged = currentLength !== lastFileListLength;
 
+                // 未传背景时不以组件内残留数据覆盖:表单为空且组件有项时不同步
+                if (formData.backgroundImages.length === 0 && currentLength > 0) return;
+
                 if (urlsChanged || lengthChanged) {
                   lastFileListUrls = currentUrls;
                   lastFileListLength = currentLength;
@@ -1444,6 +1455,7 @@ const openCreateDialog = async () => {
 
     editId.value = null;
     resetForm();
+    uploadComponentKey.value += 1;
     dialogVisible.value = true;
   } catch (error: any) {
     // 如果检查标题时出错,记录错误但允许继续创建人员(避免阻塞用户)
@@ -1461,6 +1473,7 @@ const openCreateDialog = async () => {
     // 其他错误,允许继续创建(避免因接口问题阻塞用户)
     editId.value = null;
     resetForm();
+    uploadComponentKey.value += 1;
     dialogVisible.value = true;
   }
 };
@@ -1476,7 +1489,7 @@ const editPersonnel = async (person: Personnel, index: number) => {
     // 调用获取人员详情接口(使用和详情页面相同的接口,确保数据格式一致)
     const res: any = await getStaffConfigDetail({ id: person.id });
     if (res && (res.code === 200 || res.code === "200")) {
-      const personDetail = res.data || res;
+      const personDetail = res.data ?? res;
       console.log("编辑时获取的完整人员详情数据:", personDetail);
 
       editId.value = personDetail.id;
@@ -1484,8 +1497,9 @@ const editPersonnel = async (person: Personnel, index: number) => {
       formData.position = personDetail.staffPosition || "";
       formData.avatar = personDetail.staffImage || "";
 
-      // 处理背景图片:将字符串转换为 UploadUserFile[] 格式
-      const backgroundUrlValue = personDetail.backgroundUrl || personDetail.backgroundImages || personDetail.background;
+      // 处理背景图片:接口返回 backgroundUrl 逗号分隔,转为 UploadUserFile[](兼容 background_url 等字段名)
+      const backgroundUrlValue =
+        personDetail.backgroundUrl ?? personDetail.background_url ?? personDetail.backgroundImages ?? personDetail.background;
 
       let imageFiles: UploadUserFile[] = [];
 
@@ -1522,6 +1536,8 @@ const editPersonnel = async (person: Personnel, index: number) => {
       formData.description = personDetail.personalIntroduction || "";
       formData.backgroundImages = imageFiles;
 
+      // 强制背景上传组件重新挂载,避免沿用上次的 _fileList 导致数量显示错误
+      uploadComponentKey.value += 1;
       // 打开对话框
       dialogVisible.value = true;
     } else {
@@ -2362,6 +2378,32 @@ onMounted(async () => {
         }
       }
     }
+
+    /* 列表为空时去掉空状态残留图形/背景,仅显示「暂无数据」文字 */
+    :deep(.el-table__empty-block) {
+      background: transparent !important;
+      background-image: none !important;
+      .table-empty {
+        display: flex;
+        flex-direction: column;
+        gap: 8px;
+        align-items: center;
+        justify-content: center;
+        padding: 24px 0;
+        img {
+          display: none !important;
+        }
+      }
+
+      /* 隐藏可能存在的默认空状态插图(如 Element Plus 自带的 SVG) */
+      svg {
+        display: none !important;
+      }
+    }
+    .personnel-config-empty {
+      font-size: 14px;
+      color: var(--el-text-color-secondary);
+    }
   }
   .dialog-footer {
     display: flex;
@@ -2413,12 +2455,13 @@ onMounted(async () => {
           border-radius: 8px;
         }
         .background-images {
-          display: flex;
-          flex-wrap: wrap;
+          display: grid;
+          grid-template-columns: repeat(3, 1fr);
           gap: 10px;
           margin-top: 8px;
           .background-image {
-            width: 120px;
+            width: 100%;
+            max-width: 120px;
             height: 120px;
             cursor: pointer;
             object-fit: cover;
@@ -2431,7 +2474,8 @@ onMounted(async () => {
           }
           .background-media-item {
             position: relative;
-            width: 120px;
+            width: 100%;
+            max-width: 120px;
             height: 120px;
             overflow: hidden;
             cursor: pointer;
@@ -2468,6 +2512,18 @@ onMounted(async () => {
     }
   }
 }
+
+/* 编辑弹窗:背景图片/视频上传区域一行显示三个 */
+.background-upload-three-col {
+  :deep(.upload-box .upload) {
+    display: grid;
+    grid-template-columns: repeat(3, 1fr);
+    gap: 10px;
+  }
+  :deep(.el-upload-list--picture-card) {
+    display: contents;
+  }
+}
 .video-preview-wrap {
   display: flex;
   align-items: center;