chencc 1 год назад
Родитель
Сommit
3d8f9d5525

+ 12 - 0
src/api/classifyManage/itemInformation.js

@@ -60,3 +60,15 @@ export async function getByRootLevelId(levelId) {
   }
   return Promise.reject(new Error(res.data.message));
 }
+
+
+
+//工艺路线
+
+
+export async function produceroutingPage(params) {
+  const res = await request.get('/main/producerouting/page', { params });
+  if (res.data.code == 0) {
+    return res.data.data;
+  }
+}

+ 71 - 1
src/api/produce/index.js

@@ -35,4 +35,74 @@ export async function getWarehouseList() {
     }
     return Promise.reject(new Error(res.data.message));
   }
-  
+  
+  export async function pcCheckOutsource(data) {
+    const res = await request.get(`/mes/applyoutsource/pcCheckOutsource`, { params: data });
+    if (res.data.code == 0) {
+      return res.data;
+    }
+    return Promise.reject(new Error(res.data.message));
+  }
+  
+  export async function getTaskInstanceById(data) {
+    const res = await request.get(`/pda/mes/workorder/getTaskInstanceById/${data}`);
+    if (res.data.code == 0) {
+      return res.data;
+    }
+    return Promise.reject(new Error(res.data.message));
+  }
+  
+
+  export async function checkOutsourceMaterial(data) {
+    const res = await request.get(`/mes/applyoutsource/checkOutsourceMaterial`, { params: data });
+    if (res.data.code == 0) {
+      return res.data;
+    }
+    return Promise.reject(new Error(res.data.message));
+  }
+  
+
+  export async function pdaTreeByPid(data) {
+    const res = await request.get(`/api/main/asset/pdaPage`, { params: data });
+    if (res.data.code == 0) {
+      return res.data;
+    }
+    return Promise.reject(new Error(res.data.message));
+  }
+
+  export async function applyoutsourceSave(data) {
+    const res = await request.post(`/mes/applyoutsource/save`, data );
+    if (res.data.code == 0) {
+      return res.data;
+    }
+    return Promise.reject(new Error(res.data.message));
+  }
+
+  export async function outInDetailPdaPage(data) {
+    const res = await request.get(`/main/asset/pdaPage`, { params: data });
+    if (res.data.code == '0') {
+      return res.data.data;
+    }
+    return Promise.reject(new Error(res.data.message));
+  }
+
+
+
+  export async function producerouting(data) {
+    const res = await request.get(`/main/producerouting/page`, { params: data });
+    if (res.data.code == '0') {
+      return res.data.data;
+    }
+    return Promise.reject(new Error(res.data.message));
+  }
+  
+  export async function categoryGetList(data) {
+    const res = await request.get(`/main/category/getList`, { params: data });
+    if (res.data.code == '0') {
+      return res.data.data;
+    }
+    return Promise.reject(new Error(res.data.message));
+  }
+  
+
+  // http://localhost:8084/api/main/asset/pdaPage?categoryLevelId=9&keyWord=&pageNum=1&size=100&taskId=1894207928134549506

+ 242 - 0
src/utils/dict/common.js

@@ -19,3 +19,245 @@ export const cm_workOrderStatus = [
   { code: 4, label: '已撤回' },
   { code: 5, label: '已驳回' }
 ];
+
+
+export const tableHeader = selectEquiType => {
+	
+	// singleReport 批量0  单个1
+
+	// 1:物料;4:生产设备; 5:模具;6:备品备件; 7:周转车;8:舟皿;9:产品;10:消耗材料,11:干燥区,12.质检,13.包装材料,14.工装夹具 ,15.刀具 ,99.其他
+	switch (+selectEquiType) {
+		case 1:
+			return [{
+					label: '型号',
+					prop: 'modelType'
+				},
+				{
+					label: '规格',
+					prop: 'specification'
+				},
+
+				{
+					label: '牌号',
+					prop: 'brandNum'
+				},
+
+				// {
+				// 	label: '包装库存',
+				// 	prop: '',
+				// 	formatter(row) {
+				// 		return `${row.packingCountBase || '0'}/${row.minUnit || ''}`
+				// 	}
+				// },
+
+				// {
+				// 	label: '计量库存数量',
+				// 	prop: '',
+				// 	formatter(row) {
+				// 		return `${row.availableCountBase || '0'}/${row.measuringUnit || ''}`
+				// 	}
+				// }
+			]
+
+
+
+		case 4:
+			return [{
+					label: '规格',
+					prop: 'specification'
+				},
+
+				{
+					label: '型号',
+					prop: 'modelType'
+				},
+
+				{
+					label: '工位',
+					prop: 'workstationName'
+				},
+
+
+
+			]
+
+
+		case 5:
+			return [{
+					label: '牌号',
+					prop: 'brandNum'
+				},
+				{
+					label: '型号',
+					prop: 'modelType'
+				},
+				{
+					label: '模孔数量',
+					prop: 'dieHoleNum'
+				},
+
+				{
+					label: '芯棒直径',
+					prop: 'mandrelDiameter',
+
+				},
+				{
+					label: '收缩系数',
+					prop: 'shrinkEffictive',
+				},
+				{
+					label: '已压制次数',
+					prop: '',
+					formatter(row) {
+						return row.extInfo.startCyTimes || 0
+					}
+				},
+
+				{
+					label: '最大压制次数',
+					prop: '',
+					formatter(row) {
+						return row.extInfo.maxCyTimes
+					}
+				}
+			]
+
+
+		case 7:
+			return [
+				{
+						label: '编号', 
+						prop: 'codeNumber'
+				},
+				{
+					label: '规格',
+					prop: 'modelType'
+				},
+				{
+					label: '材质',
+					prop: 'materialQuality',
+
+				},
+				{
+					label: '长宽高',
+					prop: '',
+					formatter(row) {
+						if (!row?.extInfo) return ''
+						const extendField = row.extInfo
+						return `${extendField.vehicleLen || '-'}*${extendField.wilde || '-'}*${
+											  extendField.hight || '-'
+											}`
+
+					}
+				}
+			]
+
+
+		case 8: //'舟皿'
+			return [{
+					label: '规格',
+					prop: 'specification'
+				},
+				{
+					label: '型号',
+					prop: 'modelType'
+				},
+				
+				{
+					label: '槽数',
+					prop: '',
+					formatter(row) {
+						return row.extInfo.slotNum
+					}
+				},
+				
+			
+
+
+			]
+		case 10:
+			return []
+
+		case 11:
+			return [
+
+
+			]
+
+		case 13:
+			return [
+
+				{
+					label: '规格',
+					prop: 'specification'
+				},
+
+				{
+					label: '型号',
+					prop: 'modelType'
+				},
+
+			]
+
+
+		case 14:
+			return []
+
+		case 23:
+			return [
+
+				{
+					label: '型号',
+					prop: 'modelType'
+				},
+				{
+					label: '规格',
+					prop: 'specification'
+				},
+				{
+					label: '牌号',
+					prop: 'brandNum'
+				},
+
+			]
+
+		case 9:
+			return [
+
+				{
+					label: '型号',
+					prop: 'modelType'
+				},
+				{
+					label: '规格',
+					prop: 'specification'
+				},
+				{
+					label: '牌号',
+					prop: 'brandNum'
+				},
+
+			]
+
+		case 28:
+			return [
+
+				{
+					label: '型号',
+					prop: 'modelType'
+				},
+				{
+					label: '规格',
+					prop: 'specification'
+				},
+				{
+					label: '牌号',
+					prop: 'brandNum'
+				},
+
+			]
+
+	}
+
+	return []
+}

+ 5 - 0
src/views/InTheSystem/components/tgDetails.vue

@@ -87,6 +87,11 @@
             align: 'center'
           },
 
+          {
+            prop: 'taskStayTimeDuration',
+            label: '停留时间(分钟)',
+            align: 'center'
+          },
     
           {
             prop: 'categoryCode',

+ 5 - 1
src/views/InTheSystem/index.vue

@@ -77,7 +77,11 @@
             label: '处置工序',
             align: 'center'
           },
