瀏覽代碼

部分新需求

cz 1 年之前
父節點
當前提交
13e2ba0764

+ 7 - 8
src/components/headerBar/header-bar.vue

@@ -231,7 +231,7 @@
           </div>
           <div class="job-list">
             <div class="job-item" style="margin-right:5px" @click="handlePushRouter(1)">
-              <el-badge :value="jobData.unreadMailCount" :max="99" style="margin-right:20px;margin-top:10px" v-if="jobData.unreadMailCount">
+              <el-badge :value="jobData.waitFlowCount" :max="99" style="margin-right:20px;margin-top:10px" v-if="jobData.waitFlowCount">
                 <div style="margin-top:-10px">
                   <el-icon size="20" color="#fff">
                     <Reading />
@@ -246,7 +246,7 @@
               <div>待审批</div>
             </div>
             <div class="job-item" style="margin-right:5px" @click="handlePushRouter(2)">
-              <el-badge :value="jobData.waitFlowCount" :max="99" style="margin-right:20px;margin-top:10px" v-if="jobData.waitFlowCount">
+              <el-badge :value="jobData.waitQuotationCount" :max="99" style="margin-right:20px;margin-top:10px" v-if="jobData.waitQuotationCount">
                 <div style="margin-top:-10px">
                   <el-icon size="20" color="#fff">
                     <CopyDocument />
@@ -261,7 +261,7 @@
               <div>待报价</div>
             </div>
             <div class="job-item" @click="handlePushRouter(3)">
-              <el-badge :value="jobData.claimCount" :max="99" style="margin-right:20px;margin-top:10px" v-if="jobData.claimCount">
+              <el-badge :value="jobData.waitProduceCount" :max="99" style="margin-right:20px;margin-top:10px" v-if="jobData.waitProduceCount">
                 <div style="margin-top:-10px">
                   <el-icon size="20" color="#fff">
                     <Notebook />
@@ -276,7 +276,7 @@
               <div>待投产</div>
             </div>
             <div class="job-item" style="margin-right:5px" @click=" handlePushRouter(4)">
-              <el-badge :value="jobData.waitPurchaseCount" :max="99" style="margin-right:20px;margin-top:10px" v-if="jobData.waitPurchaseCount">
+              <el-badge :value="jobData.waitInStockCount" :max="99" style="margin-right:20px;margin-top:10px" v-if="jobData.waitInStockCount">
                 <div style="margin-top:-10px">
                   <el-icon size="20" color="#fff">
                     <ShoppingCart />
@@ -291,7 +291,7 @@
               <div>待入库</div>
             </div>
             <div class="job-item" style="margin-right:5px" @click=" handlePushRouter(5)">
-              <el-badge :value="jobData.sampleHandoverCount" :max="99" style="margin-right:20px;margin-top:10px" v-if="jobData.sampleHandoverCount">
+              <el-badge :value="jobData.waitOutStockCount" :max="99" style="margin-right:20px;margin-top:10px" v-if="jobData.waitOutStockCount">
                 <div style="margin-top:-10px">
                   <el-icon size="20" color="#fff">
                     <Tickets />
@@ -306,8 +306,7 @@
               <div>待出库</div>
             </div>
             <div class="job-item" @click=" handlePushRouter(6)" v-if="useUserStore().user.companyId =='100'">
-              <el-badge :value="jobData.contractHandoverCount" :max="99" style="margin-right:20px;margin-top:10px"
-                        v-if="jobData.contractHandoverCount">
+              <el-badge :value="jobData.waitClaimCount" :max="99" style="margin-right:20px;margin-top:10px" v-if="jobData.waitClaimCount">
                 <div style="margin-top:-10px">
                   <el-icon size="20" color="#fff">
                     <Memo />
@@ -322,7 +321,7 @@
               <div>待认领</div>
             </div>
             <div class="job-item" style="margin-right:5px" @click=" handlePushRouter(7)" v-else>
-              <el-badge :value="jobData.waitAccountPayCount" :max="99" style="margin-right:20px;margin-top:10px" v-if="jobData.waitAccountPayCount">
+              <el-badge :value="jobData.stockWarnCount" :max="99" style="margin-right:20px;margin-top:10px" v-if="jobData.stockWarnCount">
                 <div style="margin-top:-10px">
                   <el-icon size="20" color="#fff">
                     <Money />

+ 3 - 0
src/components/process/SF/Contract.vue

@@ -220,6 +220,7 @@
                 </div>
               </template>
             </el-table-column>
+            <el-table-column prop="productColor" label="颜色" width="100" />
             <el-table-column label="设计图稿" width="80">
               <template #default="{ row, $index }">
                 <div style="width: 100%">