-
+          {
+            prop: 'taskStayTimeDuration',
+            label: '停留时间(分钟)',
+            align: 'center'
+          },
           {
             prop: 'categoryCode',
             label: '物品编码',

+ 4 - 0
src/views/entrust/components/produceOrder.vue

@@ -1,4 +1,5 @@
 <template>
+  <!-- 工单列表 -->
   <el-dialog
     :visible.sync="equipmentdialog"
     :before-close="handleClose"
@@ -232,6 +233,9 @@ export default {
           ? JSON.parse(JSON.stringify(this.selection))
           : JSON.parse(JSON.stringify(this.current));
       data['productNumber'] = data.formingNum;
+
+      console.log(data);
+
       this.$emit('choose', data);
       this.handleClose();
     }

+ 1 - 1
src/views/produce/components/footBtn.vue

@@ -43,7 +43,7 @@
 
           {
             name: '委外',
-            type: '',
+            type: 'Outsourcing',
             bjColor: '#39D9AC'
           },
 

+ 118 - 0
src/views/produce/components/outsourcing/assetTree.vue

@@ -0,0 +1,118 @@
+<template>
+  <div class="tree-wrapper">
+    <el-tree
+      :data="treeList"
+      :props="defaultProps"
+      v-loading="treeLoading"
+      :node-key="nodeKey"
+      ref="tree"
+      :highlight-current="true"
+      :expand-on-click-node="false"
+      @node-click="handleNodeClick"
+      :default-expanded-keys="current && current.id ? [current.id] : []"
+    >
+    </el-tree>
+  </div>
+</template>
+
+<script>
+  import { treeByPid } from '@/api/produce/workOrder';
+
+  export default {
+    props: {
+      defaultProps: {
+        type: Object,
+        default: function () {
+          return {
+            children: 'children',
+            value: 'id',
+            label: 'name'
+          };
+        }
+      },
+
+      // 初始请求treeList
+      init: {
+        type: Boolean,
+        default: true
+      },
+
+      treeIds: {
+        type: String,
+        default: ''
+      },
+      nodeKey: {
+        type: String,
+        default: 'id'
+      }
+    },
+    data() {
+      return {
+        treeList: [],
+        treeLoading: false,
+        current: {},
+        currentKey: ''
+      };
+    },
+    mounted() {
+      if (this.init) {
+        this.getTreeData();
+      }
+    },
+    methods: {
+      // 获取树结构数据
+      async getTreeData() {
+        try {
+          this.treeLoading = true;
+
+          const res = await treeByPid({ ids: this.treeIds });
+          this.treeLoading = false;
+          if (res?.code === '0') {
+            this.treeList = res.data;
+            this.$emit('setRootId', res.data[0]);
+
+            this.$nextTick(() => {
+              // 默认高亮第一级树节点
+              if (this.treeList[0]) {
+                this.setCurrentKey(this.treeList[0]);
+                this.current = this.treeList[0];
+              }
+            });
+            return this.treeList;
+          }
+        } catch (error) {
+          console.log(error);
+        }
+        this.treeLoading = false;
+      },
+
+      handleNodeClick(data, node) {
+        this.$emit('handleNodeClick', data, node);
+      },
+      // 设置默认高亮行
+      setCurrentKey(id) {
+        this.currentKey = id;
+        this.$refs.tree.setCurrentKey(this.currentKey);
+      },
+
+      // 获取树的选中状态
+      getSelectList() {
+        const selectList = this.$refs.tree.getCurrentNode();
+        return selectList;
+      }
+    }
+  };
+</script>
+
+<style lang="scss" scoped>
+  .tree-wrapper {
+    width: 100%;
+    height: 100%;
+    overflow: auto;
+
+    :deep(.el-tree) {
+      display: inline-block;
+      min-width: 100%;
+    }
+  }
+</style>

+ 271 - 0
src/views/produce/components/outsourcing/index.vue

@@ -0,0 +1,271 @@
+<template>
+    <div class="index_box">
+        <div class="c_header_title">
+            <div class="c_title">委外记录</div>
+        </div>
+        <div>
+            <el-form label-width="100px" :rules="rules" ref="form" :model="attributeData">
+
+                <el-form-item label="委外名称:" prop="name">
+                    <el-input placeholder="" v-model="attributeData.name" style="width: 260px;"></el-input>
+                </el-form-item>
+
+                <el-form-item label="委外类型:" prop="type">
+                    <el-select v-model="attributeData.type" placeholder="请选择" style="width: 260px;">
+                        <el-option v-for="item in typeList" :key="item.id" :label="item.name" :value="item.id">
+                        </el-option>
+                    </el-select>
+                </el-form-item>
+                <el-form-item label="委外数量:" prop="formedNumLast">
+                    <el-input placeholder="请输入委外数量" type="number" v-model="attributeData.formedNumLast"
+                        style="width: 260px;"></el-input>
+                </el-form-item>
+                <el-form-item label="委外到:" prop="taskIds">
+                    <el-select v-model="attributeData.taskIds" placeholder="请选择" style="width: 260px;"
+                        @change="changeTaskId">
+                        <el-option v-for="item in newStepsList" :key="item.taskId" :label="item.taskTypeName"
+                            :value="item.taskId">
+                        </el-option>
+                    </el-select>
+                </el-form-item>
+                <el-form-item label="委外场景:" prop="sceneText">
+                    <el-input placeholder="" v-model="attributeData.sceneText" disabled
+                        style="width: 260px;"></el-input>
+                </el-form-item>
+                <!-- v-if="attributeData.isFirstTask != 1" -->
+                <el-form-item label="直接入库:" borderBottom prop="isInWarehouse" >
+                    <div style="display: flex;">
+                        <div style="font-size: 15px;" v-if="attributeData.clientEnvironmentId == 2">是</div>
+                        <!-- <el-checkbox-group v-model="isInWarehouse" size="15px" v-if="attributeData.clientEnvironmentId != 2 ">
+                            <el-checkbox labelSize="15px" iconSize="10px" activeColor="#157A2C" name="true"
+                                label="是"></el-checkbox>
+                        </el-checkbox-group> -->
+                        <el-checkbox labelSize="15px" iconSize="10px" v-model="isInWarehouse" activeColor="#157A2C" name="true"
+                                label="是" v-if="attributeData.clientEnvironmentId != 2 "></el-checkbox>
+                        <el-select v-if="attributeData.clientEnvironmentId == 2 || isInWarehouse" v-model="attributeData.warehouseId" placeholder="请选择" style="width: 222px;">
+                            <el-option v-for="item in warehouseList" :key="item.id" :label="item.name"
+                                :value="item.id">
+                            </el-option>
+                        </el-select>
+                    </div>
+                </el-form-item>
+
+                <el-form-item label="工艺路线:" borderBottom style="font-size: 15px;" prop="produceRoutingId"
+                    v-if="attributeData.clientEnvironmentId != 2 && attributeData.isFirstTask != 1 && isInWarehouse && isInWarehouse.length == 0">
+
+                    <el-select v-model="attributeData.produceRoutingId" placeholder="请选择" style="width: 260px;">
+                        <el-option v-for="item in produceList" :key="item.id" :label="item.name"
+                            :value="item.id">
+                        </el-option>
+                    </el-select>
+
+                </el-form-item>
+
+
+                <el-form-item label="计划交期:" prop="requireDeliveryTime">
+                    <el-date-picker v-model="attributeData.requireDeliveryTime" value-format="yyyy-MM-dd HH:mm:ss"
+                        style="width: 260px;" type="date" placeholder="选择日期">
+                    </el-date-picker>
+                </el-form-item>
+            </el-form>
+
+            <div class="btn-box">
+                <el-button type="primary" @click="confirm">确认</el-button>
+            </div>
+        </div>
+    </div>
+</template>
+
+<script>
+
+import {getWarehouseList,producerouting} from '@/api/produce/index.js'
+export default {
+    components: {
+
+    },
+    data() {
+        return {
+            attributeData: {
+                name: '',
+                type: '',//类型
+                sceneText: '',//场景
+                formedNumLast: '',//数据
+                taskIds: '',//委外到
+                isFirstTask:'',
+                clientEnvironmentId: 1,//直接入库
+                requireDeliveryTime: '',//计划交期
+                warehouseId: '',//仓库id
+                produceRoutingId: '',//工艺路线id
+            },
+            isInWarehouse:true,
+            produceList:[],
+            warehouseList:[],
+            newStepsList: [],
+            typeList: [{
+                id: 4,
+                name: '带料生产委外'
+            },
+            {
+                id: 5,
+                name: '不带料生产委外'
+            },
+
+            ],
+            rules: {
+                name: [
+                    { required: true, message: '请输入委外名称', trigger: 'blur' },
+                ],
+                type: [
+                    { required: true, message: '请选择委外类型', trigger: 'blur' },
+                ],
+                requireDeliveryTime: [
+                    { required: true, message: '请选择计划交期时间', trigger: 'blur' },
+                ]
+            },
+
+            loading: false,
+            operationType: null,
+            workListIds: [],
+        };
+    },
+    props: {
+        outsourceFormVal: {
+            type: Object,
+            default: () => ({})
+        }
+    },
+
+    watch: {
+        outsourceFormVal: {
+            handler(val) {
+                console.log(val, 'outsourceForm');
+                Object.assign(this.attributeData, val);
+                this.newStepsList = this.attributeData.newStepsList;
+                this.getWarehouseFn();
+                this.produceFn();
+            },
+            deep: true,
+            immediate: true
+        }
+    },
+    computed: {
+        taskObj() {
+            return this.$store.state.user.taskObj;
+        }
+    },
+    methods: {
+
+        // 工艺路线
+        produceFn() {
+            let param = {
+                pageNum: 1,
+                size: -1,
+                routeType: 2
+            }
+            producerouting(param).then(res => {
+                this.produceList = res.list
+
+            })
+        },
+
+        // 仓库 
+        getWarehouseFn() {
+            getWarehouseList().then(res => {
+
+                console.log(res,'仓库数据');
+                this.warehouseList = res.data
+            })
+        },
+
+
+        changeTaskId(e) {
+            console.log(e);
+
+            const arr = this.newStepsList.find(item => item.taskId === e)
+            console.log(arr);
+
+            if (this.newStepsList.length) {
+                const id = this.newStepsList[0].sourceTaskId;
+                //isFirstTask 1是首工序 0不是
+                if (arr.isFirstTask) {
+
+                    this.attributeData.sceneText = "首工序";
+                    this.attributeData.outsourceScene = 1;
+                    if (arr.taskIds !== id) {
+                        this.attributeData.sceneText = "首工序及多工序";
+                        this.attributeData.outsourceScene = 4;
+                    }
+                } else {
+                    if (arr.taskIds === id) {
+                        // 单工序
+                        this.attributeData.sceneText = "单工序"
+                        this.attributeData.outsourceScene = 2;
+                    } else {
+                        //多工序
+                        this.attributeData.sceneText = "多工序"
+                        this.attributeData.outsourceScene = 3;
+                    }
+                }
+
+            } else {
+                uni.showToast({
+                    title: '委外到工序为空',
+                    icon: 'none'
+                })
+            }
+        },
+
+        //跳转
+
+        confirm() {
+            this.$refs.form.validate((valid) => {
+                if (valid) {
+                    console.log(this.attributeData);
+                    this.$emit('changePlugIn', this.attributeData);
+                } else {
+                    console.log('error submit!!');
+                    return false;
+                }
+
+            })
+
+        }
+    },
+    created() {
+        this.operationType = null;
+        this.workListIds = [];
+    },
+
+
+
+};
+</script>
+
+<style scoped>
+.index_box {
+    padding: 0 !important;
+}
+
+.c_header_title {
+    display: flex;
+    align-items: center;
+    margin-bottom: 0;
+    padding-left: 20px;
+    height: 52px;
+    margin-bottom: 10px;
+    box-sizing: border-box;
+    background: var(--table-header-background-color);
+    border-bottom: 1px solid var(--border-color-lighter);
+}
+
+.c_title {
+
+    color: #157a2c;
+    font-size: 16px;
+    font-weight: bold;
+}
+
+.btn-box {
+    margin-left: 50px;
+}
+</style>

+ 669 - 0
src/views/produce/components/outsourcing/outsourceList.vue

@@ -0,0 +1,669 @@
+<template>
+	<!-- 委外下一步 -->
+	<div class="card">
+		<div class="c_header_title">
+			<div class="c_title">委外记录</div>
+		</div>
+		<div class="card_box">
+			<el-descriptions>
+				<el-descriptions-item label="委外名称">{{ outObj.name }}</el-descriptions-item>
+				<el-descriptions-item label="委外类型">{{ outObj.type == 4 ? '带料委外' : '无料委外' }}</el-descriptions-item>
+				<el-descriptions-item label="直接入库">{{ outObj.isInWarehouse == 1 ? '是' : '否' }}</el-descriptions-item>
+			</el-descriptions>
+
+		</div>
+		<el-tabs v-model="activeName">
+			<el-tab-pane label="物品清单" name="0">
+				<div class="materialList">
+					<div class="u-reset" style="display: flex;" v-if="clientEnvironmentId != 2">
+						<el-checkbox color="#fff" v-model="checkedAll" :checked="seletedAll" @change="_seletedAll">全选
+						</el-checkbox>
+						<div class="gxList">勾选:<span style="color: #157A2C">{{ checkListLen || 0 }}个</span></div>
+					</div>
+					<!--  -->
+					<!-- <el-checkbox-group  v-model="checkList"> -->
+						<div v-for="(item, index) in pickOutInList" :key="index">
+							<div class="listBox rx-bs">
+								
+								<div class="listBox-sel">
+									<el-checkbox  v-model="item.checked" color="#fff"
+										@change="e => selectVal(e, item, index)" 
+										v-if='(item.rootCategoryLevelId != 11 || (item.rootCategoryLevelId == 11 && item.status != 1)) && clientEnvironmentId != 2'
+										 >
+										 </el-checkbox>
+
+								</div>
+
+								<div class="listBox-con">
+									<div class="listBox-top rx-bc">
+										<div> {{ item.name }}</div>
+										<div class="code">
+											{{ item.rootCategoryLevelId == 4 ? item.codeNumber : item.code }}
+										</div>
+									</div>
+
+									<div class="listBox-bottom rx">
+										<div v-for="(itm, index) in tableH(item.rootCategoryLevelId)" :key="index"
+											class="items" v-if="!itm.formatter">
+											<span>{{ itm.label }}</span>{{ item[itm.prop] }}
+										</div>
+
+
+
+
+										<div class="items"
+											v-if='(item.rootCategoryLevelId == 1 && item.isConsumable == 1) && item.rootCategoryLevelId != 11 && item.rootCategoryLevelId != 4'>
+											<span>可用库存:</span>{{ item.availableCountBase }} {{ item.unit }}
+										</div>
+
+
+										<div class="items"
+											v-if='([1, 2, 9, 23].includes(Number(item.rootCategoryLevelId)) && item.isConsumable == 0)'>
+											<span>刻码:</span>{{ item.extInfo.engrave }}
+										</div>
+
+
+										<div class="items"
+											v-if='([1, 2, 9, 23].includes(Number(item.rootCategoryLevelId)) && item.isConsumable == 0)'>
+											<span>物料代号:</span>{{ item.extInfo.materielCode }}
+										</div>
+
+
+										<div class="items"
+											v-if='([1, 2, 9, 23].includes(Number(item.rootCategoryLevelId)) && item.isConsumable == 0)'>
+											<span>客户代号:</span>{{ item.extInfo.clientCode }}
+										</div>
+
+
+										<div class="items" style="width: 15%;"
+											v-if='([1, 2, 9, 23].includes(Number(item.rootCategoryLevelId)) && item.isConsumable == 0)'>
+											<span>重量:</span>{{ item.extInfo.newWeight }} {{ item.extInfo.weightUnit }}
+										</div>
+
+
+										<div class="items" style="width: 15%;"
+											v-if='([1, 2, 9, 23].includes(Number(item.rootCategoryLevelId)) && item.isConsumable == 1)'>
+											<span>数量:</span>{{ item.feedQuantity }}
+										</div>
+
+										<div class="items" style="width: 15%;"
+											v-if='([1, 2, 9, 23].includes(Number(item.rootCategoryLevelId)) && item.isConsumable == 1)'>
+											<span>重量:</span>{{ item.weight || 0 }} {{ item.weightUnit }}
+										</div>
+
+										<div class="items"
+											v-if='([1, 2, 9, 23].includes(Number(item.rootCategoryLevelId)) && item.isConsumable == 1)'>
+											<span>规格:</span> {{ item.specification }}
+										</div>
+
+										<div class="items"
+											v-if='([1, 2, 9, 23].includes(Number(item.rootCategoryLevelId)) && item.isConsumable == 1)'>
+											<span>型号:</span> {{ item.modelType }}
+										</div>
+
+									</div>
+
+								</div>
+							</div>
+						</div>
+					<!-- </el-checkbox-group> -->
+				</div>
+
+			</el-tab-pane>
+			<el-tab-pane label="带料清单" name="1">
+				<div class="materialList">
+					<div class="u-reset">
+						<el-button type="primary" size="small" class="u-reset-button" @click="openPicking(2)">
+							添加
+						</el-button>
+					</div>
+
+					<div v-for="(item, index) in bomMaterialList" :key="index">
+						<label class="listBox rx-bs">
+
+
+							<div class="listBox-con">
+
+
+								<div class="listBox-bottom rx">
+									<div class="items">
+										<span>序号</span>{{ index + 1 }}
+									</div>
+									<div class="items">
+										<span>名称</span>{{ item.name }}
+									</div>
+
+
+									<div class="items">
+										<span>编码</span>{{ item.code }}
+									</div>
+
+
+									<div v-for="(itm, index) in tableH(item.rootCategoryLevelId)" :key="index"
+										class="items" v-if="!itm.formatter">
+										<span>{{ itm.label }}</span>{{ item[itm.prop] }}
+									</div>
+
+									<div class="items" v-if="item.isDemandQuantity && clientEnvironmentId != 2"
+										style="width: 15%;">
+										<span>数量</span>{{ checkListLen == 0 ? item.demandQuantity : item.count * (
+											checkListLen || 1) }}
+									</div>
+									<div class="items content_num"
+										v-if="!item.isDemandQuantity && clientEnvironmentId != 2" style="width: 15%;">
+										<span>数量</span> <input style="width: 8px !important"
+											v-model="item.demandQuantity"></input>
+									</div>
+
+									<div class="items" v-if="item.isDemandQuantity && clientEnvironmentId == 2"
+										style="width: 15%;">
+										<span>数量</span>{{ item.count * (outObj.formedNumLast || 1) }}
+									</div>
+									<div class="items content_num"
+										v-if="!item.isDemandQuantity && clientEnvironmentId == 2" style="width: 15%;">
+										<span>数量</span> <input style="width:8rpx !important"
+											v-model="item.demandQuantity"></input>
+									</div>
+
+
+
+								</div>
+
+							</div>
+
+
+						</label>
+
+					</div>
+				</div>
+			</el-tab-pane>
+			<el-tab-pane label="产出清单" name="2">
+				<div class="materialList">
+					<div class="u-reset">
+						<el-button type="primary" size="small" class="u-reset-button" @click="openPicking(3)">
+							添加
+						</el-button>
+					</div>
+					<div v-for="(item, index) in standardOutputList" :key="index">
+						<label class="listBox rx-bs">
+
+							<div class="listBox-con">
+
+
+								<div class="listBox-bottom rx">
+									<div class="items" style="width: 15%;">
+										<span>序号</span>{{ index + 1 }}
+									</div>
+									<div class="items">
+										<span>名称</span>{{ item.name }}
+									</div>
+
+									<div class="items">
+										<span>编码</span>{{ item.code }}
+									</div>
+
+
+									<div v-for="(itm, index) in tableH(item.rootCategoryLevelId)" :key="index"
+										class="items" v-if="!itm.formatter">
+										<span>{{ itm.label }}</span>{{ item[itm.prop] }}
+									</div>
+
+									<div class="items content_num">
+										<span>数量</span> <input style="width: 8rpx !important"
+											v-model="item.demandQuantity"></input>
+									</div>
+
+
+
+
+								</div>
+
+							</div>
+
+
+						</label>
+
+					</div>
+				</div>
+			</el-tab-pane>
+		</el-tabs>
+
+		<div class="operate_box  rx-bc">
+			<el-button size="small" class="u-reset-button" @click="close">
+				取消
+			</el-button>
+			<el-button type="primary" size="small" class="u-reset-button" @click="handOK(0)">
+				提交
+			</el-button>
+
+			<el-button type="primary" size="small" class="u-reset-button" @click="handOK(1)">
+				提交并发布
+			</el-button>
+
+		</div>
+
+		<pickingList ref="pickingListRef" isType="weiwai" @allSelection="allSelection"></pickingList>
+	</div>
+</template>
+
+<script>
+import {
+	// 	checkOutsourceMaterial,
+	applyoutsourceSave,
+	// 	getWarehouseList
+} from '@/api/produce/index.js'
+
+
+
+import {
+	tableHeader
+} from '@/utils/dict/common.js'
+// import {
+// 	EventBus
+// } from '@/utils/eventBus.js'
+import pickingList from './pickingList.vue'
+export default {
+	components: { pickingList },
+	data() {
+		return {
+			checkListLen: 0,
+			checkedAll:true,
+			checkList: [],
+			mode: 'center',
+			show: false,
+			topHight: 20 || 20,
+			activeName: "0",
+			outObj: {
+				name: '111',
+				type: 4,
+				isInWarehouse: 1
+			},
+
+			tabList: [{
+				name: '物品清单'
+			},
+			{
+				name: '带料清单'
+			},
+			{
+				name: '产出清单'
+			}
+			],
+
+			actTab: '物品清单',
+			datapickOutInList: [],
+			bomMaterialList: [],
+			pickOutInList: [],
+			materialList: [],
+			standardOutputList: [],
+
+			isFirstTask: null,
+
+			// clientEnvironmentId: uni.getStorageSync("userInfo") && uni.getStorageSync("userInfo")
+			// 	.clientEnvironmentId, // *1 主环境-601环境   2 soll-索尔环境    3 tg-碳谷环境
+
+
+			seletedAll: false, //全选状态
+			checkListLen: 0,
+			
+			warehouseList: []
+		}
+	},
+
+	created() {
+		// EventBus.$on('outEvent', this.handleEvent);
+		// this.outsourceMaterialFn()
+	},
+
+	computed: {
+		clientEnvironmentId() {
+			return this.$store.state.user.info.clientEnvironmentId;
+		}
+	},
+
+	props: {
+		outsourceFormVal: {
+			type: Object,
+			default: () => { }
+		},
+	},
+	watch: {
+		outsourceFormVal: {
+			handler(val) {
+				console.log(val, 'outsourceFormVal');
+				this.outsourceMaterialFn(val);
+				this.outObj = val;
+			},
+			deep: true,
+			immediate: true
+		}
+	},
+
+
+
+	methods: {
+		// open(obj) {
+		// 	// this.outObj = obj;
+		// 	this.actTab = '物品清单';
+		// 	// this.outsourceMaterialFn()
+		// 	// this.getWarehouseFn()
+		// },
+		allSelection(e, item) {
+			if (e == 2) {
+				if (item.length) {
+					item.map(v => {
+						this.bomMaterialList.push(v)
+					})
+				}
+				;
+				console.log(this.bomMaterialList);
+			} else if (e == 3) {
+				if (item.length) {
+
+					this.standardOutputList = item;
+				}
+			}
+
+		},
+
+
+		openPicking(id) {
+			this.$refs.pickingListRef.open(id);
+		},
+
+
+		outsourceMaterialFn(res) {
+
+			let _arr = []
+			_arr = [...res.pickOutInList, ...res.materialList]
+
+			this.pickOutInList = _arr.reduce((acc, item) => {
+				const existingItem = acc.find(existing => existing.id === item.id);
+				if (!existingItem) {
+					acc.push(item);
+				}
+				return acc;
+			}, []);
+
+
+			this.bomMaterialList = res.bomMaterialList.map((m) => {
+				return {
+					...m,
+					isDemandQuantity: true
+
+				}
+			})
+
+			this.pickOutInList.map(v => {
+				v.checked = true;
+			})
+			
+			this.checkListLen = this.pickOutInList.length;
+
+			this.standardOutputList = res.standardOutputList
+
+			// let param = {
+			// 	taskId: this.outObj.taskId,
+			// 	taskIds: this.outObj.taskIds,
+			// 	workOrderId: this.outObj.workOrderId
+
+			// }
+			// checkOutsourceMaterial(param).then(res => {
+
+
+
+
+			// 	let _arr = []
+			// 	_arr = [...res.pickOutInList, ...res.materialList]
+			// 	this.pickOutInList = _arr.reduce((acc, item) => {
+			// 		const existingItem = acc.find(existing => existing.id === item.id);
+			// 		if (!existingItem) {
+			// 			acc.push(item);
+			// 		}
+			// 		return acc;
+			// 	}, []);
+
+
+			// 	this.bomMaterialList = res.bomMaterialList.map((m) => {
+			// 		return {
+			// 			...m,
+			// 			isDemandQuantity: true
+
+			// 		}
+			// 	})
+			// 	this.standardOutputList = res.standardOutputList
+			// 	this.$forceUpdate()
+			// })
+		},
+
+
+		// 仓库 
+		getWarehouseFn() {
+			getWarehouseList().then(res => {
+				this.warehouseList = res
+			})
+		},
+
+
+		handTab(item) {
+			this.actTab = item.name
+		},
+		//关闭弹窗
+		close() {
+			this.$emit('closeForm')
+		},
+
+		handleEvent({
+			message
+		}) {
+			if (message.pid == 3) {
+				this.standardOutputList = message.memoList
+			} else {
+				if (message.pid == 2) {
+					this.bomMaterialList = message.memoList
+				}
+			}
+
+
+		},
+
+		tableH(type) {
+			return tableHeader(type)
+		},
+		//勾选
+		selectVal(e, val, index) {
+			this.$forceUpdate()
+			this.pickOutInList[index] = val
+			this.$set(this, 'pickOutInList', this.pickOutInList)
+			
+			this.checkListLen = this.pickOutInList.filter(f => f.checked == true).length;
+		},
+
+		_seletedAll() {
+
+			console.log(this.seletedAll,this.pickOutInList,'this.seletedAll');
+			// this.seletedAll true 是全选 
+
+			if (!this.seletedAll) {
+				// 非全选
+				this.seletedAll = true;
+				this.checkListLen = 0;
+				
+				this.pickOutInList.map(item => {
+					item.checked =false;
+				})
+
+				this.$set(this, 'pickOutInList', this.pickOutInList)
+
+			} else {
+				this.seletedAll = false;
+				
+				this.pickOutInList.map(item => {
+					item.checked =true;
+				})
+				this.$set(this, 'pickOutInList', this.pickOutInList)
+
+			}
+			this.checkListLen = this.pickOutInList.filter(f => f.checked == true).length
+		},
+
+
+
+		scrolltolower() { },
+
+		addPicking(id) {
+			const storageKey = Date.now() + "";
+			let arr = null
+			if (id == 3) {
+				arr = [{
+					standardOutputList: this.standardOutputList,
+				}]
+
+			} else {
+				arr = [{
+					bomMaterialList: this.bomMaterialList,
+				}]
+			}
+
+			// uni.setStorageSync(storageKey, arr);
+			// uni.navigateTo({
+			// 	url: `/pages/pda/workOrder/search/index?id=${id}&storageKey=${storageKey}&isType=zdy&taskId=${this.outObj.taskId}&classIds=[1,23,9]`
+			// })
+		},
+
+		handOK(isRelease) {
+			// isRelease? 0 提交 2提交并发布
+		
+			if (this.checkListLen > 0 && !this.outObj.warehouseId) {
+				return this.$message({
+					message: "请选择仓库",
+					type: "warning"
+				})
+			}
+
+
+			// 环境判断
+			let _pickOutInList = []
+
+			if (this.clientEnvironmentId == 2) {
+				_pickOutInList = this.pickOutInList
+			} else {
+				_pickOutInList = this.pickOutInList.filter(f => f.checked == true)
+			}
+
+
+
+			let param = {
+				...this.outObj,
+				isRelease: isRelease,
+				bomMaterialList: this.bomMaterialList,
+				pickOutInList: _pickOutInList,
+				materialList: this.materialList,
+				standardOutputList: this.standardOutputList,
+			}
+			applyoutsourceSave(param).then(res => {
+				return this.$message({
+					message: "提交成功",
+					type: "scuccess"
+				})
+				this.checkListLen = 0
+
+			})
+		},
+	}
+}
+</script>
+
+<style lang="scss" scoped>
+.c_header_title {
+	display: flex;
+	align-items: center;
+	margin-bottom: 0;
+	height: 58px;
+	margin-bottom: 10px;
+	box-sizing: border-box;
+	border-bottom: 1px solid var(--border-color-lighter);
+}
+
+.operate_box {
+	padding: 15px;
+	box-shadow: 0px -2px 15px 0px rgba(0, 0, 0, 0.1);
+}
+
+.c_title {
+
+	color: #157a2c;
+	font-size: 16px;
+	font-weight: bold;
+}
+
+.materialList {
+	height: 55vh;
+	overflow-y: auto;
+}
+
+.card {
+	width: 100%;
+	padding: 0 20px;
+}
+
+.u-reset {
+	width: 100%;
+	padding: 5px;
+	text-align: right;
+}
+
+.listBox-con {
+	width: 100%;
+
+
+}
+.gxList{
+	margin-left: 10px;
+}
+
+
+.listBox-sel {
+	margin: 0 10px
+}
+
+.listBox-top {
+	display: flex;
+	padding: 15px;
+	font-size: 14px;
+	font-weight: bold;
+	border-bottom: 1px solid #ddd;
+}
+
+.listBox-bottom {
+	display: flex;
+	width: 100%;
+	flex-wrap: wrap;
+	margin-bottom: 0;
+}
+
+.listBox {
+	display: flex;
+	align-items: center;
+	border: 1px solid #ddd;
+	margin-bottom: 20px;
+}
+
+.items {
+	font-size: 12px;
+	width: 28%;
+	display: flex;
+	align-items: center;
+
+	// border: 1px solid #ddd;
+	// border-bottom: 1px solid #ddd;
+	// border-right: 0;
+	span {
+		display: block;
+		padding: 10px;
+		margin-right: 5px;
+		color: #157a2c;
+		background-color: #f7f9fa;
+	}
+}
+</style>

+ 189 - 0
src/views/produce/components/outsourcing/outsourcingList.vue

@@ -0,0 +1,189 @@
+<template>
+    <div class="ele-body">
+      <el-card shadow="never" v-loading="loading">
+        <return-search @search="reload" ref="searchRef"> </return-search>
+  
+        <!-- 数据表格 -->
+        <ele-pro-table
+          ref="table"
+          :columns="columns"
+          :datasource="datasource"
+          row-key="id"
+          cache-key="returnKey"
+          autoAmendPage
+          :parse-data="parseData"
+          :selection.sync="selection"
+        >
+          <template v-slot:toolbar>
+            <el-button type="primary" size="mini" @click="handleReturn"
+              >新建</el-button
+            >
+          </template>
+  
+          <template v-slot:scene="{ row }">
+            {{ sceneListFn(row.scene) }}
+          </template>
+  
+          <template v-slot:action="{ row }">
+            <el-button type="text" size="mini" @click="handDetailed(row)"
+              >详情</el-button
+            >
+          </template>
+        </ele-pro-table>
+      </el-card>
+  
+      <returnPop
+        v-if="returnShow"
+        :returnDetailsId="returnDetailsId"
+        @close="close"
+        :sceneList="sceneList"
+      ></returnPop>
+    </div>
+  </template>
+  
+  <script>
+
+    export default {
+      components: {
+        returnSearch,
+        returnPop
+      },
+      data() {
+        return {
+          // 加载状态
+          loading: false,
+          selection: [],
+  
+          returnShow: false,
+          returnDetailsId: null,
+  
+          sceneList: []
+        };
+      },
+      computed: {
+        columns() {
+          return [
+            {
+              prop: 'remark',
+              label: '材料名称',
+              align: 'center'
+            },
+            {
+              prop: 'remark',
+              label: '材料名称',
+              align: 'center'
+            },
+            {
+              prop: 'code',
+              label: '牌号',
+              align: 'center'
+            },
+  
+            {
+              prop: 'name',
+              label: '型号',
+              align: 'center'
+            },
+  
+            {
+              slot: 'scene',
+              prop: 'scene',
+              label: '模孔数量',
+              align: 'center'
+            },
+  
+            {
+              prop: 'executorName',
+              label: '芯棒直径',
+              align: 'center'
+            },
+  
+            {
+              prop: 'executorTime',
+              label: '收缩系数',
+              align: 'center'
+            },
+        
+          ];
+        }
+      },
+      created() {
+        this.getByCodeFn();
+      },
+      methods: {
+        /* 表格数据源 */
+        async datasource({ page, limit, where }) {
+          let res = await returnPage({
+            ...where,
+  
+            pageNum: page,
+            size: limit
+          });
+  
+          return res;
+        },
+  
+        // 新增退料
+        handleReturn() {
+          this.returnDetailsId = null;
+          this.returnShow = true;
+        },
+  
+        close(val) {
+          if (val) {
+            this.reload();
+          }
+          this.returnDetailsId = null;
+          this.returnShow = false;
+        },
+  
+        //查看详情
+        handDetailed(row) {
+          this.returnDetailsId = row.id;
+          this.returnShow = true;
+        },
+  
+        getByCodeFn() {
+          getByCode('returnScenario').then((res) => {
+            let _arr = [];
+            res.data.map((item) => {
+              const key = Object.keys(item)[0];
+              const value = item[key];
+              _arr.push({ label: value, value: key });
+            });
+  
+            this.sceneList = _arr;
+          });
+        },
+  
+        sceneListFn(val) {
+          let _arr = this.sceneList;
+          for (const item of _arr) {
+            if (item.value == val) {
+              return item.label;
+            }
+          }
+        },
+  
+        /* 刷新表格 */
+        reload(where = {}) {
+          this.$refs.table.reload({ page: 1, where });
+        },
+  
+        /* 数据转为树形结构 */
+        parseData(data) {
+          return {
+            ...data,
+            list: this.$util.toTreeData({
+              data: data.list,
+              count: data.total,
+  
+              idField: 'id',
+              parentIdField: 'parentId'
+            })
+          };
+        }
+      }
+    };
+  </script>
+  

+ 643 - 0
src/views/produce/components/outsourcing/pickingList.vue

@@ -0,0 +1,643 @@
+<template>
+  <el-dialog title="领料列表" :visible.sync="visible" v-if="visible" :before-close="handleClose"
+    :close-on-click-modal="false" :close-on-press-escape="false" append-to-body width="75%">
+    <el-card shadow="never">
+      <pickingListSearch @search="reload" ref="searchRef" />
+
+      <ele-split-layout width="244px" allow-collapse :right-style="{ overflow: 'hidden' }">
+        <div class="ele-border-lighter split-layout-right-content">
+          <AssetTree ref="assetTreeRef" :treeIds="treeIds" @handleNodeClick="handleNodeClick" @setRootId="setRootId" />
+        </div>
+        <!-- 表格 -->
+
+        <template v-slot:content>
+          <ele-pro-table :initLoad="false" ref="table" :columns="columns" :datasource="datasource"
+            :selection.sync="selection" row-key="id" height="calc(100vh - 350px)" class="dict-table"
+            :cache-key="tableKey" :row-style="rowStyle" :row-click-checked="true" :row-click-checked-intelligent="false"
+            @update:selection="handleSelectionChange">
+            <template v-slot:toolbar>
+              <el-alert type="info" :closable="false" class="ele-alert-border" style="width: 300px">
+                <i class="el-icon-info ele-text-info"></i>
+                <span class="ele-text">
+                  <span>
+                    已选择
+                    <b class="ele-text-info">{{ allSelection.length }}</b>
+                    项数据<em></em>
+                  </span>
+                </span>
+                <el-link type="primary" :underline="false" @click="clearChoose">
+                  清空
+                </el-link>
+              </el-alert>
+            </template>
+
+            <template v-slot:code="{ row }">
+              {{ row.rootCategoryLevelId == 4 ? row.codeNumber : row.code }}
+            </template>
+
+            <template v-slot:runStatus="{ row }">
+              {{ stateList[Number(row.runStatus)] }}
+            </template>
+
+            <template v-slot:vehicleLen="{ row }">
+              {{ row.extInfo.vehicleLen || '-' }}
+              {{ row.extInfo.wilde || '-' }} {{ row.extInfo.hight || '-' }}
+            </template>
+
+            <template v-slot:status="{ row }">
+              <span :style="{ color: row.status == 0 ? '#157A2C' : '#FFA929' }">{{
+                row.status == 0 ? '空闲' : row.status == 1 ? '占用' : ''
+              }}</span>
+            </template>
+
+            <template v-slot:packingCountBase="{ row }">
+              {{ row.packingCountBase }} {{ row.minUnit }}
+            </template>
+
+            <template v-slot:availableCountBase="{ row }">
+              {{ row.availableCountBase }} {{ row.measuringUnit }}
+            </template>
+
+            <template v-slot:weight="{ row }">
+              {{ row.weight }} {{ row.weightUnit }}
+            </template>
+
+            <!-- 库存保质期 -->
+            <template v-slot:expirationDate="{ row }">
+              <span v-if="row.expirationDate">
+                {{ row.expirationDate ? row.expirationDate : '-' }}
+                {{
+                  row.expirationDateUnit == 'year'
+                    ? '年'
+                    : row.expirationDateUnit == 'month'
+                      ? '月'
+                      : '日'
+                }}
+              </span>
+            </template>
+            <!-- 质检状态 -->
+            <template v-slot:qualityStatus="{ row }">
+              <span v-if="row.qualityResult == 0 || row.qualityResult == 1">已检</span>
+              <span v-else-if="row.qualityStatus == 1">已检</span>
+              <span v-else-if="row.qualityStatus == 0">未检</span>
+              <span v-else>-</span>
+            </template>
+            <!-- 质检结果 -->
+            <template v-slot:qualityResult="{ row }">
+              <span v-if="row.qualityResult == 0 || row.qualityResult == ''">合格</span>
+              <span v-else-if="row.qualityResult == 1">不合格</span>
+              <span v-else-if="row.qualityResult == 3">让步接收</span>
+              <span v-else>-</span>
+            </template>
+          </ele-pro-table>
+        </template>
+      </ele-split-layout>
+    </el-card>
+
+    <div class="btns">
+      <el-button type="primary" size="small" @click="selected">选择</el-button>
+      <el-button size="small" @click="handleClose">关闭</el-button>
+    </div>
+  </el-dialog>
+</template>
+
+<script>
+import AssetTree from './assetTree.vue';
+import pickingListSearch from './pickingListSearch.vue';
+import {
+  pageeLedgerMain,
+  assetPage,
+  listInProduct
+} from '@/api/produce/workOrder';
+
+import { pdaTreeByPid,outInDetailPdaPage ,categoryGetList} from '@/api/produce/index';
+
+
+export default {
+  components: { AssetTree, pickingListSearch },
+  props: {
+    isType: {
+      type: String,
+      default: '',
+      required: true
+    }
+  },
+  data() {
+    return {
+      visible: false,
+
+      id: null,
+      treeIds: null,
+      categoryLevelId: null,
+      rootCategoryLevelId: null,
+      isCategory: true,
+
+      stateList: [
+        '启动',
+        '空闲',
+        '运行',
+        '故障',
+        '检修',
+        '停机',
+        '待料',
+        '占用'
+      ],
+
+      selection: [],
+
+      allSelection: [],
+      temporaryList: []
+    };
+  },
+
+  computed: {
+    tableKey() {
+      return `table-${this.rootCategoryLevelId}`;
+    },
+
+    // 表格列配置
+    columns() {
+      return [
+        {
+          width: 45,
+          type: 'selection',
+          columnKey: 'selection',
+          align: 'center',
+          reserveSelection: true
+        },
+        {
+          columnKey: 'index',
+          label: '序号',
+          type: 'index',
+          width: 50,
+          align: 'center'
+        },
+        {
+          prop: 'code',
+          label: '编码',
+          slot: 'code'
+        },
+        {
+          prop: 'name',
+          label: '名称',
+          showOverflowTooltip: true
+        },
+        {
+          prop: 'brandNum',
+          label: '牌号',
+          showOverflowTooltip: true
+        },
+        {
+          prop: 'specification',
+          label: '规格',
+          showOverflowTooltip: true
+        },
+        {
+          prop: 'modelType',
+          label: '型号',
+          showOverflowTooltip: true
+        },
+
+        {
+          prop: 'batchNo',
+          label: '批次号',
+          align: 'center'
+        },
+        {
+          prop: 'manualBatchNo',
+          label: '批次号',
+          align: 'center'
+        },
+        {
+          prop: 'availableCountBase',
+          label: '计量库存数量',
+          sortable: 'custom',
+          slot: 'availableCountBase',
+          showOverflowTooltip: true,
+          width: 130,
+          align: 'center'
+        },
+
+        ...([1, 23, 8].includes(Number(this.rootCategoryLevelId))
+          ? [
+            {
+              prop: 'packingCountBase',
+              label: '包装库存',
+              slot: 'packingCountBase',
+              showOverflowTooltip: true
+            }
+          ]
+          : []),
+
+        {
+          prop: 'weight',
+          label: '重量',
+          showOverflowTooltip: true,
+          slot: 'weight'
+        },
+
+        {
+          prop: 'expirationDate',
+          slot: 'expirationDate',
+          label: '库存保质期',
+          width: 100
+        },
+        {
+          prop: 'expirationTime',
+          label: '周期倒计时',
+          showOverflowTooltip: true,
+          width: 100
+        },
+        {
+          prop: 'qualityResult',
+          slot: 'qualityResult',
+          label: '质检结果',
+          showOverflowTooltip: true,
+          width: 100
+        },
+        {
+          prop: 'qualityStatus',
+          slot: 'qualityStatus',
+          label: '质检状态',
+          showOverflowTooltip: true,
+          width: 100
+        },
+        {
+          prop: 'pathName',
+          width: 230,
+          label: '仓库',
+          showOverflowTooltip: true
+        },
+
+        ...(this.rootCategoryLevelId == '4'
+          ? [
+            {
+              prop: 'workstationName',
+              label: '工位',
+              showOverflowTooltip: true
+            },
+
+            {
+              prop: 'runStatus',
+              label: '状态',
+              slot: 'runStatus',
+              showOverflowTooltip: true
+            }
+          ]
+          : []),
+
+        // ...(this.rootCategoryLevelId == '5'
+        //   ? [
+        //       {
+        //         prop: 'dieHoleNum',
+        //         label: '模孔数量',
+        //         showOverflowTooltip: true
+        //       },
+        //       {
+        //         prop: 'mandrelDiameter',
+        //         label: '芯棒直径',
+        //         showOverflowTooltip: true
+        //       },
+        //       {
+        //         prop: 'shrinkEffictive',
+        //         label: '收缩系数',
+        //         showOverflowTooltip: true
+        //       }
+        //     ]
+        //   : []),
+
+        // ...(this.rootCategoryLevelId == '7'
+        //   ? [
+        //       {
+        //         prop: 'materialQuality',
+        //         label: '材质',
+        //         showOverflowTooltip: true
+        //       },
+
+        //       {
+        //         prop: 'vehicleLen',
+        //         label: '长宽高',
+        //         slot: 'vehicleLen',
+        //         showOverflowTooltip: true
+        //       }
+        //     ]
+        //   : []),
+
+        ...(this.rootCategoryLevelId == '8'
+          ? [
+            {
+              prop: 'extInfo.slotNum',
+              label: '槽数',
+              showOverflowTooltip: true
+            }
+          ]
+          : []),
+
+        ...(this.rootCategoryLevelId == '11'
+          ? [
+            {
+              prop: 'status',
+              label: '状态',
+              slot: 'status',
+              showOverflowTooltip: true
+            },
+
+            {
+              prop: 'region',
+              label: '位置',
+              showOverflowTooltip: true
+            }
+          ]
+          : [])
+      ];
+    }
+  },
+  watch: {},
+  methods: {
+    /* 表格数据源 */
+    async datasource({ page, where, limit }) {
+      let URL;
+
+      let param = {
+        ...where,
+        pageNum: page,
+        size: limit,
+        categoryLevelId: this.categoryLevelId
+      };
+      console.log(URL,'URLURLURL');
+
+      if (this.isType == 'pick') {
+        param.dimension = 1;
+
+        URL = pageeLedgerMain;
+
+      } else if (this.isType == 'feed') {
+
+        if ([4, 7, 14].includes(Number(this.rootCategoryLevelId))) {
+          URL = assetPage;
+        } else if (this.rootCategoryLevelId == 2) {
+          param.workOrderId = this.id;
+          delete param.taskId;
+          delete param.categoryLevelId;
+          URL = listInProduct;
+        } else if (
+          ![2, 4, 7, 14].includes(Number(this.rootCategoryLevelId))
+        ) {
+          URL = assetPage;
+        }
+      } else if (this.isType == 'job') {
+        URL = assetPage;
+      } else if (this.isType == 'weiwai') {
+
+        if(this.id==2){
+          param.dimension = 1;
+          URL = outInDetailPdaPage;
+        }else if(this.id==3){
+
+          URL = categoryGetList
+        }
+       
+
+        
+        console.log(URL,'URLURLURL');
+      }
+
+
+
+      const res = await URL(param);
+
+      console.log(res);
+
+      if (this.rootCategoryLevelId == '11') {
+        let _res = res;
+        let _list = [];
+        _res.list.forEach((e) => {
+          if (e.aridRegionList && e.aridRegionList.length != 0) {
+            e.aridRegionList.map((i) => {
+              let obj = {
+                name: e.name,
+                region: e.extInfo.region,
+                rootCategoryLevelId: e.rootCategoryLevelId,
+                ...i,
+                instanceId: i.id
+              };
+              _list.push(obj);
+            });
+          }
+        });
+        res.list = _list;
+        return res;
+      } else {
+        let _res = res;
+        let _list = [];
+
+        _list.push(
+          ..._res.list.map((i) => {
+            const warehouseId = i.pathIds && i.pathIds.split(',')[0];
+
+            return {
+              warehouseId,
+              ...i,
+              instanceId: i.id
+            };
+          })
+        );
+
+        res.list = _list;
+        return res;
+      }
+    },
+
+    handleSelectionChange(data) {
+      console.log(data);
+      this.allSelection = data;
+    },
+
+    /* 清空选择 */
+    clearChoose() {
+      this.allSelection = [];
+      this.$refs.table.clearSelection();
+    },
+    rowStyle({ row }) {
+      return this.selection.includes(row) ? { background: '#e6f7ff' } : null;
+    },
+    handleNodeClick(data) {
+      this.isCategory = true;
+      this.categoryLevelId = data.id;
+      this.rootCategoryLevelId = data.rootCategoryLevelId;
+      this.reload();
+    },
+
+    setRootId(data) {
+      this.categoryLevelId = data.id;
+      this.rootCategoryLevelId = data.rootCategoryLevelId;
+      this.reload();
+    },
+
+    /* 刷新表格 */
+    reload(where) {
+      this.$nextTick(() => {
+        this.isCategory = false;
+        this.$refs.table.reload({ pageNum: 1, where: where });
+      });
+    },
+
+    onDone() {
+      this.$nextTick(() => {
+        this.allSelection.forEach((item) => {
+          this.$refs.table.toggleRowSelection(item, true);
+        });
+      });
+    },
+    open(id, item) {
+      this.id = id;
+      if (this.isType == 'pick') {
+        this.temporaryList = item.pickList || [];
+        this.allSelection = item.pickList || [];
+        this.visible = true;
+        this.$nextTick(() => {
+          this.allSelection.forEach((item) => {
+            this.$refs.table.toggleRowSelection(item, true);
+          });
+        });
+      } else if (this.isType == 'feed') {
+        let feedList = [];
+        feedList = [
+          ...item.modelList,
+          ...item.equipmentList,
+          ...item.instanceList,
+          ...item.aridRegionList,
+          ...item.turnover,
+          ...item.palletList,
+          ...item.revolvingDiskList,
+          ...item.semiProductList
+        ];
+        this.temporaryList = feedList || [];
+        this.allSelection = feedList || [];
+        this.visible = true;
+
+        this.$nextTick(() => {
+          feedList.forEach((item) => {
+            this.$refs.table.toggleRowSelection(item, true);
+          });
+        });
+      } else if (this.isType == 'job') {
+        let feedList = [];
+        feedList = [
+          ...item.turnover,
+          ...item.equipmentList,
+        ];
+        this.temporaryList = feedList || [];
+        this.allSelection = feedList || [];
+        this.visible = true;
+
+        this.$nextTick(() => {
+          feedList.forEach((item) => {
+            this.$refs.table.toggleRowSelection(item, true);
+          });
+        });
+      } else if (this.isType == 'weiwai') {
+
+        this.treeIds = '1,23,9';
+        this.visible = true;
+      }
+    },
+
+    handleClose() {
+      this.clearChoose();
+      this.temporaryList = [];
+      this.allSelection = [];
+      this.visible = false;
+    },
+    selected() {
+      if (this.allSelection.length == 0) {
+        this.$message.warning('请选择物料');
+        return false;
+      }
+
+      console.log(this.temporaryList, 'this.temporaryList');
+      // return
+
+      if (this.temporaryList.length > 0) {
+        // 使用Promise来“模拟”异步操作
+        new Promise((resolve) => {
+          if (this.temporaryList.length > 0) {
+            this.temporaryList.forEach((item) => {
+              this.allSelection.forEach((item2) => {
+                if (item.id == item2.id && this.isType == 'pick') {
+                  this.$set(item2, 'demandQuantity', item.demandQuantity || null);
+                } else if (item.id == item2.id && this.isType == 'feed') {
+                  this.$set(item2, 'feedQuantity', item.feedQuantity || null);
+                }
+              });
+            });
+          }
+          this.allSelection.sort(
+            (a, b) => a.rootCategoryLevelId - b.rootCategoryLevelId
+          );
+
+          resolve();
+        }).then(() => {
+
+          this.$emit('allSelection', this.id, this.allSelection);
+          this.handleClose();
+        });
+      } else {
+
+        this.allSelection.sort(
+          (a, b) => a.rootCategoryLevelId - b.rootCategoryLevelId
+        );
+
+        this.$emit('allSelection', this.id, this.allSelection);
+        this.handleClose();
+      }
+    }
+  },
+
+  created() {
+    if (this.isType == 'pick') {
+      this.treeIds = '1, 5, 7, 8, 10, 13, 14, 23, 26, 9, 28';
+    } else if (this.isType == 'feed') {
+      this.treeIds = '1, 2, 4, 5, 7, 8, 10, 11, 13, 14, 26, 9, 23,28';
+    } else if (this.isType == 'job') {
+      this.treeIds = '4, 7';
+    }
+  }
+};
+</script>
+
+<style lang="scss" scoped>
+.tree_col {
+  border: 1px solid #eee;
+  padding: 10px 0;
+  box-sizing: border-box;
+  height: 500px;
+  overflow: auto;
+}
+
+.table_col {
+  padding-left: 10px;
+
+  ::v-deep .el-table th.el-table__cell {
+    background: #f2f2f2;
+  }
+}
+
+.pagination {
+  text-align: right;
+  padding: 10px 0;
+}
+
+.btns {
+  text-align: center;
+  padding: 10px 0;
+}
+
+.topsearch {
+  margin-bottom: 15px;
+}
+
+::v-deep .is-checked {
+  background: #e6f7ff;
+}
+</style>

+ 170 - 0
src/views/produce/components/outsourcing/pickingListSearch.vue

@@ -0,0 +1,170 @@
+<!-- 搜索表单 -->
+<template>
+  <el-form
+    label-width="77px"
+    class="ele-form-search"
+    @keyup.enter.native="search"
+    @submit.native.prevent
+  >
+    <el-row :gutter="15">
+      <el-col v-bind="styleResponsive ? { lg: 6, md: 12 } : { span: 6 }">
+        <el-form-item label="仓库:" prop="warehouseId">
+          <template>
+            <el-select
+              clearable
+              filterable
+              style="width: 100%"
+              v-model="where.warehouseId"
+              placeholder="请选择"
+            >
+              <el-option
+                v-for="item in warehouseList"
+                :label="item.name"
+                :value="item.id"
+                :key="item.id"
+              >
+              </el-option>
+            </el-select>
+          </template>
+        </el-form-item>
+      </el-col>
+
+      <el-col v-bind="styleResponsive ? { lg: 6, md: 12 } : { span: 6 }">
+        <el-form-item label="物品编码:" prop="code">
+          <el-input
+            clearable
+            placeholder="请输入"
+            v-model.trim="where.code"
+          ></el-input>
+        </el-form-item>
+      </el-col>
+      <el-col v-bind="styleResponsive ? { lg: 6, md: 12 } : { span: 6 }">
+        <el-form-item label="物品名称:" prop="assetName">
+          <el-input
+            clearable
+            v-model="where.assetName"
+            placeholder="请输入"
+          ></el-input>
+        </el-form-item>
+      </el-col>
+      <el-col v-bind="styleResponsive ? { lg: 6, md: 12 } : { span: 6 }">
+        <el-form-item label="批次号:" prop="batchNo">
+          <el-input
+            clearable
+            v-model="where.batchNo"
+            placeholder="请输入"
+          ></el-input>
+        </el-form-item>
+      </el-col>
+      <el-col v-bind="styleResponsive ? { lg: 6, md: 12 } : { span: 6 }">
+        <el-form-item label="批次号:" prop="manualBatchNo">
+          <el-input
+            clearable
+            v-model="where.manualBatchNo"
+            placeholder="请输入"
+          ></el-input>
+        </el-form-item>
+      </el-col>
+
+      <el-col v-bind="styleResponsive ? { lg: 6, md: 12 } : { span: 6 }">
+        <el-form-item label="型号:" prop="modelType">
+          <el-input
+            clearable
+            v-model="where.modelType"
+            placeholder="请输入"
+          ></el-input>
+        </el-form-item>
+      </el-col>
+      <el-col v-bind="styleResponsive ? { lg: 6, md: 12 } : { span: 6 }">
+        <el-form-item label="规格:" prop="specification">
+          <el-input
+            clearable
+            v-model="where.specification"
+            placeholder="请输入"
+          ></el-input>
+        </el-form-item>
+      </el-col>
+
+      <el-col v-bind="styleResponsive ? { lg: 6, md: 12 } : { span: 6 }">
+        <div class="ele-form-actions">
+          <el-button
+            type="primary"
+            icon="el-icon-search"
+            class="ele-btn-icon"
+            @click="search"
+            size="small"
+          >
+            查询
+          </el-button>
+          <el-button
+            @click="reset"
+            icon="el-icon-refresh-left"
+            size="small"
+            type="primary"
+            >重置</el-button
+          >
+        </div>
+      </el-col>
+    </el-row>
+  </el-form>
+</template>
+
+<script>
+  import { getWarehouseList } from '@/api/produce/index.js';
+  export default {
+    data() {
+      // 默认表单数据
+      const defaultWhere = {
+        batchNo: '',
+
+        warehouseId: '',
+        manualBatchNo: '',
+
+        modelType: '',
+        specification: '',
+        code: '',
+
+        assetName: ''
+      };
+      return {
+        defaultWhere,
+        // 表单数据
+        where: { ...defaultWhere },
+        warehouseList: []
+      };
+    },
+    computed: {
+      // 是否开启响应式布局
+      styleResponsive() {
+        return this.$store.state.theme.styleResponsive;
+      }
+    },
+    created() {
+      this.getArguInfo();
+    },
+    methods: {
+      /* 搜索 */
+      search() {
+        this.$emit('search', this.where);
+      },
+      /*  重置 */
+      reset() {
+        this.where = { ...this.defaultWhere };
+        this.search();
+      },
+      //搜索数据源
+      async getArguInfo() {
+        const { data } = await getWarehouseList();
+        this.warehouseList = data;
+      }
+    }
+  };
+</script>
+
+<style>
+  .ele-form-actions {
+    display: inline-block;
+    transform: translate(0);
+    transition: all;
+  }
+</style>

+ 5 - 0
src/views/produce/components/produceOrder.vue

@@ -282,10 +282,15 @@
           return item.id;
         });
         console.log(ids);
+
+
+
         this.$emit('workSelect', ids);
       },
 
       rowClick(e) {
+
+      
         this.$emit('rowClick', e, this.taskObj.id);
       },
 

+ 102 - 118
src/views/produce/components/search.vue

@@ -6,34 +6,20 @@
         返回
       </div>
 
-      <el-form
-        class="search_form"
-        label-width="90px"
-        @keyup.enter.native="search"
-        @submit.native.prevent
-      >
+      <el-form class="search_form" label-width="90px" @keyup.enter.native="search" @submit.native.prevent>
         <el-form-item label="工序名称:">
-          <el-select v-model="search.taskId" @change="changeSelect"  filterable 
-          >
-            <el-option
-              v-for="(item, index) in produceTaskList"
-              :key="index"
-              :label="item.name"
-              :value="item.id"
-            ></el-option>
+          <el-select v-model="search.taskId" @change="changeSelect" filterable>
+            <el-option v-for="(item, index) in produceTaskList" :key="index" :label="item.name"
+              :value="item.id"></el-option>
           </el-select>
         </el-form-item>
 
 
         <el-form-item label="设备名称:">
-          <el-input
-            clearable
-            v-model="search.deviceName"
-            placeholder="请输入"
-          />
+          <el-input clearable v-model="search.deviceName" placeholder="请输入" />
         </el-form-item>
 