@@ -1044,6 +1045,7 @@ const handleClickSelectMaterial = (index) => {
 
 const contractProductBomList = ref([]);
 const selectProduct = async (goods) => {
+  console.log(goods, "asaas");
   if (goods && goods.id) {
     let rowId = uuidv4();
     let allFile = [];
@@ -1088,6 +1090,7 @@ const selectProduct = async (goods) => {
           productLength: goods["length"],
           productWidth: goods.width,
           productHeight: goods.height,
+          productColor: goods.color,
           prodFilePath: goods.prodFilePath,
           quantity: null,
           price: goods.price || null,

+ 2 - 0
src/components/process/SF/ContractChange.vue

@@ -220,6 +220,7 @@
                 </div>
               </template>
             </el-table-column>
+            <el-table-column prop="productColor" label="颜色" width="100" />
             <el-table-column label="设计图稿" width="80">
               <template #default="{ row, $index }">
                 <div style="width: 100%">
@@ -1089,6 +1090,7 @@ const selectProduct = async (goods) => {
           productLength: goods["length"],
           productWidth: goods.width,
           productHeight: goods.height,
+          productColor: goods.color,
           prodFilePath: goods.prodFilePath,
           quantity: null,
           price: goods.price || null,

+ 1 - 1
src/components/process/SF/ReturnGood.vue

@@ -187,8 +187,8 @@ const handleSelect = (row) => {
     );
     proxy.msgTip("选择成功");
     openMaterial.value = false;
+    getAllFileData();
   });
-  getAllFileData();
 };
 
 const handleRemove = (index) => {

+ 1 - 1
src/views/EHSD/procurement/returnGood/index.vue

@@ -179,7 +179,7 @@ const config = computed(() => {
     {
       attrs: {
         label: "采购单号",
-        prop: "productSn",
+        prop: "purchaseCode",
       },
     },
     {

+ 11 - 1
src/views/EHSD/productLibrary/companyProduct/index.vue

@@ -154,7 +154,7 @@
         </el-upload>
       </div>
       <template #footer>
-        <el-button @click="openExcelDialog = false" size="default">取 消</el-button>
+        <el-button @click="openExcelDialog = false" size="default" v-debounce>取 消</el-button>
       </template>
     </el-dialog>
 
@@ -215,6 +215,9 @@ const rules = ref({
   length: [{ required: true, message: "请输入长 (cm)", trigger: "blur" }],
   width: [{ required: true, message: "请输入宽 (cm)", trigger: "blur" }],
   height: [{ required: true, message: "请输入高 (cm)", trigger: "blur" }],
+  technologyId: [
+    { required: true, message: "请选择生产工艺", trigger: "change" },
+  ],
 });
 const props = defineProps({
   selectStatus: Boolean,
@@ -509,6 +512,13 @@ const formConfig = computed(() => {
       disabled: false,
     },
     {
+      type: "input",
+      prop: "color",
+      label: "颜色",
+      itemWidth: 50,
+      disabled: false,
+    },
+    {
       type: "slot",
       slotName: "size",
       prop: "",

+ 3 - 2
src/views/EHSD/saleContract/PriceSheetDetail.vue

@@ -78,7 +78,7 @@
                     </el-table-column>
                     <el-table-column prop="productCode" label="物料编码" width="190" />
                     <el-table-column prop="productName" label="物料名称" min-width="200" />
-                    <el-table-column label="尺寸 cm*cm*cm" width="150">
+                    <el-table-column label="尺寸 (cm)" width="150">
                       <template #default="{ row, $index }">
                         <div style="width: 100%">
                           {{row.productLength}} * {{row.productWidth}} * {{row.productHeight}}
@@ -134,13 +134,14 @@
             </el-table-column>
             <el-table-column prop="productCode" label="商品编码" width="190" />
             <el-table-column prop="productName" label="商品名称" min-width="200" />
-            <el-table-column label="尺寸 cm*cm*cm" width="150">
+            <el-table-column label="尺寸 (cm)" width="150">
               <template #default="{ row, $index }">
                 <div style="width: 100%">
                   {{row.productLength}} * {{row.productWidth}} * {{row.productHeight}}
                 </div>
               </template>
             </el-table-column>
+            <el-table-column prop="productColor" label="颜色" width="100" />
             <el-table-column prop="quantity" label="数量" width="110" />
             <!-- <template #default="{ row, $index }">
                 <div style="width: 100%">

+ 2 - 0
src/views/EHSD/saleContract/contractEHSD/index.vue

@@ -45,6 +45,8 @@
                 <div style="width:calc(100% - 60px)">
                   <div>产品编码:{{i.productCode}}</div>
                   <div>产品名称:{{i.productName}}</div>
+                  <div>产品尺寸:{{i.productLength}}cm*{{i.productWidth}}cm*{{i.productHeight}}cm</div>
+                  <div>产品颜色:{{i.productColor}}</div>
                   <div>产品数量:{{i.quantity}}</div>
                 </div>
               </div>

+ 7 - 4
src/views/EHSD/saleContract/priceSheetEHSD/index.vue

@@ -159,7 +159,7 @@
                       </el-table-column>
                       <el-table-column prop="productCode" label="物料编码" width="190" />
                       <el-table-column prop="productName" label="物料名称" min-width="200" />
-                      <el-table-column label="尺寸 cm*cm*cm" width="150">
+                      <el-table-column label="尺寸 (cm)" width="150">
                         <template #default="{ row, $index }">
                           <div style="width: 100%">
                             {{row.productLength}} * {{row.productWidth}} * {{row.productHeight}}
@@ -225,13 +225,14 @@
               </el-table-column>
               <el-table-column prop="productCode" label="商品编码" width="190" />
               <el-table-column prop="productName" label="商品名称" min-width="200" />
-              <el-table-column label="尺寸 cm*cm*cm" width="150">
+              <el-table-column label="尺寸 (cm)" width="150">
                 <template #default="{ row, $index }">
                   <div style="width: 100%">
                     {{row.productLength}} * {{row.productWidth}} * {{row.productHeight}}
                   </div>
                 </template>
               </el-table-column>
+              <el-table-column prop="productColor" label="颜色" width="100" />
               <el-table-column label="数量" width="110">
                 <template #default="{ row, $index }">
                   <div style="width: 100%">
@@ -300,7 +301,7 @@
                       </el-table-column>
                       <el-table-column prop="productCode" label="物料编码" width="190" />
                       <el-table-column prop="productName" label="物料名称" min-width="200" />
-                      <el-table-column label="尺寸 cm*cm*cm" width="150">
+                      <el-table-column label="尺寸 (cm)" width="150">
                         <template #default="{ row, $index }">
                           <div style="width: 100%">
                             {{row.productLength}} * {{row.productWidth}} * {{row.productHeight}}
@@ -360,13 +361,14 @@
               </el-table-column>
               <el-table-column prop="productCode" label="商品编码" width="190" />
               <el-table-column prop="productName" label="商品名称" min-width="200" />
-              <el-table-column label="尺寸 cm*cm*cm" width="150">
+              <el-table-column label="尺寸 (cm)" width="150">
                 <template #default="{ row, $index }">
                   <div style="width: 100%">
                     {{row.productLength}} * {{row.productWidth}} * {{row.productHeight}}
                   </div>
                 </template>
               </el-table-column>
+              <el-table-column prop="productColor" label="颜色" width="100" />
               <el-table-column label="数量" width="110" prop="quantity">
               </el-table-column>
               <el-table-column label="单价" width="110" prop="price">
@@ -1097,6 +1099,7 @@ const selectProduct = (goods) => {
           productLength: goods["length"],
           productWidth: goods.width,
           productHeight: goods.height,
+          productColor: goods.color,
           quantity: null,
           price: null,
           amount: "",

+ 3 - 2
src/views/EHSD/saleContract/priceSheetEstimate/index.vue

@@ -81,7 +81,7 @@
                       </el-table-column>
                       <el-table-column prop="productCode" label="物料编码" width="190" />
                       <el-table-column prop="productName" label="物料名称" min-width="200" />
-                      <el-table-column label="尺寸 cm*cm*cm" width="150">
+                      <el-table-column label="尺寸 (cm)" width="150">
                         <template #default="{ row, $index }">
                           <div style="width: 100%">
                             {{row.productLength}} * {{row.productWidth}} * {{row.productHeight}}
@@ -134,13 +134,14 @@
               </el-table-column>
               <el-table-column prop="productCode" label="商品编码" width="190" />
               <el-table-column prop="productName" label="商品名称" min-width="200" />
-              <el-table-column label="尺寸 cm*cm*cm" width="150">
+              <el-table-column label="尺寸 (cm)" width="150">
                 <template #default="{ row, $index }">
                   <div style="width: 100%">
                     {{row.productLength}} * {{row.productWidth}} * {{row.productHeight}}
                   </div>
                 </template>
               </el-table-column>
+              <el-table-column prop="productColor" label="颜色" width="100" />
               <el-table-column label="数量" width="120" prop="quantity">
               </el-table-column>
               <el-table-column label="单价" width="120" prop="price">

+ 3 - 2
src/views/EHSD/saleContract/priceSheetForeign/index.vue

@@ -150,7 +150,7 @@
                       </el-table-column>
                       <el-table-column prop="productCode" label="物料编码" width="190" />
                       <el-table-column prop="productName" label="物料名称" min-width="200" />
-                      <el-table-column label="尺寸 cm*cm*cm" width="150">
+                      <el-table-column label="尺寸 (cm)" width="150">
                         <template #default="{ row, $index }">
                           <div style="width: 100%">
                             {{row.productLength}} * {{row.productWidth}} * {{row.productHeight}}
@@ -194,13 +194,14 @@
               </el-table-column>
               <el-table-column prop="productCode" label="商品编码" width="190" />
               <el-table-column prop="productName" label="商品名称" min-width="200" />
-              <el-table-column label="尺寸 cm*cm*cm" width="150">
+              <el-table-column label="尺寸 (cm)" width="150">
                 <template #default="{ row, $index }">
                   <div style="width: 100%">
                     {{row.productLength}} * {{row.productWidth}} * {{row.productHeight}}
                   </div>
                 </template>
               </el-table-column>
+              <el-table-column prop="productColor" label="颜色" width="100" />
               <el-table-column label="数量" width="120" prop="quantity">
               </el-table-column>
               <el-table-column label="单价" width="120" prop="price">

+ 3 - 1
src/views/MES/productionOrder/index.vue

@@ -38,6 +38,7 @@
                   <div>产品编码:{{product.productCode}}</div>
                   <div>产品名称:{{product.productName}}</div>
                   <div>产品尺寸:{{product.productLength}}cm*{{product.productWidth}}cm*{{product.productHeight}}cm</div>
+                  <div>产品颜色:{{product.productColor}}</div>
                   <div>产品数量:{{product.quantity}}</div>
                 </div>
                 <template #reference>
@@ -176,13 +177,14 @@
               </el-table-column>
               <el-table-column prop="productCnName" label="商品名称" min-width="130" />
               <el-table-column prop="productCode" label="商品编码" width="130" />
-              <el-table-column label="尺寸 cm*cm*cm" width="180">
+              <el-table-column label="尺寸 (cm)" width="150">
                 <template #default="{ row, $index }">
                   <div style="width: 100%">
                     {{row.productLength}} * {{row.productWidth}} * {{row.productHeight}}
                   </div>
                 </template>
               </el-table-column>
+              <el-table-column prop="productColor" label="颜色" width="100" />
               <el-table-column label="设计图稿" width="80">
                 <template #default="{ row, $index }">
                   <div style="width: 100%">

+ 72 - 54
src/views/MES/productionTask/index.vue

@@ -28,6 +28,14 @@
           <div v-else></div>
         </template>
 
+        <template #size="{ item }">
+          <div v-if="item.productLength && item.productWidth && item.productHeight">
+            <span>{{ item.productLength }}</span>*
+            <span>{{ item.productWidth }}</span>*
+            <span>{{ item.productHeight }}</span>
+          </div>
+        </template>
+
         <template #isOverdue="{item}">
           <div style="width: 100%">
             <span class="red" v-if="item.isOverdue=='1'"> 逾期 </span>
@@ -38,15 +46,9 @@
           <div style="width:100%">
             <span v-if="isShowCotent(slotItem,item)" style="font-weight:700;min-width:50px;line-height:18px;display:inline-block"
                   :class="showCotentQuantity(slotItem,item)">
-              <!-- <el-icon :size="20" color="green">
-                <CircleCheckFilled />
-              </el-icon> -->
               {{showCotent(slotItem,item)}}
             </span>
             <div v-else class="no-bk">
-              <!-- <el-icon :size="20" color="red">
-                <CircleClose />
-              </el-icon> -->
               -
             </div>
           </div>
@@ -188,9 +190,9 @@
                   <div>
                     <table border class="table son">
                       <tr>
-                        <td style="width:70%">名称</td>
-                        <td style="width:15%">单价</td>
-                        <td style="width:15%">量</td>
+                        <td style="width:85%">名称</td>
+                        <!-- <td style="width:15%">单价</td> -->
+                        <td style="width:15%">量</td>
                       </tr>
                       <tr v-for="son in item.contractProductBomList" :key="son.id">
                         <td>
@@ -201,7 +203,7 @@
                             {{son.productName}}
                           </div>
                         </td>
-                        <td>{{son.price}}</td>
+                        <!-- <td>{{son.price}}</td> -->
                         <td>{{son.quantity}}</td>
                       </tr>
                     </table>
@@ -212,25 +214,6 @@
             </table>
             <div style="page-break-after: always"></div>
           </div>
-          <!-- <div style="border-top: 1px solid #000;border-bottom: 1px solid #000; padding: 10px 0; margin:10px auto;text-align:center">
-            <div :ref="printData.id" style="width:200px;margin-left:55px">
-            </div>
-            <div style="font-size:20px;text-align:center;font-weight:700;margin-top:10px">
-              {{printData.createTime}}
-            </div>
-          </div> -->
-          <!-- <div style="margin-left:10px;display:flex;flex-direction:column;justify-content:space-around">
-            <div style="font-size:14px;margin-top:8px"> 产品编码:{{printData.productCode}}</div>
-            <div style="font-size:14px;margin-top:8px">
-              产品名称:{{printData.productName}}
-            </div>
-            <div style="font-size:14px;margin-top:8px">
-              原材料编码:{{printData.rawMaterialCode}}
-            </div>
-            <div style="font-size:14px;margin-top:8px">
-              原材料名称:{{printData.rawMaterialName}}
-            </div>
-          </div> -->
         </div>
       </div>
       <template #footer>
@@ -238,6 +221,17 @@
         <el-button type="primary" v-print="printObj" size="defualt">打 印</el-button>
       </template>
     </el-dialog>
+
+    <el-dialog title="备注" v-model="remarkDialog" width="500" destroy-on-close v-if="remarkDialog">
+      <byForm :formConfig="formConfig" :formOption="formOption" v-model="formData.data" :rules="rules" ref="formDom" v-loading="submitLoading">
+      </byForm>
+      <template #footer>
+        <el-button @click="remarkDialog = false" size="defualt" v-debounce>取 消</el-button>
+        <el-button type="primary" @click="submitForm()" size="defualt" v-debounce>
+          确 定
+        </el-button>
+      </template>
+    </el-dialog>
   </div>
 </template>
 
@@ -268,6 +262,8 @@ const sourceList = ref({
 });
 const treeData = ref([]);
 const dialogVisible = ref(false);
+const remarkDialog = ref(false);
+
 const modalType = ref("add");
 const statusData = ref([
   {
@@ -381,6 +377,20 @@ const config = ref([
   },
   {
     attrs: {
+      label: "产品尺寸 (cm)",
+      slot: "size",
+      width: 160,
+    },
+  },
+  {
+    attrs: {
+      label: "产品颜色",
+      prop: "productColor",
+      width: 80,
+    },
+  },
+  {
+    attrs: {
       label: "生产件数",
       prop: "quantity",
       width: 100,
@@ -439,6 +449,13 @@ const config = ref([
       width: 100,
     },
   },
+  {
+    attrs: {
+      label: "备注",
+      prop: "remark",
+      "min-width": 200,
+    },
+  },
 ]);
 const formData = reactive({
   data: {},
@@ -453,34 +470,16 @@ const formConfig = computed(() => {
   return [
     {
       type: "input",
-      prop: "code",
-      label: "店铺编号",
-      itemWidth: 100,
-      disabled: false,
-    },
-    {
-      type: "input",
-      prop: "name",
-      label: "店铺名称",
-      itemWidth: 100,
-      disabled: false,
-    },
-    {
-      type: "treeSelect",
-      prop: "deptId",
-      label: "负责部门",
-      data: treeData.value,
-      propsTreeLabel: "deptName",
-      propsTreeValue: "deptId",
+      prop: "remark",
+      itemType: "textarea",
+      label: "备注",
       itemWidth: 100,
       disabled: false,
     },
   ];
 });
 const rules = ref({
-  deptId: [{ required: true, message: "请选择负责部门", trigger: "change" }],
-  name: [{ required: true, message: "请输入店铺名称", trigger: "blur" }],
-  code: [{ required: true, message: "请输入店铺编号", trigger: "blur" }],
+  remark: [{ required: true, message: "请输入备注", trigger: "blur" }],
 });
 
 const getList = async (req) => {
@@ -595,10 +594,10 @@ const openModal = () => {
 const submitForm = () => {
   formDom.value.handleSubmit((valid) => {
     submitLoading.value = true;
-    proxy.post("/shopInfo/" + modalType.value, formData.data).then(
+    proxy.post("/produceOrderDetail/editRemark", formData.data).then(
       (res) => {
         proxy.msgTip("操作成功", 1);
-        dialogVisible.value = false;
+        remarkDialog.value = false;
         submitLoading.value = false;
         getList();
       },
@@ -639,7 +638,7 @@ const getProcesses = () => {
       config.value.push({
         attrs: {
           label: "操作",
-          width: "100",
+          width: "160",
           align: "center",
           fixed: "right",
         },
@@ -656,6 +655,17 @@ const getProcesses = () => {
                 printQrCode(row);
               },
             },
+            {
+              attrs: {
+                label: "备注",
+                type: "primary",
+                text: true,
+              },
+              el: "button",
+              click() {
+                openRemark(row);
+              },
+            },
           ];
         },
       });
@@ -745,6 +755,14 @@ const getDict = () => {
     });
 };
 getDict();
+
+const openRemark = (row) => {
+  formData.data = {
+    id: row.id,
+    remark: row.remark,
+  };
+  remarkDialog.value = true;
+};
 </script>
 
 <style lang="scss" scoped>

+ 2 - 1
src/views/index.vue

@@ -229,13 +229,14 @@
               </el-table-column>
               <el-table-column prop="productCnName" label="商品名称" min-width="130" />
               <el-table-column prop="productCode" label="商品编码" width="130" />
-              <el-table-column label="尺寸 cm*cm*cm" width="180">
+              <el-table-column label="尺寸 (cm)" width="150">
                 <template #default="{ row, $index }">
                   <div style="width: 100%">
                     {{row.productLength}} * {{row.productWidth}} * {{row.productHeight}}
                   </div>
                 </template>
               </el-table-column>
+              <el-table-column prop="productColor" label="颜色" width="100" />
               <el-table-column label="设计图稿" width="80">
                 <template #default="{ row, $index }">
                   <div style="width: 100%">

+ 1 - 0
src/views/process/processApproval/index.vue

@@ -433,6 +433,7 @@ const skipPage = () => {
     purchase_update_flow: "Purchased",
     purchase_flow: "Purchase",
     pay_flow: "Payment",
+    purchase_back_flow: "ReturnGood",
   };
   const useTagsStore = useTagsViewStore();
   useTagsStore.delVisitedView(router.currentRoute.value);

+ 53 - 8
src/views/process/processConfig/vueFlow.vue

@@ -208,7 +208,18 @@ const formConfig = computed(() => {
       itemWidth: 50,
       prop: "handleObjectId",
       placeholder: "请选择办理人",
-      data: [],
+      data: selectHanleData.value,
+      isShow: formData.data.handleObjectType !== 5,
+    },
+    {
+      type: "select",
+      label: "",
+      itemWidth: 50,
+      prop: "handleObjectId",
+      multiple: true,
+      placeholder: "请选择办理人",
+      data: selectHanleData.value,
+      isShow: formData.data.handleObjectType === 5,
     },
     {
       type: "input",
@@ -274,6 +285,13 @@ const formOption = reactive({
 let graph;
 const submitForm = () => {
   byform.value.handleSubmit((valid) => {
+    //如果处理类型是角色, 则角色转,分割
+    // if (
+    //   formData.data.handleObjectType &&
+    //   formData.data.handleObjectType === 5
+    // ) {
+    //   formData.data.handleObjectId = formData.data.handleObjectId.join(",");
+    // }
     flowDefinitionNodeObj.value[formData.data.id] = formData.data;
     dialogVisible.value = false;
     formData.data.cell.setData({
@@ -290,6 +308,17 @@ const submitFormData = {
   lineObject: "",
   flowDefinitionNodeList: [],
 };
+const dataRollback = () => {
+  for (const key in flowDefinitionNodeObj.value) {
+    if (
+      flowDefinitionNodeObj.value[key].handleObjectType &&
+      flowDefinitionNodeObj.value[key].handleObjectType === 5
+    ) {
+      flowDefinitionNodeObj.value[key].handleObjectId =
+        flowDefinitionNodeObj.value[key].handleObjectId.split(",");
+    }
+  }
+};
 const submitAll = () => {
   if (proxy.title == "") {
     ElMessage({
@@ -298,11 +327,23 @@ const submitAll = () => {
     });
     return;
   }
+  // 如果选择类型是角色,则角色数据转成 ','分割
+  for (const key in flowDefinitionNodeObj.value) {
+    if (
+      flowDefinitionNodeObj.value[key].handleObjectType &&
+      flowDefinitionNodeObj.value[key].handleObjectType === 5
+    ) {
+      flowDefinitionNodeObj.value[key].handleObjectId =
+        flowDefinitionNodeObj.value[key].handleObjectId.join(",");
+    }
+  }
+
   submitFormData.titleTemplate = proxy.title;
   const nodeList = graph.toJSON().cells;
   submitFormData.nodeObject = JSON.stringify(nodeList);
   submitFormData.lineObject = JSON.stringify(flowDefinitionNodeObj.value);
-  console.log(nodeList);
+
+  // console.log(nodeList);
   const isStart = false;
   for (let i = 0; i < nodeList.length; i++) {
     const element = nodeList[i];
@@ -317,6 +358,7 @@ const submitAll = () => {
           message: "有节点未配置,请检查节点",
           type: "warning",
         });
+        dataRollback();
         return;
       }
       submitFormData.flowDefinitionNodeList.push({
@@ -346,6 +388,7 @@ const submitAll = () => {
           message: "有节点未配置,请检查节点",
           type: "warning",
         });
+        dataRollback();
         return;
       }
       flowDefinitionNodeObj.value[element.target.cell].id = element.target.cell;
@@ -376,6 +419,7 @@ const addVersion = () => {
         message: "有结束节点未连线,请配置",
         type: "warning",
       });
+      dataRollback();
       return;
     }
     if (isNaN(element.id)) {
@@ -427,6 +471,7 @@ const deleteFlowDefinitionNodeObj = (id) => {
   dialogVisible.value = false;
 };
 
+const selectHanleData = ref([]);
 const gethandleObjectList = (e, flag) => {
   if (flag) {
     formData.data.handleObjectId = "";
@@ -440,7 +485,7 @@ const gethandleObjectList = (e, flag) => {
         {}
       )
       .then((res) => {
-        formConfig.value[2].data = res.rows.map((item) => {
+        selectHanleData.value = res.rows.map((item) => {
           return {
             label: item.nickName,
             value: item.userId,
@@ -456,7 +501,7 @@ const gethandleObjectList = (e, flag) => {
         {}
       )
       .then((res) => {
-        formConfig.value[2].data = res.data.map((item) => {
+        selectHanleData.value = res.data.map((item) => {
           return {
             label: item.deptName,
             value: item.deptId,
@@ -474,7 +519,7 @@ const gethandleObjectList = (e, flag) => {
         {}
       )
       .then((res) => {
-        formConfig.value[2].data = res.rows.map((item) => {
+        selectHanleData.value = res.rows.map((item) => {
           return {
             label: item.roleName,
             value: item.roleId,
@@ -655,8 +700,8 @@ const antvInit = (data) => {
   });
   // #endregion
   graph.on("cell:click", ({ e, x, y, cell, view }) => {
-    console.log(flowDefinitionNodeObj.value);
-    console.log(cell);
+    // console.log(flowDefinitionNodeObj.value);
+    // console.log(cell);
     if (cell.shape === "start-btn") {
       startModalType.value = true;
       return;
@@ -939,7 +984,7 @@ const getFlowInfo = () => {
 const router = useRouter();
 onActivated(() => {});
 onDeactivated(() => {
-  console.log(window.document.getElementById("minimap").children);
+  // console.log(window.document.getElementById("minimap").children);
   if (window.document.getElementById("minimap").children.length > 1) {
     window.document.getElementById("minimap").children[0].remove();
   }

+ 95 - 67
src/views/product/material/index.vue

@@ -81,12 +81,40 @@
       </div>
 
       <template #footer>
-        <el-button @click="dialogVisible = false" size="defualt">取 消</el-button>
-        <el-button type="primary" @click="submitForm()" size="defualt" :loading="submitLoading">
+        <el-button @click="dialogVisible = false" size="defualt" v-debounce>取 消</el-button>
+        <el-button type="primary" @click="submitForm()" size="defualt" :loading="submitLoading" v-debounce>
           确 定
         </el-button>
       </template>
     </el-dialog>
+
+    <el-dialog :title="'关联产品'+`  (${associationProductData.length})`" v-model="openAssociationProduct" width="70%" destroy-on-close>
+      <div style="padding: 0 15px" class="public_height_dialog">
+        <el-table :data="associationProductData" style="width: 100%;">
+          <el-table-column label="产品图片" width="80">
+            <template #default="{ row }">
+              <div v-if="row.fileUrl">
+                <img :src="row.fileUrl" class="pic" @click="openImg(row.fileUrl)" />
+              </div>
+            </template>
+          </el-table-column>
+          <el-table-column prop="name" label="产品名称" min-width="130" />
+          <el-table-column prop="customCode" label="产品编码" width="180" />
+          <el-table-column label="尺寸 (cm)" width="130">
+            <template #default="{ row, $index }">
+              <div style="width: 100%">
+                {{row['length']}} * {{row.width}} * {{row.height}}
+              </div>
+            </template>
+          </el-table-column>
+          <el-table-column prop="color" label="颜色" width="150" />
+        </el-table>
+      </div>
+      <template #footer>
+        <el-button @click="openAssociationProduct = false" size="defualt" v-debounce>关 闭</el-button>
+      </template>
+    </el-dialog>
+
   </div>
 </template>
 
@@ -145,9 +173,7 @@ const rules = ref({
   width: [{ required: true, message: "请输入宽 (cm)", trigger: "blur" }],
   height: [{ required: true, message: "请输入高 (cm)", trigger: "blur" }],
 });
-const props = defineProps({
-  selectStatus: Boolean,
-});
+
 const selectConfig = computed(() => []);
 const config = computed(() => {
   return [
@@ -248,73 +274,57 @@ const config = computed(() => {
     {
       attrs: {
         label: "操作",
-        width: "160",
+        width: "180",
         align: "center",
         fixed: "right",
       },
       renderHTML(row) {
         return [
-          // props.selectStatus
-          //   ? {}
-          //   : {
-          //       attrs: {
-          //         label: "复制",
-          //         type: "primary",
-          //         text: true,
-          //       },
-          //       el: "button",
-          //       click() {
-          //         getDtlOne(row);
-          //       },
-          //     },
-          props.selectStatus
-            ? {
-                attrs: {
-                  label: "选择",
-                  type: "primary",
-                  text: true,
-                },
-                el: "button",
-                click() {
-                  clickSelect(row);
-                },
-              }
-            : {
-                attrs: {
-                  label: "修改",
-                  type: "primary",
-                  text: true,
-                },
-                el: "button",
-                click() {
-                  getDtl(row);
-                },
-              },
-          props.selectStatus
-            ? {}
-            : {
-                attrs: {
-                  label: "删除",
-                  type: "danger",
-                  text: true,
-                },
-                el: "button",
-                click() {
+          {
+            attrs: {
+              label: "产品反查",
+              type: "primary",
+              text: true,
+            },
+            el: "button",
+            click() {
+              getAssociationProduct(row);
+            },
+          },
+          {
+            attrs: {
+              label: "修改",
+              type: "primary",
+              text: true,
+            },
+            el: "button",
+            click() {
+              getDtl(row);
+            },
+          },
+          {
+            attrs: {
+              label: "删除",
+              type: "danger",
+              text: true,
+            },
+            el: "button",
+            click() {
+              proxy
+                .msgConfirm()
+                .then((res) => {
                   proxy
-                    .msgConfirm()
-                    .then((res) => {
-                      proxy
-                        .post("/productInfo/delete", {
-                          id: row.id,
-                        })
-                        .then((res) => {
-                          proxy.msgTip("删除成功", 1);
-                          getList();
-                        });
+                    .post("/productInfo/delete", {
+                      id: row.id,
                     })
-                    .catch((err) => {});
-                },
-              },
+                    .then((res) => {
+                      proxy.msgTip("删除成功", 1);
+                      getList();
+                    });
+                })
+                .catch((err) => {});
+            },
+          },
         ];
       },
     },
@@ -585,8 +595,26 @@ const handleClickFile = (file) => {
 getTreeList();
 getList();
 
-const clickSelect = (item) => {
-  proxy.$emit("selectMaterial", item);
+const openAssociationProduct = ref(false);
+const associationProductData = ref([]);
+const getAssociationProduct = (row) => {
+  openAssociationProduct.value = true;
+  proxy
+    .post("/productInfo/getProductByMaterialId", { materialId: row.id })
+    .then((res) => {
+      associationProductData.value = res;
+      let productIds = associationProductData.value.map((x) => x.id);
+      if (productIds && productIds.length > 0) {
+        proxy.getFileData({
+          businessIdList: productIds,
+          data: associationProductData.value,
+          att: "id",
+          businessType: "0",
+          fileAtt: "fileList",
+          filePathAtt: "fileUrl",
+        });
+      }
+    });
 };
 </script>
 

+ 13 - 0
src/views/production/project/processes/index.vue

@@ -70,6 +70,7 @@ let modalType = ref("add");
 let fileList = ref([]);
 let rules = ref({
   name: [{ required: true, message: "请输入工序名称", trigger: "blur" }],
+  code: [{ required: true, message: "请输入工序编号", trigger: "blur" }],
 });
 const { proxy } = getCurrentInstance();
 const selectConfig = reactive([
@@ -96,6 +97,12 @@ const config = computed(() => {
   return [
     {
       attrs: {
+        label: "工序编号",
+        prop: "code",
+      },
+    },
+    {
+      attrs: {
         label: "工序名称",
         prop: "name",
       },
@@ -192,6 +199,12 @@ const formConfig = computed(() => {
   return [
     {
       type: "input",
+      prop: "code",
+      label: "工序编号",
+      required: true,
+    },
+    {
+      type: "input",
       prop: "name",
       label: "工序名称",
       required: true,

+ 6 - 2
src/views/purchaseSales/outAndInWarehouse/manualDelivery/index.vue

@@ -102,6 +102,10 @@ const outBoundReason = ref([
     label: "借用出库",
     value: "3",
   },
+  {
+    label: "其他出库",
+    value: "10",
+  },
 ]);
 
 const produceOrder = ref([]);
@@ -389,7 +393,7 @@ const formConfig = computed(() => {
       required: true,
       data: outBoundReason.value,
       fn: (val) => {
-        if (["1", "2", "0"].includes(val)) {
+        if (["1", "2", "0", "10"].includes(val)) {
           formData.data.expectRestitutionTime = "";
         } else {
           formData.data.prodOrderId = "";
@@ -404,7 +408,7 @@ const formConfig = computed(() => {
       data: produceOrder.value,
       filterable: true,
       itemWidth: 50,
-      isShow: ["1", "2", "0"].includes(formData.data.type),
+      isShow: ["1", "2", "0", "10"].includes(formData.data.type),
     },
     // {
     //   type: "select",

+ 6 - 2
src/views/purchaseSales/outAndInWarehouse/manualWarehousing/index.vue

@@ -112,6 +112,10 @@ const inBoundReason = ref([
     label: "错领归还",
     value: "109",
   },
+  {
+    label: "其他入库",
+    value: "110",
+  },
 ]);
 const produceOrder = ref([]);
 const lendData = ref([]);
@@ -392,7 +396,7 @@ const formConfig = computed(() => {
       data: inBoundReason.value,
       fn: (val) => {
         formData.data.list = [];
-        if (["101", "102", "108", "109"].includes(val)) {
+        if (["101", "102", "108", "109", "110"].includes(val)) {
           formData.data.borrowId = "";
           formData.data.loseId = "";
         } else if (val == "103") {
@@ -412,7 +416,7 @@ const formConfig = computed(() => {
       data: produceOrder.value,
       filterable: true,
       itemWidth: 50,
-      isShow: ["101", "102", "108", "109"].includes(formData.data.type),
+      isShow: ["101", "102", "108", "109", "110"].includes(formData.data.type),
     },
     {
       type: "select",

+ 8 - 0
src/views/purchaseSales/outAndInWarehouse/record/index.vue

@@ -140,6 +140,10 @@ const typeList = ref([
     value: "9",
   },
   {
+    label: "其他出库",
+    value: "10",
+  },
+  {
     label: "借用归还",
     value: "100",
   },
@@ -179,6 +183,10 @@ const typeList = ref([
     label: "错领归还",
     value: "109",
   },
+  {
+    label: "其他入库",
+    value: "110",
+  },
 ]);
 const warehouseList = ref([]);
 const sourceList = ref({

+ 763 - 0
src/views/salesMange/afterSales/SelectContractProduct.vue

@@ -0,0 +1,763 @@
+<template>
+  <div class="user">
+    <!-- <div class="tree">
+      <treeList title="产品分类" submitType="1" :hiddenBtn="true" :data="treeListData" v-model="sourceList.pagination.productClassifyId"
+                @change="treeChange" @changeTreeList="getTreeList">
+      </treeList>
+    </div> -->
+    <div class="content">
+      <byTable :source="sourceList.data" :tableHeight="tableHeight" :pagination="sourceList.pagination" :config="config" :loading="loading"
+               highlight-current-row :selectConfig="selectConfig" :table-events="{
+          //element talbe事件都能传
+          select: select,
+        }" :action-list="[]" @get-list="getList">
+
+        <template #pic="{ item }">
+          <div style="width:100%">
+            <img v-if="item.fileUrl" :src="item.fileUrl" class="pic" @click="openImg(item.fileUrl)" />
+          </div>
+        </template>
+
+        <template #size="{ item }">
+          <div v-if="item.productLength && item.productWidth && item.productHeight">
+            <span>{{ item.productLength}}</span>*
+            <span>{{ item.productWidth }}</span>*
+            <span>{{ item.productHeight }}</span>
+          </div>
+          <div v-else></div>
+        </template>
+        <template #price="{ item }">
+          <div v-if="item.price">
+            <span>{{ item.currency }} {{ moneyFormat(item.price ,2)}}</span>
+          </div>
+          <div v-else></div>
+        </template>
+      </byTable>
+    </div>
+    <!-- <div class="right">
+      <div style="margin-bottom:30px">
+        <TitleInfo :content="'已选择商品'"></TitleInfo>
+      </div>
+      <el-tag style="margin-right: 10px; margin-bottom: 10px" type="info" v-for="(good, index) in goodList" :key="good.productId">
+        {{ good.productCnName || good.productName }}
+      </el-tag>
+    </div> -->
+
+    <el-dialog :title="modalType == 'add' ? '添加产品' : '编辑产品'" v-model="dialogVisible" width="700" v-loading="submitLoading" destroy-on-close>
+      <div class="public_height_dialog">
+        <byForm :formConfig="formConfig" :formOption="formOption" v-model="formData.data" :rules="rules" ref="byform">
+          <template #nameEnglish>
+            <div style="width: 100%">
+              <el-form-item label="英文名" prop="nameEnglish">
+                <el-input v-model="formData.data.nameEnglish" placeholder="请输入" onkeyup="value=value.replace(/[^\x00-\xff]/g, '')"></el-input>
+                <!-- @input="(val) => handleKeyup(val)" -->
+              </el-form-item>
+            </div>
+          </template>
+          <template #productPic>
+            <div>
+              <el-upload v-model:fileList="fileList" :action="uploadUrl" :data="uploadData" list-type="picture-card" :on-remove="handleRemove"
+                         :before-upload="handleBeforeUpload" :on-preview="handlePreview" accept=".gif, .jpeg, .jpg, .png">
+                <el-icon>
+                  <Plus />
+                </el-icon>
+              </el-upload>
+            </div>
+          </template>
+        </byForm>
+      </div>
+      <template #footer>
+        <el-button @click="dialogVisible = false" size="default">取 消</el-button>
+        <el-button type="primary" @click="submitForm('byform')" size="default" :loading="submitLoading">确 定</el-button>
+      </template>
+    </el-dialog>
+
+    <el-dialog title="导入产品" v-model="openExcelDialog" width="400" v-loading="excelLoading">
+      <el-upload :action="actionUrl + '/productInfo/excelImportByEhsd'" :headers="headers" :on-success="handleSuccess" :on-progress="handleProgress"
+                 :show-file-list="false" :on-error="handleError" accept=".xlsx">
+        <el-button type="primary">点击导入</el-button>
+      </el-upload>
+      <template #footer>
+        <el-button @click="openExcelDialog = false" size="default">取 消</el-button>
+      </template>
+    </el-dialog>
+
+    <el-dialog v-if="productContractDialog" v-model="productContractDialog" :title="'外销合同'" width="80%" append-to-body>
+      <ProductContract :currentProductId="currentProductId"></ProductContract>
+    </el-dialog>
+  </div>
+</template>
+
+<script setup>
+import { ElMessage, ElMessageBox } from "element-plus";
+import byTable from "@/components/byTable/index";
+import byForm from "@/components/byForm/index";
+import treeList from "@/components/product/treeList";
+import { getToken } from "@/utils/auth";
+import ProductContract from "@/components/contractCom/productContract.vue";
+import TitleInfo from "@/components/TitleInfo/index.vue";
+import { watch } from "vue";
+const { proxy } = getCurrentInstance();
+const props = defineProps({
+  alreadySelectData: Array,
+  companyId: {
+    type: String,
+    default: "",
+  },
+  // 过滤是否配置过bom
+  isRawMaterial: {
+    type: String,
+    default: "",
+  },
+});
+const tableHeight = ref(0);
+const getTableHeight = () => {
+  tableHeight.value = window.innerHeight - 245;
+};
+getTableHeight();
+window.addEventListener("resize", () => {
+  getTableHeight();
+});
+const goodList = ref([]);
+onMounted(() => {
+  // goodList.value = proxy.deepClone(props.alreadySelectData);
+});
+const headers = ref({ Authorization: "Bearer " + getToken() });
+const actionUrl = import.meta.env.VITE_APP_BASE_API;
+const loading = ref(false);
+const submitLoading = ref(false);
+const treeListData = ref([]);
+const innerMethon = ref([]);
+const outsideMethon = ref([]);
+const productUnit = ref([]);
+const companyData = ref([]);
+const accountCurrency = ref([]);
+const sourceList = ref({
+  data: [],
+  pagination: {
+    total: 3,
+    pageNum: 1,
+    pageSize: 10,
+    keyword: "",
+  },
+});
+let dialogVisible = ref(false);
+let openExcelDialog = ref(false);
+let excelLoading = ref(false);
+let modalType = ref("add");
+let rules = ref({
+  productClassifyId: [
+    { required: true, message: "请选择产品分类", trigger: "change" },
+  ],
+  name: [{ required: true, message: "请输入产品名称", trigger: "blur" }],
+  nameEnglish: [
+    { required: true, message: "请输入产品英文名", trigger: "blur" },
+  ],
+  productLong: [
+    { required: true, message: "请输入长 (cm)", trigger: "blur" },
+  ],
+  productWide: [
+    { required: true, message: "请输入宽 (cm)", trigger: "blur" },
+  ],
+  productHigh: [
+    { required: true, message: "请输入高 (cm)", trigger: "blur" },
+  ],
+  innerPackMethod: [
+    { required: true, message: "请选择内包装方式", trigger: "change" },
+  ],
+  outerPackMethod: [
+    { required: true, message: "请选择外包装方式", trigger: "change" },
+  ],
+});
+
+const selectConfig = computed(() => [
+  // {
+  //   label: "归属公司",
+  //   prop: "companyId",
+  //   data: companyData.value,
+  // },
+]);
+const config = computed(() => {
+  return [
+    {
+      attrs: {
+        label: "生产公司",
+        prop: "corporationName",
+        width: 110,
+      },
+    },
+    {
+      attrs: {
+        label: "订单号",
+        prop: "contractCode",
+        width: 150,
+      },
+    },
+    {
+      attrs: {
+        label: "图片",
+        slot: "pic",
+        align: "center",
+        width: 80,
+      },
+    },
+    {
+      attrs: {
+        label: "产品分类",
+        prop: "productCategory",
+        width: 140,
+      },
+    },
+    {
+      attrs: {
+        label: "产品编码",
+        prop: "productCode",
+        width: 180,
+      },
+    },
+    {
+      attrs: {
+        label: "产品名称",
+        prop: "productName",
+        "min-width": 200,
+      },
+    },
+    {
+      attrs: {
+        label: "尺寸 (cm)",
+        slot: "size",
+        width: 130,
+      },
+    },
+    // {
+    //   attrs: {
+    //     label: "颜色",
+    //     prop: "productColor",
+    //     width: 120,
+    //   },
+    // },
+    {
+      attrs: {
+        label: "订单数量",
+        prop: "quantity",
+        width: 120,
+      },
+    },
+    {
+      attrs: {
+        label: "操作",
+        width: "80",
+        align: "center",
+        fixed: "right",
+      },
+      // 渲染 el-button,一般用在最后一列。
+      renderHTML(row) {
+        return [
+          {
+            attrs: {
+              label: "选择",
+              type: "primary",
+              text: true,
+            },
+            el: "button",
+            click() {
+              clickSelect(row);
+            },
+          },
+        ];
+      },
+    },
+  ];
+});
+
+const uploadData = ref({});
+const fileList = ref([]);
+const fileListCopy = ref([]);
+let formData = reactive({
+  data: {},
+});
+const formOption = reactive({
+  disabled: false,
+  inline: true,
+  labelWidth: 100,
+  itemWidth: 100,
+  rules: [],
+});
+const byform = ref(null);
+const formConfig = computed(() => {
+  return [
+    {
+      type: "title",
+      title: "基本信息",
+    },
+    {
+      type: "treeSelect",
+      prop: "productClassifyId",
+      label: "产品分类",
+      data: treeListData.value,
+      itemWidth: 100,
+      disabled: false,
+      style: {
+        width: "100%",
+      },
+    },
+    {
+      type: "input",
+      prop: "name",
+      label: "产品名称",
+      itemWidth: 100,
+      disabled: false,
+    },
+    {
+      type: "slot",
+      slotName: "nameEnglish",
+      label: "",
+    },
+    {
+      type: "slot",
+      slotName: "productPic",
+      prop: "fileList",
+      label: "产品图片",
+    },
+    {
+      type: "title",
+      title: "价格信息",
+    },
+    {
+      type: "selectInput",
+      prop: "price",
+      selectProp: "currency",
+      label: "销售指导价",
+      itemWidth: 50,
+      style: {
+        width: "100%",
+      },
+      data: accountCurrency.value,
+    },
+    {
+      type: "selectInput",
+      prop: "costPrice",
+      selectProp: "costCurrency",
+      label: "成本价",
+      itemWidth: 50,
+      style: {
+        width: "100%",
+      },
+      data: accountCurrency.value,
+    },
+    {
+      type: "title",
+      title: "属性信息",
+    },
+    {
+      type: "input",
+      prop: "spec",
+      label: "规格型号",
+      itemWidth: 100,
+      disabled: false,
+    },
+    {
+      type: "input",
+      prop: "productLong",
+      label: "尺寸",
+      itemWidth: 33.33,
+      placeholder: "长(cm)",
+      disabled: false,
+    },
+    {
+      type: "input",
+      prop: "productWide",
+      label: " ",
+      itemWidth: 33.33,
+      placeholder: "宽(cm)",
+      disabled: false,
+    },
+    {
+      type: "input",
+      prop: "productHigh",
+      label: " ",
+      itemWidth: 33.33,
+      placeholder: "高(cm)",
+      disabled: false,
+    },
+    {
+      type: "select",
+      prop: "innerPackMethod",
+      label: "内包装方式",
+      required: true,
+      itemWidth: 50,
+      multiple: true,
+      data: innerMethon.value,
+      filterable: true,
+      placeholder: "内包装方式",
+      style: {
+        width: "100%",
+      },
+      disabled: false,
+    },
+    {
+      type: "select",
+      prop: "outerPackMethod",
+      label: "外包装方式",
+      required: true,
+      itemWidth: 50,
+      multiple: true,
+      data: outsideMethon.value,
+      filterable: true,
+      placeholder: "外包装方式",
+      style: {
+        width: "100%",
+      },
+      disabled: false,
+    },
+    {
+      type: "input",
+      prop: "netWeight",
+      label: "净重(kg)",
+      itemWidth: 100,
+      style: {
+        width: "30%",
+      },
+    },
+    {
+      type: "input",
+      prop: "hsCode",
+      label: "海关编码",
+      itemWidth: 100,
+      style: {
+        width: "30%",
+      },
+      disabled: false,
+    },
+    {
+      type: "input",
+      itemType: "textarea",
+      prop: "remark",
+      label: "备注",
+      itemWidth: 100,
+    },
+  ];
+});
+
+const getList = async (req) => {
+  sourceList.value.pagination = { ...sourceList.value.pagination, ...req };
+  loading.value = true;
+  proxy.post("/contractProduct/page", sourceList.value.pagination).then(
+    (message) => {
+      sourceList.value.data = message.rows;
+      sourceList.value.pagination.total = message.total;
+      setTimeout(() => {
+        loading.value = false;
+      }, 200);
+      const productIdList = message.rows.map((x) => x.productId);
+      // 请求文件数据并回显
+      if (productIdList && productIdList.length > 0) {
+        proxy.getFileData({
+          businessIdList: productIdList,
+          data: sourceList.value.data,
+          att: "productId",
+          businessType: "0",
+          fileAtt: "fileList",
+          filePathAtt: "fileUrl",
+        });
+      }
+    },
+    (err) => {
+      loading.value = false;
+    }
+  );
+};
+
+const treeChange = (e) => {
+  sourceList.value.pagination.productClassifyId = e.id;
+  getList({ productClassifyId: e.id });
+};
+
+const openModal = () => {
+  dialogVisible.value = true;
+  modalType.value = "add";
+  formData.data = {
+    definition: "1",
+    outerPackMethod: [],
+    innerPackMethod: [],
+    fileList: [],
+    fileListCopy: [],
+    currency: "",
+    costCurrency: "",
+  };
+  if (accountCurrency.value && accountCurrency.value.length > 0) {
+    formData.data.currency = accountCurrency.value[0].value;
+    formData.data.costCurrency = accountCurrency.value[0].value;
+  }
+  fileList.value = [];
+  fileListCopy.value = [];
+};
+
+const openExcel = () => {
+  openExcelDialog.value = true;
+};
+
+const needAtt = [
+  "productClassifyId",
+  "name",
+  "spec",
+  "remark",
+  "fileList",
+  "id",
+  "unit",
+  "definition",
+];
+const submitForm = () => {
+  byform.value.handleSubmit((valid) => {
+    // if (!fileListCopy.value.length > 0) {
+    //   return ElMessage({
+    //     message: "请上传产品图片",
+    //     type: "info",
+    //   });
+    // }
+    let jsonObj = {};
+    formData.data.fileList = fileListCopy.value.map((x) => ({
+      id: x.id,
+      fileName: x.fileName,
+    }));
+    for (const key in formData.data) {
+      if (needAtt.includes(key)) {
+      } else {
+        jsonObj[key] = formData.data[key];
+        delete formData.data[key];
+      }
+    }
+    jsonObj.innerPackMethod = jsonObj.innerPackMethod.join(",");
+    jsonObj.outerPackMethod = jsonObj.outerPackMethod.join(",");
+    jsonObj.type = "1"; //1为公司产品库
+    formData.data.ehsdJson = JSON.stringify(jsonObj);
+    submitLoading.value = true;
+    proxy.post(`/productInfo/${modalType.value}ByEhsd`, formData.data).then(
+      (res) => {
+        ElMessage({
+          message: modalType.value == "add" ? "添加成功" : "编辑成功",
+          type: "success",
+        });
+        dialogVisible.value = false;
+        submitLoading.value = false;
+        getList();
+      },
+      (err) => {
+        for (const key in jsonObj) {
+          formData.data[key] = jsonObj[key];
+        }
+        formData.data.innerPackMethod =
+          formData.data.innerPackMethod.split(",");
+        formData.data.outerPackMethod =
+          formData.data.outerPackMethod.split(",");
+        submitLoading.value = false;
+      }
+    );
+  });
+};
+const getTreeList = () => {
+  proxy
+    .post("/productClassify/tree", { parentId: "", name: "", definition: "1" })
+    .then((message) => {
+      treeListData.value = message;
+    });
+};
+const getDtl = (row) => {
+  modalType.value = "edit";
+  proxy.post("/productInfo/detailByEhsd", { id: row.id }).then((res) => {
+    res.definition = "1"; //产品
+    let jsonObj = JSON.parse(res.ehsdJson);
+    res = {
+      ...res,
+      currency: jsonObj.currency
+        ? jsonObj.currency
+        : accountCurrency.value[0].value,
+      costCurrency: jsonObj.costCurrency
+        ? jsonObj.costCurrency
+        : accountCurrency.value[0].value,
+      ...jsonObj,
+    };
+    if (res.innerPackMethod) {
+      res.innerPackMethod = res.innerPackMethod.split(",");
+    } else {
+      res.innerPackMethod = [];
+    }
+    if (res.outerPackMethod) {
+      res.outerPackMethod = res.outerPackMethod.split(",");
+    } else {
+      res.outerPackMethod = [];
+    }
+    formData.data = res;
+    dialogVisible.value = true;
+    proxy
+      .post("/fileInfo/getList", { businessIdList: [row.id] })
+      .then((fileObj) => {
+        if (fileObj[row.id]) {
+          fileList.value = fileObj[row.id].map((x) => ({
+            ...x,
+            url: x.fileUrl,
+          }));
+          fileListCopy.value = fileObj[row.id].map((x) => ({
+            ...x,
+            url: x.fileUrl,
+          }));
+        } else {
+          fileList.value = [];
+          fileListCopy.value = [];
+        }
+      });
+  });
+};
+const isdisabled = ["price", "costPrice", "remark", "netWeight"];
+// watch(modalType, (val) => {
+//   if (val) {
+//     for (let i = 0; i < formConfig.value.length; i++) {
+//       const element = formConfig.value[i];
+//       if (element.type != "title" || element.type != "slot") {
+//         if (!isdisabled.includes(element.prop)) {
+//           element.disabled = val == "edit" ? true : false;
+//         }
+//       }
+//     }
+//   }
+// });
+const handleBeforeUpload = async (file) => {
+  const res = await proxy.post("/fileInfo/getSing", { fileName: file.name });
+  uploadData.value = res.uploadBody;
+  fileListCopy.value.push({
+    id: res.id,
+    fileName: res.fileName,
+    path: res.fileUrl,
+    url: res.fileUrl,
+    uid: file.uid,
+  });
+};
+const handleRemove = (file) => {
+  const index = fileListCopy.value.findIndex(
+    (x) => x.uid === file.uid || x.id === file.id
+  );
+  fileListCopy.value.splice(index, 1);
+};
+const handleClickFile = (file) => {
+  window.open(file.fileUrl, "_blank");
+};
+const handleProgress = () => {
+  excelLoading.value = true;
+};
+const handleError = (err) => {
+  ElMessage({
+    message: `${err},请重试!`,
+    type: "info",
+  });
+  openExcelDialog.value = false;
+  excelLoading.value = false;
+};
+const handleSuccess = (res) => {
+  if (res.code != 200) {
+    return ElMessage({
+      message: `${res.msg},请重试!`,
+      type: "info",
+    });
+  } else {
+    ElMessage({
+      message: "导入成功!",
+      type: "success",
+    });
+    openExcelDialog.value = false;
+    excelLoading.value = false;
+    getList();
+  }
+};
+const getDict = () => {
+  proxy
+    .get("/tenantDept/list", {
+      pageNum: 1,
+      pageSize: 9999,
+      keyword: "",
+      tenantId: proxy.useUserStore().user.tenantId,
+      type: 0,
+    })
+    .then((res) => {
+      companyData.value = res.data.map((x) => ({
+        ...x,
+        label: x.deptName,
+        value: x.deptId,
+      }));
+      // treeDataOne.value = proxy.handleTree(res.data, "deptId");
+    });
+};
+// getDict();
+// getTreeList();
+
+if (props && props.companyId) {
+  sourceList.value.pagination.companyId = props.companyId;
+}
+if (props && props.isRawMaterial) {
+  sourceList.value.pagination.isRawMaterial = props.isRawMaterial;
+}
+
+getList();
+const clickSelect = (item) => {
+  // item.selectType = "1";
+  // goodList.value.push({
+  //   ...item,
+  //   productName: item.name,
+  // });
+  proxy.$emit("selectProduct", item);
+};
+
+const handleKeypress = (event) => {
+  // 判断输入字符是否为中文字符
+  if (event.key.match(/[\u4e00-\u9fa5]/)) {
+    // 阻止输入
+    event.preventDefault();
+  }
+};
+const handleKeyup = (val) => {
+  // 过滤掉中文字符
+  formData.data.nameEnglish = formData.data.nameEnglish.replace(
+    /[\u4e00-\u9fa5]/g,
+    ""
+  );
+};
+
+const handlePreview = (file) => {
+  if (file && file.fileUrl) {
+    window.open(file.fileUrl, "_black");
+  }
+};
+const productContractDialog = ref(false);
+const currentProductId = ref("");
+const handleOpenProductContract = (row) => {
+  currentProductId.value = row.id;
+  productContractDialog.value = true;
+};
+</script>
+
+<style lang="scss" scoped>
+.user {
+  // padding: 10px;
+  display: flex;
+  justify-content: space-between;
+  // .tree {
+  //   width: 300px;
+  //   border-right: 1px solid rgb(223, 221, 221);
+  // }
+  .content {
+    width: 100%;
+    // width: calc(100% - 310px);
+  }
+  .right {
+    padding-left: 10px;
+    width: 170px;
+    border-left: 1px solid #eee;
+  }
+}
+.pic {
+  object-fit: contain;
+  width: 50px;
+  height: 50px;
+  cursor: pointer;
+  vertical-align: middle;
+}
+</style>

+ 164 - 79
src/views/salesMange/afterSales/index.vue

@@ -12,6 +12,28 @@
             action: () => clickAdd(),
           },
         ]" @get-list="getList">
+
+        <template #code="{ item }">
+          <div style="width:100%">
+            <span class="el-click" @click="getDtl(item)">{{item.code}}</span>
+          </div>
+        </template>
+
+        <template #pic="{ item }">
+          <div style="width:100%">
+            <img v-if="item.fileUrl" :src="item.fileUrl" class="pic" @click="openImg(item.fileUrl)" />
+          </div>
+        </template>
+
+        <template #size="{ item }">
+          <div v-if="item.productLength && item.productWidth && item.productWidth">
+            <span>{{ item.productLength }}</span>*
+            <span>{{ item.productWidth }}</span>*
+            <span>{{ item.productWidth }}</span>
+          </div>
+          <div v-else></div>
+        </template>
+
       </byTable>
     </div>
 
@@ -20,8 +42,8 @@
         <template #btn>
           <div style="width:100%;display:flex">
             <div style="width:calc(100% - 105px)">
-              <el-form-item label="订单号" prop="code" class="margin-b-0">
-                <el-input disabled v-model="formData.data.code" placeholder="请选择"></el-input>
+              <el-form-item label="订单号" prop="contractCode" class="margin-b-0">
+                <el-input disabled v-model="formData.data.contractCode" placeholder="请选择"></el-input>
               </el-form-item>
             </div>
             <el-button type="primary" style="width:88px;margin-left:15px" @click="openMaterial = true" plain>选择产品</el-button>
@@ -30,11 +52,11 @@
 
         <template #image>
           <div style="width:100%">
-            aaa
+            <img v-if="formData.data.fileUrl" :src="formData.data.fileUrl" class="pic" @click="openImg(formData.data.fileUrl)" />
           </div>
         </template>
       </byForm>
-      <template #footer>
+      <template #footer v-if="!formOption.disabled">
         <el-button @click="dialogVisible = false" size="defualt" v-debounce>取 消</el-button>
         <el-button type="primary" @click="submitForm()" size="defualt" v-debounce>
           确 定
@@ -42,14 +64,14 @@
       </template>
     </el-dialog>
 
-    <!-- <el-dialog v-model="openMaterial" title="选择物料/半成品" width="70%" append-to-body>
-      <SelectMaterial @handleSelect="handleSelect"></SelectMaterial>
+    <el-dialog v-model="openMaterial" title="选择订单产品" width="80%" append-to-body>
+      <SelectContractProduct @selectProduct="handleSelect"></SelectContractProduct>
       <template #footer>
         <span class="dialog-footer">
           <el-button @click="openMaterial = false">取消</el-button>
         </span>
       </template>
-    </el-dialog> -->
+    </el-dialog>
 
   </div>
 </template>
@@ -57,6 +79,7 @@
 <script setup>
 import byTable from "@/components/byTable/index";
 import byForm from "@/components/byForm/index";
+import SelectContractProduct from "./SelectContractProduct.vue";
 
 const { proxy } = getCurrentInstance();
 const loading = ref(false);
@@ -74,19 +97,17 @@ const openMaterial = ref(false);
 const dialogVisible = ref(false);
 const openFollow = ref(false);
 const rules = ref({
-  productSn: [{ required: true, message: "请输入产品Sn", trigger: "blur" }],
+  contractCode: [{ required: true, message: "请选择订单", trigger: "blur" }],
   type: [{ required: true, message: "请选择售后类型", trigger: "change" }],
   remark: [{ required: true, message: "请输入售后说明", trigger: "blur" }],
   contactName: [
     { required: true, message: "请输入客户联系人", trigger: "blur" },
   ],
-  contactInfo: [
+  contactWay: [
     { required: true, message: "请输入客户联系方式", trigger: "blur" },
   ],
-  afterSalesPersonId: [
-    { required: true, message: "请选择售后人员", trigger: "change" },
-  ],
-  quantity: [{ required: true, message: "请输入数量", trigger: "blur" }],
+  userId: [{ required: true, message: "请选择售后人员", trigger: "change" }],
+  quantity: [{ required: true, message: "请输入售后数量", trigger: "blur" }],
 });
 const userList = ref([]);
 const afterSalesType = computed(
@@ -118,39 +139,75 @@ const config = computed(() => {
     {
       attrs: {
         label: "售后编码",
-        prop: "code",
+        slot: "code",
+        width: 130,
       },
     },
     {
       attrs: {
-        label: "产品Sn",
-        prop: "productSn",
+        label: "订单号",
+        prop: "contractCode",
+        width: 130,
+      },
+    },
+    {
+      attrs: {
+        label: "售后类型",
+        prop: "type",
+        width: 80,
+      },
+      render(val) {
+        return proxy.dictKeyValue(val, afterSalesType.value);
+      },
+    },
+    {
+      attrs: {
+        label: "图片",
+        slot: "pic",
+        align: "center",
+        width: 80,
+      },
+    },
+    {
+      attrs: {
+        label: "产品编码",
+        prop: "productCode",
+        width: 150,
       },
     },
-
     {
       attrs: {
         label: "产品名称",
         prop: "productName",
+        "min-width": 150,
       },
     },
-
     {
       attrs: {
-        label: "规格型号",
-        prop: "productSpec",
+        label: "尺寸 (cm)",
+        slot: "size",
+        width: 130,
       },
     },
     {
       attrs: {
-        label: "售后金额",
-        prop: "amount",
+        label: "客户联系人",
+        prop: "contactName",
+        width: 100,
+      },
+    },
+    {
+      attrs: {
+        label: "客户联系方式",
+        prop: "contactWay",
+        width: 150,
       },
     },
     {
       attrs: {
         label: "售后状态",
         prop: "status",
+        width: 100,
       },
       render(status) {
         return status == "0" ? "进行中" : "完成";
@@ -158,15 +215,22 @@ const config = computed(() => {
     },
     {
       attrs: {
-        label: "操作",
-        width: "200",
-        align: "center",
-        fixed: "right",
-      },
-      renderHTML(row) {
-        return [];
+        label: "售后人员",
+        prop: "userName",
+        width: 100,
       },
     },
+    // {
+    //   attrs: {
+    //     label: "操作",
+    //     width: "200",
+    //     align: "center",
+    //     fixed: "right",
+    //   },
+    //   renderHTML(row) {
+    //     return [];
+    //   },
+    // },
   ];
 });
 const formData = reactive({
@@ -198,7 +262,7 @@ const formConfig = computed(() => {
     },
     {
       type: "number",
-      prop: "amount",
+      prop: "quantity",
       label: "售后数量",
       precision: 2,
       min: 0,
@@ -208,7 +272,7 @@ const formConfig = computed(() => {
     {
       type: "input",
       itemType: "text",
-      prop: "remark",
+      prop: "productCode",
       label: "产品编码",
       itemWidth: 50,
       disabled: true,
@@ -216,7 +280,7 @@ const formConfig = computed(() => {
     {
       type: "input",
       itemType: "text",
-      prop: "remark",
+      prop: "productName",
       label: "产品名称",
       itemWidth: 50,
       disabled: true,
@@ -224,12 +288,20 @@ const formConfig = computed(() => {
     {
       type: "input",
       itemType: "text",
-      prop: "remark",
+      prop: "size",
       label: "尺寸 (cm)",
       itemWidth: 50,
       disabled: true,
     },
     {
+      type: "input",
+      itemType: "text",
+      prop: "productColor",
+      label: "颜色",
+      itemWidth: 50,
+      disabled: true,
+    },
+    {
       type: "slot",
       slotName: "image",
       label: "产品图片",
@@ -250,7 +322,7 @@ const formConfig = computed(() => {
     },
     {
       type: "select",
-      prop: "afterSalesPersonId",
+      prop: "userId",
       label: "售后人员",
       itemWidth: 50,
       filterable: true,
@@ -268,7 +340,7 @@ const formConfig = computed(() => {
     {
       type: "input",
       itemType: "text",
-      prop: "contactInfo",
+      prop: "contactWay",
       label: "客户联系方式",
       disabled: false,
       itemWidth: 50,
@@ -289,26 +361,33 @@ const formDom = ref(null);
 const getList = (req) => {
   sourceList.value.pagination = { ...sourceList.value.pagination, ...req };
   loading.value = true;
-  proxy
-    .post("/sale/accountRunningWater/page", sourceList.value.pagination)
-    .then((res) => {
-      sourceList.value.data = res.rows;
-      sourceList.value.pagination.total = res.total;
-      setTimeout(() => {
-        loading.value = false;
-      }, 200);
-    });
+  proxy.post("/afterSales/page", sourceList.value.pagination).then((res) => {
+    sourceList.value.data = res.rows;
+    sourceList.value.pagination.total = res.total;
+    const productIdList = res.rows.map((x) => x.productId);
+    // 请求文件数据并回显
+    if (productIdList && productIdList.length > 0) {
+      proxy.getFileData({
+        businessIdList: productIdList,
+        data: sourceList.value.data,
+        att: "productId",
+        businessType: "0",
+        fileAtt: "fileList",
+        filePathAtt: "fileUrl",
+      });
+    }
+    setTimeout(() => {
+      loading.value = false;
+    }, 200);
+  });
 };
 
 const submitForm = () => {
   formDom.value.handleSubmit(() => {
     submitLoading.value = true;
-    proxy.post("/afterSalesRecord/add", formData.data).then(
+    proxy.post("/afterSales/add", formData.data).then(
       (res) => {
-        ElMessage({
-          message: "操作成功",
-          type: "success",
-        });
+        proxy.msgTip("操作成功");
         dialogVisible.value = false;
         submitLoading.value = false;
         getList();
@@ -339,43 +418,49 @@ const getDict = () => {
 getDict();
 getList();
 const clickAdd = (type) => {
-  formData.data = {
-    afterSalesPersonId: proxy.useUserStore().user.userId,
-    fileList: [],
-  };
+  formOption.disabled = false;
+  formData.data = {};
   dialogVisible.value = true;
 };
 
 const handleSelect = (row) => {
-  const flag = formData.followData.afterSalesMaterialsList.some(
-    (x) => x.productId === row.id
-  );
-  if (flag) {
-    return ElMessage({
-      message: "该物料已选择",
-      type: "info",
-    });
-  } else {
-    formData.followData.afterSalesMaterialsList.push({
-      productId: row.id,
-      productCode: row.code,
-      productName: row.name,
-      productSpec: row.spec,
-      quantity: null,
-    });
-    return ElMessage({
-      message: "选择成功",
-      type: "success",
+  formData.data = {
+    contractCode: row.contractCode,
+    productCode: row.productCode,
+    productName: row.productName,
+    productColor: row.productColor,
+    size: `${row.productLength}*${row.productWidth}*${row.productHeight}`,
+    contractId: row.contractId,
+    type: "",
+    userId: proxy.useUserStore().user.userId,
+    contactName: "",
+    contactWay: "",
+    remark: "",
+    status: "",
+    contractProductId: row.id,
+    productId: row.productId,
+    quantity: null,
+  };
+  proxy
+    .post("/fileInfo/getList", { businessIdList: [row.productId] })
+    .then((res) => {
+      if (res[row.productId] && res[row.productId].length > 0) {
+        let list = res[row.productId].filter((x) => x.businessType == "0");
+        console.log(list);
+        if (list && list.length > 0) {
+          formData.data.fileUrl = list[0].fileUrl;
+        }
+      }
     });
-  }
+  openMaterial.value = false;
+  proxy.msgTip("选择成功");
 };
 
-const handleRemove = (index, type) => {
-  formData.followData.afterSalesMaterialsList.splice(index, 1);
-  return ElMessage({
-    message: "删除成功",
-    type: "success",
-  });
+const getDtl = (row) => {
+  formOption.disabled = true;
+  formData.data = row;
+  formData.data.size = `${row.productLength}*${row.productWidth}*${row.productHeight}`;
+  dialogVisible.value = true;
 };
 </script>