-  
+
       </el-form>
     </div>
     <div class="right">
@@ -44,128 +30,126 @@
 </template>
 
 <script>
-  import { listTask } from '@/api/produce/index';
-  export default {
-    data() {
-      return {
-        currentTime: '',
-        userName: JSON.parse(localStorage.getItem('info'))?.name,
-
-        produceTaskList: [],
-        search: {
-          taskId: null,
-          deviceName: null
-        }
-      };
-    },
-    created() {
-      this.getTaskList();
+import { listTask } from '@/api/produce/index';
+export default {
+  data() {
+    return {
+      currentTime: '',
+      userName: JSON.parse(localStorage.getItem('info'))?.name,
+
+      produceTaskList: [],
+      search: {
+        taskId: null,
+        deviceName: null
+      }
+    };
+  },
+  created() {
+    this.getTaskList();
 
 
 
-      this.updateCurrentTime();
-      setInterval(this.updateCurrentTime, 1000); // 每秒更新一次时间
-    },
+    this.updateCurrentTime();
+    setInterval(this.updateCurrentTime, 1000); // 每秒更新一次时间
+  },
 
-    watch: {
-      'search.taskId': {
-        handler(val) {
-          if(val) {
-            this.changeSelect(val)
-          } else {
-            this.$store.commit('user/setTaskObj', {});
-          }
-         
-        },
-        immediate: true,
-      }
-    },
-    methods: {
-      getTaskList() {
-        listTask().then((res) => {
-          this.produceTaskList = res;
+  watch: {
+    'search.taskId': {
+      handler(val) {
+        if (val) {
+          this.changeSelect(val)
+        } else {
+          this.$store.commit('user/setTaskObj', {});
+        }
 
-         
-        });
       },
+      immediate: true,
+    }
+  },
+  methods: {
+    getTaskList() {
+      listTask().then((res) => {
+        this.produceTaskList = res;
+      });
+    },
 
-      changeSelect(e) {
-        let taskObj = {};
-        taskObj = this.produceTaskList.find((item) => item.id === e);
+    changeSelect(e) {
+      let taskObj = {};
+      taskObj = this.produceTaskList.find((item) => item.id === e);
 
-        this.$store.commit('user/setTaskObj', taskObj);
-      },
-      back() {
-        this.$router.go(-1);
-      },
-      updateCurrentTime() {
-        const now = new Date();
-        const year = now.getFullYear();
-        const month = (now.getMonth() + 1).toString().padStart(2, '0'); // 月份是从0开始的
-        const day = now.getDate().toString().padStart(2, '0');
-        const hours = now.getHours().toString().padStart(2, '0');
-        const minutes = now.getMinutes().toString().padStart(2, '0');
-        const seconds = now.getSeconds().toString().padStart(2, '0');
-
-        this.currentTime = `${year}-${month}-${day} ${hours}:${minutes}:${seconds}`;
-      }
+      this.$store.commit('user/setTaskObj', taskObj);
+    },
+    back() {
+      this.$router.go(-1);
+    },
+    updateCurrentTime() {
+      const now = new Date();
+      const year = now.getFullYear();
+      const month = (now.getMonth() + 1).toString().padStart(2, '0'); // 月份是从0开始的
+      const day = now.getDate().toString().padStart(2, '0');
+      const hours = now.getHours().toString().padStart(2, '0');
+      const minutes = now.getMinutes().toString().padStart(2, '0');
+      const seconds = now.getSeconds().toString().padStart(2, '0');
+
+      this.currentTime = `${year}-${month}-${day} ${hours}:${minutes}:${seconds}`;
     }
-  };
+  }
+};
 </script>
 
 <style lang="scss" scoped>
-  .search_box {
-    min-width: 1280px;
-    width: 100%;
-    height: 50px;
-    background: #157a2c;
-    padding: 0 16px;
+.search_box {
+  min-width: 1280px;
+  width: 100%;
+  height: 50px;
+  background: #157a2c;
+  padding: 0 16px;
+  display: flex;
+  align-items: center;
+  justify-content: space-between;
+  font-size: 20px;
+
+  .left {
     display: flex;
     align-items: center;
-    justify-content: space-between;
-    font-size: 20px;
-
-    .left {
-      display: flex;
-      align-items: center;
-      font-size: 16px;
-      color: #fff;
-
-      .back {
-        margin-right: 40px;
-        cursor: pointer;
-      }
+    font-size: 16px;
+    color: #fff;
+
+    .back {
+      margin-right: 40px;
+      cursor: pointer;
     }
+  }
 
-    .right {
-      display: flex;
-      align-items: center;
-      font-size: 16px;
-      color: #fff;
+  .right {
+    display: flex;
+    align-items: center;
+    font-size: 16px;
+    color: #fff;
 
-      .lab {
-        line-height: 50px;
-        margin-left: 60px;
-      }
+    .lab {
+      line-height: 50px;
+      margin-left: 60px;
     }
   }
+}
 
-  .search_form {
-    display: flex !important;
-    height: 50px;
+.search_form {
+  display: flex !important;
+  height: 50px;
 
-    align-items: center;
-  }
+  align-items: center;
+}
 
-  .el-form-item {
-    margin-bottom: 0px !important;
-  }
+.el-form-item {
+  margin-bottom: 0px !important;
+}
 </style>
 
 <style>
-  .search_box {
-    .el-form-item__label {
-      color: #fff !important;
-    }
+.search_box {
+  .el-form-item__label {
+    color: #fff !important;
   }
+}
 </style>

+ 326 - 245
src/views/produce/index.vue

@@ -1,30 +1,17 @@
-
-
 <template>
   <div class="index_box">
     <div class="content_box">
-      <Search></Search>
 
-      <ele-split-layout
-        space="0px"
-        width="45%"
-        :resizable="true"
-        :min-size="200"
-        :max-size="-200"
-        :left-style="{
-          overflow: 'hidden',
-          width: '100%'
-        }"
-        :right-style="{ overflow: 'hidden' }"
-        :responsive="false"
-        style="height: calc(100vh - 70px - 50px - 80px)"
-      >
+      <Search></Search>
+      <ele-split-layout space="0px" width="45%" :resizable="true" :min-size="200" :max-size="-200" :left-style="{
+        overflow: 'hidden',
+        width: '100%'
+      }" :right-style="{ overflow: 'hidden' }" :responsive="false" style="height: calc(100vh - 70px - 50px - 80px)">
         <div class="left_main">
           <div class="top">
-            <produceOrder
-              @workSelect="workSelect"
-              @rowClick="rowClick"
-            ></produceOrder>
+
+            <produceOrder @workSelect="workSelect" @rowClick="rowClick"></produceOrder>
+
           </div>
           <!-- <div class="bottom">
             <productionResource :BomObj="BomObj"></productionResource>
@@ -32,6 +19,8 @@
         </div>
 
         <template v-slot:content>
+
+
           <div class="right_main">
 
             <div v-if="operationType == 'pick'">
@@ -43,17 +32,9 @@
             </div>
 
             <div v-if="operationType == 'job'">
-              <warehousing
-                v-if="taskObj.id == -1"
-                :workListIds="workListIds"
-                ref="wareRef"
-              ></warehousing>
-
-              <jobBooking
-                v-else
-                :workListIds="workListIds"
-                ref="jobRef"
-              ></jobBooking>
+              <warehousing v-if="taskObj.id == -1" :workListIds="workListIds" ref="wareRef"></warehousing>
+
+              <jobBooking v-else :workListIds="workListIds" ref="jobRef"></jobBooking>
             </div>
 
 
@@ -61,6 +42,16 @@
               55
             </div>
 
+            <!-- 委外 -->
+            <div v-if="operationType == 'Outsourcing'&& isType=='3'" class="right_main_box">
+         
+              <outsourcing :outsourceFormVal="outsourceForm" @changePlugIn="changePlugIn" v-if="isStep"></outsourcing>
+        
+              <!--   -->
+              <outsourceList :outsourceFormVal="outObj"  @closeForm="closeForm" v-else></outsourceList>
+
+            </div>
+
           </div>
         </template>
       </ele-split-layout>
@@ -69,271 +60,361 @@
     </div>
 
     <!--领料弹框 -->
-    <picking
-      v-if="pickingShow"
-      @close="pickingClose"
-      :workListIds="workListIds"
-    ></picking>
+    <picking v-if="pickingShow" @close="pickingClose" :workListIds="workListIds"></picking>
+
+    
   </div>
 </template>
 
 <script>
-  import Search from './components/search.vue';
-  import footBtn from './components/footBtn.vue';
-  import produceOrder from './components/produceOrder.vue';
-  import productionResource from './components/productionResource/index.vue';
+import Search from './components/search.vue';
+import footBtn from './components/footBtn.vue';
+import produceOrder from './components/produceOrder.vue';
+import productionResource from './components/productionResource/index.vue';
+import outsourcing from './components/outsourcing/index.vue';
+import picking from './components/picking/index.vue';
+import pickDetails from './components/picking/details.vue';
+
+import feeding from './components/feeding/index.vue';
+
+import jobBooking from './components/jobBooking/index.vue';
+import warehousing from './components/warehousing/index.vue';
+import outsourceList from './components/outsourcing/outsourceList.vue';
+
+
+import { getByTaskId, pcCheckOutsource,getTaskInstanceById,checkOutsourceMaterial } from '@/api/produce/index';
+
+export default {
+  components: {
+    Search,
+    footBtn,
+    produceOrder,
+    productionResource,
+    outsourcing,
+    picking,
+    pickDetails,
+    outsourceList,
+    feeding,
+
+    jobBooking,
+    warehousing
+  },
+  data() {
+    return {
+      loading: false,
+      operationType: null,
+      workListIds: [],
+      isType: '',
+      isStep:true,
+      outsourceForm:{},
+      outObj:{},
+      pickingShow: false,
+      BomObj: {}
+    };
+  },
+
+  computed: {
+    taskObj() {
+      return this.$store.state.user.taskObj;
+    }
+  },
+
+  created() {
+    this.operationType = null;
+    this.workListIds = [];
+  },
+  methods: {
+    closeForm(){
+      this.isStep = true;
+    },
 
-  import picking from './components/picking/index.vue';
-  import pickDetails from './components/picking/details.vue';
+    // 切换组件
+    async changePlugIn(e){
+      this.outObj = e;
 
-  import feeding from './components/feeding/index.vue';
+      let req = {
+        taskId:e.taskId,
+        taskIds:e.taskIds,
+        workOrderId:e.workOrderId
+      }
+     const res =await checkOutsourceMaterial(req);
+    
 
-  import jobBooking from './components/jobBooking/index.vue';
-  import warehousing from './components/warehousing/index.vue';
+     this.outObj = {...this.outObj,...res.data,...this.outsourceForm};
 
-  import { getByTaskId } from '@/api/produce/index';
+     console.log(this.outObj,'this.outObj');
+  
+      this.isStep = false;
 
-  export default {
-    components: {
-      Search,
-      footBtn,
-      produceOrder,
-      productionResource,
+    },
 
-      picking,
-      pickDetails,
+    workSelect(data) {
+      this.isStep = true; 
+      this.operationType = null;
+      this.workListIds = data;
+    },
 
-      feeding,
+    footBtn(t) {
+      this.operationType = t;
 
-      jobBooking,
-      warehousing
-    },
-    data() {
-      return {
-        loading: false,
-        operationType: null,
-        workListIds: [],
-
-        pickingShow: false,
-        BomObj: {}
-      };
-    },
 
-    computed: {
-      taskObj() {
-        return this.$store.state.user.taskObj;
+      if (
+        Object.keys(this.$store.state.user.taskObj).length === 0 &&
+        this.$store.state.user.taskObj.constructor === Object
+      ) {
+        this.$message.warning('请选择工序');
+        return false;
       }
-    },
-
-    created() {
-      this.operationType = null;
-      this.workListIds = [];
-    },
-    methods: {
-      workSelect(data) {
-        this.workListIds = data;
-      },
-
-      footBtn(t) {
-        this.operationType = t;
-
-        if (
-          Object.keys(this.$store.state.user.taskObj).length === 0 &&
-          this.$store.state.user.taskObj.constructor === Object
-        ) {
-          this.$message.warning('请选择工序');
+      if (['pick', 'feed', 'job'].includes(t)) {
+        if (this.workListIds.length == 0) {
+          this.$message.warning('请选择工单列表');
           return false;
         }
-        if (['pick', 'feed', 'job'].includes(t)) {
-          if (this.workListIds.length == 0) {
-            this.$message.warning('请选择工单列表');
-            return false;
-          }
-        }
+      }
 
-        if (t == 'pick') {
-          this.$nextTick(() => {
-            this.$refs.pickListRef.getList(this.workListIds);
-          });
+      if (t == 'pick') {
+        this.$nextTick(() => {
+          this.$refs.pickListRef.getList(this.workListIds);
+        });
 
-        
-        }
 
-        if (t == 'feed') {
+      }
+
+      if (t == 'feed') {
+      }
+
+      // 委外
+      if (t == 'Outsourcing') {
+        if (this.workListIds.length > 1) {
+          return this.$message.warning('委外工序只能选择一个工单!');
+
+        } else if (this.workListIds.length < 1)
+          return this.$message.warning('请选择工单!');
+        else {
+          // /
+          this.handOutsource(this.workListIds[0]);
         }
-      },
+      }
 
-      pickAdd() {
-  this.pickingShow = true;
-      },
 
-      pickingClose(val) {
-        if (val) {
-          this.$nextTick(() => {
-            this.$refs.pickListRef.getList(this.workListIds);
-          });
+    },
+
+    handOutsource(workOrderId) {
+      console.log(this.taskObj,workOrderId);
+      // return 
+      let param = {
+        taskId: this.taskObj.id,
+        workOrderId: workOrderId,
+      }
+      pcCheckOutsource(param).then(res => {
+        this.outsourceForm = {
+          ...res.data,
         }
-        this.pickingShow = false;
-      },
-
-      rowClick(row, taskId) {
-
-        if (taskId) {
-   
-          let params = {
-            categoryId: row.categoryId,
-            taskId: taskId
-          };
-          getByTaskId(params).then((res) => {
-            this.BomObj = res.data;
-            this.$forceUpdate();
-
-      
-          });
+        this.outsourceForm.name = this.taskObj.name + '委外'
+
+        console.log(res,'res');
+        if (res.data.outsource) {
+          this.isType = '3';
+          this.getTaskInstanceByIdFn(workOrderId)
+        } else {
+          return this.$message.warning('此工序不能委外');
         }
-      }
+      })
+
     },
 
-    mounted() {
-      this.$nextTick(() => {
-        const targetElements =
-          document.getElementsByClassName('ele-admin-tabs');
-
-        if (targetElements.length > 0) {
-          // 遍历所有具有 'ele-admin-tabs' 类的元素
-          Array.from(targetElements).forEach((element) => {
-            // 对每个元素添加 'new-ele-admin-tabs' 类
-            element.classList.add('new-ele-admin-tabs');
-          });
+    //获取工单列表
+    getTaskInstanceByIdFn(workOrderId){
+
+      getTaskInstanceById(workOrderId).then((res) => {
+       console.log(res,'res');
+       let {data} = res;
+        if(data.length){
+          data = data.filter(item=>item.type == 1);
+          let arr = data.findIndex(item=>item.sourceTaskId == this.taskObj.id)
+          console.log(arr);
+          if(arr != -1){
+            data.splice(0,arr+1)
+          } 
+          this.$set(this.outsourceForm,'newStepsList',data)
         }
-      });
+
+      })
+
     },
 
-    destroyed() {
-      this.$nextTick(() => {
-        const targetElements =
-          document.getElementsByClassName('ele-admin-tabs');
+    pickAdd() {
+      this.pickingShow = true;
+    },
 
-        if (targetElements.length > 0) {
-          Array.from(targetElements).forEach((element) => {
-            element.classList.remove('new-ele-admin-tabs');
-          });
-        }
-      });
+    pickingClose(val) {
+      if (val) {
+        this.$nextTick(() => {
+          this.$refs.pickListRef.getList(this.workListIds);
+        });
+      }
+      this.pickingShow = false;
+    },
+
+    rowClick(row, taskId) {
+      console.log(row, taskId, '1111111111');
+      if (taskId) {
+        let params = {
+          categoryId: row.categoryId,
+          taskId: taskId
+        };
+        getByTaskId(params).then((res) => {
+          this.BomObj = res.data;
+          this.$forceUpdate();
+        });
+      }
     }
-  };
+  },
+
+  mounted() {
+    this.$nextTick(() => {
+      const targetElements =
+        document.getElementsByClassName('ele-admin-tabs');
+
+      if (targetElements.length > 0) {
+        // 遍历所有具有 'ele-admin-tabs' 类的元素
+        Array.from(targetElements).forEach((element) => {
+          // 对每个元素添加 'new-ele-admin-tabs' 类
+          element.classList.add('new-ele-admin-tabs');
+        });
+      }
+    });
+  },
+
+  destroyed() {
+    this.$nextTick(() => {
+      const targetElements =
+        document.getElementsByClassName('ele-admin-tabs');
+      if (targetElements.length > 0) {
+        Array.from(targetElements).forEach((element) => {
+          element.classList.remove('new-ele-admin-tabs');
+        });
+      }
+    });
+  }
+};
 </script>
 
 <style>
-  .new-ele-admin-tabs {
-    display: none !important;
+.new-ele-admin-tabs {
+  display: none !important;
+}
+
+.c_title {
+  color: #157a2c;
+  font-size: 16px;
+  font-weight: bold;
+}
+
+.tableZ_box {
+  border: 1px solid #e3e5e5;
+  margin: 6px 0;
+
+  &:last-child {
+    border-bottom: none;
   }
 
-  .c_title {
-    color: #157a2c;
-    font-size: 16px;
-    font-weight: bold;
+  .row {
+    width: 100%;
+    display: flex;
   }
 
-  .tableZ_box {
-    border: 1px solid #e3e5e5;
-    margin: 6px 0;
+  .col {
+    width: calc(100% / 5);
+    display: flex;
+    align-items: center;
+    min-width: 200px;
+    min-height: 32px;
+    border-bottom: 1px solid #e3e5e5;
+    border-right: 1px solid #e3e5e5;
 
     &:last-child {
-      border-bottom: none;
-    }
-
-    .row {
-      width: 100%;
-      display: flex;
+      border-right: none;
     }
 
-    .col {
-      width: calc(100% / 5);
+    .name {
       display: flex;
       align-items: center;
-      min-width: 200px;
-      min-height: 32px;
-      border-bottom: 1px solid #e3e5e5;
-      border-right: 1px solid #e3e5e5;
-
-      &:last-child {
-        border-right: none;
-      }
-
-      .name {
-        display: flex;
-        align-items: center;
-        padding: 4px;
-        width: 80px;
-        height: 100%;
-        background-color: #d0e4d5;
-        color: #000;
-      }
-
-      .content {
-        padding: 4px 6px;
-        color: #000;
-      }
+      padding: 4px;
+      width: 80px;
+      height: 100%;
+      background-color: #d0e4d5;
+      color: #000;
     }
 
-    .pd6 {
-      padding: 0 6px;
+    .content {
+      padding: 4px 6px;
+      color: #000;
     }
   }
-</style>
-<style lang="scss" scoped>
-  .index_box {
-    padding: 8px;
-    padding-bottom: 0px;
-    width: 100%;
-
-    min-width: 1280px !important;
-    height: calc(100vh - 60px);
-    overflow-x: auto;
-    /* 当内容超出宽度时,允许水平滚动 */
-    white-space: nowrap;
-    /* 防止内部文本换行,确保所有内容都在一行显示 */
-    scrollbar-width: thin;
-    /* 设置滚动条宽度(浏览器兼容性可能有所不同) */
-    scrollbar-color: #40a9ff transparent;
-    /* 设置滚动条颜色和轨道颜色(同样,浏览器兼容性) */
-  }
-
-  .main {
-    width: 100%;
-    min-width: 1280px;
 
-    height: calc(100vh - 70px - 50px - 80px);
-    display: flex;
-    justify-content: space-between;
+  .pd6 {
+    padding: 0 6px;
   }
-
-  .left_main {
+}
+</style>
+<style lang="scss" scoped>
+.right_main_box{
+  background-color: #fff;
+  height: 100%;
+  box-sizing: border-box;
+}
+.index_box {
+  padding: 8px;
+  padding-bottom: 0px;
+  width: 100%;
+
+  min-width: 1280px !important;
+  height: calc(100vh - 60px);
+  overflow-x: auto;
+  /* 当内容超出宽度时,允许水平滚动 */
+  white-space: nowrap;
+  /* 防止内部文本换行,确保所有内容都在一行显示 */
+  scrollbar-width: thin;
+  /* 设置滚动条宽度(浏览器兼容性可能有所不同) */
+  scrollbar-color: #40a9ff transparent;
+  /* 设置滚动条颜色和轨道颜色(同样,浏览器兼容性) */
+}
+
+.main {
+  width: 100%;
+  min-width: 1280px;
+
+  height: calc(100vh - 70px - 50px - 80px);
+  display: flex;
+  justify-content: space-between;
+}
+
+.left_main {
+  width: 100%;
+  height: 100%;
+  display: flex;
+  flex-direction: column;
+  justify-content: space-around;
+  min-width: 640px;
+
+  .top {
     width: 100%;
     height: 100%;
-    display: flex;
-    flex-direction: column;
-    justify-content: space-around;
-    min-width: 640px;
-
-    .top {
-      width: 100%;
-      height: 100%;
-      overflow: hidden;
-    }
-
-    // .bottom {
-    //   width: 100%;
-    //   min-height: calc((100vh - 70px - 50px - 80px - 20px) / 2);
-    //   overflow: hidden;
-    // }
+    overflow: hidden;
   }
 
-  .right_main {
-    min-width: 640px;
-    height: calc((100vh - 70px - 50px - 80px - 12px));
-    margin-top: 6px;
-    background: #f0f3f3;
-  }
+  // .bottom {
+  //   width: 100%;
+  //   min-height: calc((100vh - 70px - 50px - 80px - 20px) / 2);
+  //   overflow: hidden;
+  // }
+}
+
+.right_main {
+  min-width: 640px;
+  padding-bottom: 12px;
+  height: calc((100vh - 70px - 50px - 80px - 12px));
+  background: #f0f3f3;
+}
 </style>

+ 300 - 0
src/views/produceOrder/components/EquipmentDialog.vue

@@ -0,0 +1,300 @@
+<template>
+  <el-dialog title="选择工艺路线" :visible.sync="equipmentdialog" :before-close="handleClose" :close-on-click-modal="true"
+    :close-on-press-escape="false" append-to-body width="80%">
+    <div>
+      <el-row>
+        <el-form label-width="120px" class="ele-form-search" @keyup.enter.native="search" @submit.native.prevent>
+          <el-row>
+            <el-col v-bind="styleResponsive ? { lg: 8, md: 12 } : { span: 6 }">
+              <el-form-item label="工艺路线组编码:">
+                <el-input clearable v-model.trim="where.code" placeholder="请输入" />
+              </el-form-item>
+            </el-col>
+            <el-col v-bind="styleResponsive ? { lg: 8, md: 12 } : { span: 6 }">
+              <el-form-item label="工艺路线名称:">
+                <el-input clearable v-model.trim="where.name" placeholder="请输入" />
+              </el-form-item>
+            </el-col>
+            <!-- <el-col v-bind="styleResponsive ? { lg: 6, md: 12 } : { span: 6 }">
+              <el-form-item label="生产版本:">
+                <el-select v-model.trim="where.produceVersionId" filterable placeholder="请选择"
+                  :style="{ width: '100%' }">
+                  <el-option v-for="item in versionList" :key="item.code" :label="item.code + '-' + item.name"
+                    :value="item.id">
+                  </el-option>
+                </el-select>
+              </el-form-item>
+            </el-col> -->
+            <el-col v-bind="styleResponsive ? { lg: 8, md: 12 } : { span: 6 }">
+              <el-form-item label="状态:" label-width="70px">
+                <el-select v-model.trim="where.status" filterable placeholder="请选择" style="width: 100%">
+                  <el-option v-for="item in statusList" :key="item.value" :label="item.label" :value="item.value">
+                  </el-option>
+                </el-select>
+              </el-form-item>
+            </el-col>
+          </el-row>
+          <el-row>
+            <el-col v-bind="styleResponsive ? { lg: 8, md: 12 } : { span: 6 }">
+              <el-form-item label="组织机构:">
+                <auth-selection v-model.trim="where.deptIds" style="width: 100%"></auth-selection>
+              </el-form-item>
+            </el-col>
+            <el-col v-bind="styleResponsive ? { lg: 6, md: 12 } : { span: 6 }">
+              <div class="ele-form-actions">
+                <el-button type="primary" icon="el-icon-search" class="ele-btn-icon" @click="search">
+                  查询
+                </el-button>
+                <el-button @click="reset">重置</el-button>
+              </div>
+            </el-col>
+          </el-row>
+        </el-form>
+        <el-col :span="24" class="table_col">
+          <ele-pro-table ref="equiTable" :columns="columns" highlight-current-row :datasource="datasource"
+            :selection.sync="selection" :current.sync="current" :pagination="pagination" @select="handleSelect"
+            cache-key="systemRoleTable3" row-key="id" height="50vh" @done="setSelect">
+          </ele-pro-table>
+        </el-col>
+      </el-row>
+    </div>
+    <div class="btns">
+      <el-button type="primary" size="small" @click="selected">选择</el-button>
+      <el-button size="small" @click="handleClose">关闭</el-button>
+    </div>
+  </el-dialog>
+</template>
+
+<script>
+import { getList, produceroutingPage } from '@/api/classifyManage/itemInformation';
+export default {
+  props: {
+    selectList: Array,
+    type: {
+      default: 1 //1多选 2单选
+    }
+  },
+  data() {
+    const defaultWhere = {
+      code: '',
+      name: '',
+      status: 1,
+      produceVersionId: ''
+    };
+    return {
+      equipmentdialog: false,
+      current: null,
+      // 搜索
+      where: { ...defaultWhere },
+      statusList: [
+        { label: '草稿', value: -1 },
+        { label: '失效', value: 0 },
+        { label: '生效', value: 1 }
+      ],
+      pagination: {
+        pageSize: 20,
+        currentPage: 1,
+        pageSizes: [10, 20, 50, 100],
+      },
+
+
+      versionList: [],
+
+      columns: [
+        {
+          width: 45,
+          type: 'selection',
+          columnKey: 'selection',
+          align: 'center',
+          reserveSelection: true,
+          show: this.type == 1
+        },
+
+        {
+          prop: 'code',
+          label: '工艺路线组编码',
+          showOverflowTooltip: true,
+          align: 'center',
+          minWidth: 110,
+          slot: 'code',
+        },
+        {
+          prop: 'name',
+          label: '工艺路线名称',
+          showOverflowTooltip: true,
+          align: 'center',
+          minWidth: 110
+        },
+
+
+        {
+          prop: 'version',
+          label: '工艺路线版本',
+          align: 'center',
+          showOverflowTooltip: true,
+          minWidth: 110
+        },
+
+        {
+          prop: 'produceVersionName',
+          label: '工艺类型',
+          align: 'center',
+          showOverflowTooltip: true
+        },
+
+        {
+          prop: 'status',
+          label: '状态',
+          align: 'center',
+          slot: 'status',
+          showOverflowTooltip: true,
+          minWidth: 110
+        },
+
+        {
+          slot: 'routeType',
+          label: '类型',
+          align: 'center',
+          showOverflowTooltip: true
+        },
+
+        {
+          slot: 'factoryName',
+          label: '所属工厂',
+          align: 'center',
+          showOverflowTooltip: true
+        },
+
+
+
+
+
+
+      ],
+      tableList: [],
+      categoryLevelId: null,
+      code: null,
+      searchKey: '',
+      selection: []
+    };
+  },
+  computed: {
+    // 是否开启响应式布局
+    styleResponsive() {
+      return this.$store.state.theme.styleResponsive;
+    }
+  },
+  watch: {},
+  methods: {
+    async datasource({ page, limit }) {
+
+      const params = {
+        ...this.where,
+        pageNum: page,
+        size: 20,
+      };
+      const data = await produceroutingPage(params);
+      this.tableList = data.list;
+
+      this.$refs.equiTable.setData(data.list);
+      return data;
+    },
+    open() {
+      this.equipmentdialog = true;
+      this.setSelect();
+    },
+    handleNodeClick(data) {
+      this.categoryLevelId = data.id;
+      this.reload();
+    },
+    reload() {
+      this.where = { ...this.defaultWhere }
+      this.search();
+    },
+
+    search() {
+      this.datasource({ page: 1, limit: 20 })
+
+    },
+
+
+    handleClose() {
+      this.equipmentdialog = false;
+      this.code = '';
+      this.$refs.equiTable.clearSelection();
+    },
+    reset() {
+      this.code = null;
+      this.reload();
+    },
+    // 设置选中
+    setSelect() {
+      // this.$nextTick(() => {
+      //   this.tableList.forEach((row) => {
+      //     this.selectList?.forEach((selected, index) => {
+      //       if (selected.productCode === row.code) {
+      //         this.$refs.equiTable.toggleRowSelection(row, true);
+      //       }
+      //     });
+      //   });
+      // });
+    },
+    // 取消选中
+    handleSelect(selection, row) {
+      this.$refs.equiTable.clearSelection();
+      this.$refs.equiTable.toggleRowSelection(row, true);
+      // if (!selection.find((i) => i.id === row.id)) {
+      //   const index = this.selectList.findIndex(
+      //     (itm) => row.code == itm.productCode
+      //   );
+      //   console.log(index);
+      //   if (index > -1) {
+      //     this.selectList.splice(index, 1);
+      //   }
+      // }
+    },
+    // 选择
+    selected() {
+      let list = this.type == 1 ? this.selection : [this.current]
+      this.$emit('choose', JSON.parse(JSON.stringify(list)));
+      this.handleClose();
+    }
+  }
+};
+</script>
+
+<style lang="scss" scoped>
+.tree_col {
+  border: 1px solid #eee;
+  padding: 10px 0;
+  box-sizing: border-box;
+  max-height: 530px;
+  overflow: auto;
+}
+
+.table_col {
+  padding-left: 10px;
+
+  ::v-deep .el-table th.el-table__cell {
+    background: #f2f2f2;
+  }
+}
+
+.ele-form-actions {
+  margin-left: 20px;
+}
+
+.pagination {
+  text-align: right;
+  padding: 10px 0;
+}
+
+.btns {
+  text-align: center;
+  padding: 10px 0;
+}
+
+.topsearch {
+  margin-bottom: 15px;
+}
+</style>

+ 38 - 3
src/views/produceOrder/index.vue

@@ -106,6 +106,15 @@
               取消完结
             </el-link></template
           >
+          <el-link
+              v-if="row.status == 4 && row.isSplit == 0"
+              type="primary"
+              :underline="false"
+            
+              @click="routing(row)"
+            >
+              工艺路线
+          </el-link>
           <template v-if="activeName != 'second'">
             <el-link
               v-if="row.status == 4 && row.isSplit == 0"
@@ -147,6 +156,7 @@
     <pickingDialog ref="PickingRef" />
 
     <detailsPop ref="detailsRef"> </detailsPop>
+    <EquipmentDialog ref="equipmentRef" @choose="choose"></EquipmentDialog>
   </div>
 </template>
 
@@ -155,7 +165,8 @@
     getPage,
     batchCompletion,
     cancelCompletion,
-    updatePriority
+    updatePriority,
+    update
   } from '@/api/produceOrder/index.js';
 
   import { fieldModel } from '@/api/produceWord/index.js';
@@ -166,7 +177,7 @@
   import print from './components/print.vue';
   import printSr from './components/printSr';
   import printTg from './components/printTg';
-  
+  import EquipmentDialog from './components/EquipmentDialog.vue'
   import detailsPop from './components/details/index.vue'
 
   import { debounce } from 'lodash';
@@ -181,11 +192,13 @@
       print,
       printSr,
       printTg,
-      detailsPop
+      detailsPop,
+      EquipmentDialog
     },
     data() {
       return {
         activeName: 'first',
+        id: '',
 
         // 加载状态
         loading: false,
@@ -425,6 +438,13 @@
 
         return obj && obj.label;
       },
+
+      routing(row){
+        this.id = row.id
+
+        this.$refs.equipmentRef.open()
+      },
+
       /* 表格数据源 */
       async datasource({ page, limit, where, order }) {
         let res = await getPage({
@@ -647,6 +667,21 @@
         return ids;
       },
 
+      choose(row) {
+       this.updateFn(row);
+      },
+
+      async updateFn(row){
+        let req = {
+          id:this.id,	//工艺路线id		false	
+          produceRoutingId:row[0].id,	//工艺路线id		false	
+          produceRoutingName:row[0].name,
+
+        };
+        const res = await update(req);
+        this.reload();
+      },
+
       sortTop(row) {
         row.priority = Number(row.priority) + 1;
         this.priorityChange(row);

+ 5 - 2
vue.config.js

@@ -33,8 +33,11 @@ module.exports = {
       '/api': {
         // target: 'http://124.71.68.31:50001',
         // target: 'http://192.168.1.116:18086',
-        target: 'http://192.168.1.251:18086',
-        // target: 'http://192.168.1.125:18086',
+        // target: 'http://192.168.1.251:18086',
+        // target: 'http://192.168.1.103:18086',
+
+        
+        target: 'http://192.168.1.125:18086',
         changeOrigin: true, // 只有这个值为true的情况下 才表示开启跨域
         pathRewrite: {
           '^/api': ''