Explorar o código

Merge remote-tracking branch 'origin/dev' into dev

# Conflicts:
#	src/enum/dict.js
#	src/layout/components/header-tools.vue
Z hai 1 ano
pai
achega
346099038b
Modificáronse 43 ficheiros con 2630 adicións e 560 borrados
  1. BIN=BIN
      dist.rar
  2. 23 0
      src/api/codeManagement/index.js
  3. 24 0
      src/api/material/BOM.js
  4. 40 0
      src/api/material/inspectionClassify.js
  5. 38 1
      src/api/system/file/index.js
  6. 120 0
      src/components/upload/import-dialog.vue
  7. 4 1
      src/enum/dict.js
  8. 5 5
      src/layout/components/header-tools.vue
  9. 117 0
      src/views/classifyManage/treeClassify/components/upload-dialog.vue
  10. 19 4
      src/views/classifyManage/treeClassify/index.vue
  11. 11 1
      src/views/enterpriseModel/dept/index.vue
  12. 31 9
      src/views/factoryModel/station/components/edit.vue
  13. 1 3
      src/views/factoryModel/station/index.vue
  14. 1 1
      src/views/factoryModel/workshop/index.vue
  15. 124 0
      src/views/material/BOMmanage/components/BOM-search.vue
  16. 12 24
      src/views/material/BOMmanage/components/StepModal1.vue
  17. 163 71
      src/views/material/BOMmanage/components/attribute.vue
  18. 19 13
      src/views/material/BOMmanage/components/baseInfo.vue
  19. 86 48
      src/views/material/BOMmanage/components/bomTreeDialog.vue
  20. 197 0
      src/views/material/BOMmanage/components/detailedList.vue
  21. 13 1
      src/views/material/BOMmanage/components/processModal.vue
  22. 25 4
      src/views/material/BOMmanage/components/routing.vue
  23. 21 14
      src/views/material/BOMmanage/components/routingDialog.vue
  24. 270 0
      src/views/material/BOMmanage/components/standardOutput.vue
  25. 153 210
      src/views/material/BOMmanage/components/workingProcedure.vue
  26. 89 21
      src/views/material/BOMmanage/details.vue
  27. 48 29
      src/views/material/BOMmanage/index.vue
  28. 126 0
      src/views/material/BOMmanage/qualityTesting/import-dialog.vue
  29. 224 0
      src/views/material/BOMmanage/qualityTesting/inspectionClassify/components/edit.vue
  30. 165 0
      src/views/material/BOMmanage/qualityTesting/inspectionClassify/components/user-list.vue
  31. 84 0
      src/views/material/BOMmanage/qualityTesting/inspectionClassify/components/user-search.vue
  32. 105 0
      src/views/material/BOMmanage/qualityTesting/inspectionClassify/index.vue
  33. 0 0
      src/views/material/BOMmanage/qualityTesting/spot.vue
  34. 20 0
      src/views/material/BOMmanage/qualityTesting/term.vue
  35. 30 30
      src/views/material/product/components/index-data.vue
  36. 129 59
      src/views/material/product/detail.vue
  37. 4 2
      src/views/system/organization/components/org-user-edit.vue
  38. 11 1
      src/views/system/organization/components/org-user-list.vue
  39. 20 1
      src/views/technology/production/index.vue
  40. 1 0
      src/views/technology/route/components/user-taskinstance.vue
  41. 16 4
      src/views/technology/stepManagement/index.vue
  42. 40 2
      src/views/workforceManagement/team/components/userTable.vue
  43. 1 1
      vue.config.js

BIN=BIN
dist.rar


+ 23 - 0
src/api/codeManagement/index.js

@@ -58,3 +58,26 @@ export async function checkCode (code) {
   }
   return Promise.reject(new Error(res.data.message));
 }
+
+// 根据根级物品id升级物品编码
+export async function rootCategoryCode (rootCategoryLevelId) {
+  const res = await request.get(`/main/category/copyInfo/${rootCategoryLevelId}`);
+  if (res.data.code == 0) {
+    return res.data.data;
+  }
+  return Promise.reject(new Error(res.data.message));
+}
+
+
+
+
+// 动态表头
+export async function fieldModel(params) {
+  const res = await request.get(
+    `/main/fieldmodel/list`, { params }
+  );
+  if (res.data.code == 0) {
+    return res.data.data;
+  }
+  return Promise.reject(new Error(res.data.message));
+}

+ 24 - 0
src/api/material/BOM.js

@@ -158,6 +158,18 @@ export async function getBomPageList(params) {
   return Promise.reject(new Error(res.data.message));
 }
 
+// 获取产品BOM列表
+export async function getBomPageCategoryId(params) {
+  const res = await request.get(`/main/bomCategory/pageByCategoryId`, { params });
+  if (res.data.code == 0) {
+    return res.data.data;
+  }
+  return Promise.reject(new Error(res.data.message));
+}
+
+
+
+
 // 转换
 export async function convert(data) {
   const res = await request.post(`/main/bomCategory/convert`, data);
@@ -167,6 +179,18 @@ export async function convert(data) {
   return Promise.reject(new Error(res.data.message));
 }
 
+// 转换 ABOM
+export async function convertABom(data) {
+  const res = await request.post(`/main/bomCategory/convertABom`, data);
+  if (res.data.code == 0) {
+    return res.data;
+  }
+  return Promise.reject(new Error(res.data.message));
+}
+
+
+
+
 // 文档
 export async function getBomFilePageList(params) {
   const res = await request.get(`/main/bomfile/page`, { params });

+ 40 - 0
src/api/material/inspectionClassify.js

@@ -0,0 +1,40 @@
+import request from '@/utils/request';
+
+
+
+
+// 列表 
+
+export async function getList (data) {
+  let par = new URLSearchParams(data);
+  const res = await request.get(`/qms/qualitylevel/page?` + par, {});
+  if (res.data.code == 0) {
+    return res.data.data;
+  }
+  return Promise.reject(new Error(res.data.message));
+}
+
+
+  
+
+  export async function getById(id) {
+    const res = await request.get(`/qms/qualitylevel/getById/${id}`);
+    if (res.data.code == 0) {
+      return res.data;
+    }
+    return Promise.reject(new Error(res.data.message));
+  }
+
+
+
+
+
+// 批量保存
+export async function saveBatch (data) {
+  const res = await request.post(`/qms/qualitylevel/saveBatch`, data);
+  if (res.data.code == 0) {
+    return res.data;
+  }
+  return Promise.reject(new Error(res.data.message));
+}
+

+ 38 - 1
src/api/system/file/index.js

@@ -16,7 +16,7 @@ export async function uploadFile (data) {
   return Promise.reject(new Error(res.data.message));
 }
 /**
- * 上传文件 批量
+ * 导入文件 批量
  * @param file 文件
  */
 export async function uploadBatch (data) {
@@ -83,3 +83,40 @@ export async function getFileList (data) {
   }
   return Promise.reject(new Error(res.data.message));
 }
+
+/**
+ * 导入文件 批量
+ * @param file 文件
+ */
+export async function importBatch (data) {
+  const formData = new FormData();
+  data.multiPartFiles.forEach((item, index) => {
+    formData.append(`multiPartFiles`, item);
+  });
+  const res = await request.post(
+    `/main/file/importBatch?module=${data.module}`,
+    formData
+  );
+  if (res.data.code === '0') {
+    return res.data;
+  }
+  return Promise.reject(new Error(res.data.message));
+}
+
+// 导入pbom
+export async function importPBom (data) {
+  const formData = new FormData();
+  data.multiPartFiles.forEach((item, index) => {
+    formData.append(`multiPartFiles`, item);
+  });
+  const res = await request.post(
+    `/main/bomCategory/importPBom`,
+    formData
+  );
+  if (res.data.code === '0') {
+    return res.data;
+  }
+  return Promise.reject(new Error(res.data.message));
+}
+
+

+ 120 - 0
src/components/upload/import-dialog.vue

@@ -0,0 +1,120 @@
+<template>
+  <!-- 上传 -->
+  <el-dialog title="导入文件上传" :visible.sync="dialogVisible" width="40%">
+    <el-form label-width="110px" class="zw-criterion">
+      <el-form-item label="选择文件">
+        <el-upload
+          class="avatar-uploader"
+          action="#"
+          :show-file-list="false"
+          :http-request="handlSuccess"
+          :before-upload="beforeUpload"
+        >
+          <el-button icon="el-icon-plus" size="small" type="primary"
+            >文件上传</el-button
+          >
+          <div slot="tip" class="el-upload__tip"
+            >只能上传excel文件,或批量上传打包成zip、rar压缩文件,单文件不超过10mb</div
+          >
+        </el-upload>
+      </el-form-item>
+      <el-form-item label="上传列表">
+        <div class="imgs-box">
+          <p v-for="(item, index) in attaments" :key="index" class="imgs-p">
+            <span> {{ item.name }}</span>
+            <el-link @click="delFileList(index)" type="primary">删除</el-link>
+          </p>
+        </div>
+      </el-form-item>
+    </el-form>
+    <div slot="footer" class="dialog-footer">
+      <el-button size="small" @click="dialogVisible = false">关 闭</el-button>
+      <el-button size="small" @click="upload" type="primary">上 传</el-button>
+    </div>
+  </el-dialog>
+</template>
+
+<script>
+  import { importBatch } from '@/api/system/file/index.js';
+
+  export default {
+    props: {
+      // eslint-disable-next-line vue/require-prop-type-constructor
+      defModule: ''
+    },
+    //注册组件
+    data() {
+      return {
+        showViewer: false, // 显示查看器
+        dialogVisible: false,
+        uploadShow: false,
+        module: '',
+        attaments: [], //上传文件
+        file: ''
+      };
+    },
+    created() {},
+    methods: {
+      open() {
+        this.attaments = [];
+        this.module = '';
+        this.dialogVisible = true;
+      },
+      //删除附件
+      delFileList(index) {
+        this.attaments.splice(index, 1);
+      },
+      //上传限制
+      beforeUpload(file) {
+        const isLt10M = file.size / 1024 / 1024 < 10;
+        if (!isLt10M) {
+          this.$message.error('导入单文件大小不能超过 10MB!');
+        }
+        return isLt10M;
+      },
+      //图片上传
+      handlSuccess(param) {
+        this.file = param.file;
+        this.attaments.push(param.file);
+      },
+      // 文件上传
+      async upload() {
+        if (this.attaments.length == 0) {
+          return this.$message.warning('文件不能为空!');
+        }
+        this.module = this.$props.defModule;
+
+        await importBatch({
+          module: this.module,
+          multiPartFiles: this.attaments
+        });
+        this.$message.success('操作成功!');
+        this.dialogVisible = false;
+        this.$emit('success');
+      }
+    }
+  };
+</script>
+
+<style lang="scss">
+  .zw-table-header {
+    float: right;
+  }
+
+  .imgs-box .imgs-p {
+    height: 30px;
+    background: #f0f3f3;
+    line-height: 30px;
+    width: 372px;
+    margin-bottom: 5px;
+    padding: 0 10px;
+    display: flex;
+    justify-content: space-between;
+  }
+  .zw-criterion-normal {
+    padding: 20px 0 0 0;
+  }
+  .el-main {
+    overflow: hidden;
+  }
+</style>

+ 4 - 1
src/enum/dict.js

@@ -46,8 +46,11 @@ export default {
   区域等级: 'main_area_level',
   区域类型: 'main_area_type',
   工种类型: 'work_type',
+  '客户/供应商资质类型': 'contact_qc_type',
   版本规则分类: 'version_rule_type',
-  '客户/供应商资质类型': 'contact_qc_type'
+  生产类型: 'productionType',
+  质检标准类型: 'quality_testing_code',
+  质检方式: 'quality_method_code'
 };
 
 export const numberList = [

+ 5 - 5
src/layout/components/header-tools.vue

@@ -21,12 +21,12 @@
     <div class="ele-admin-header-tool-item">
       <el-dropdown @command="onUserDropClick">
         <div class="ele-admin-header-avatar">
-<!--          <el-avatar-->
-<!--            :src="loginUser && loginUser.avatarA ? loginUser.avatar : ''"-->
-<!--          />-->
-          <span class="hidden-xs-only">{{
+          <el-avatar
+             src="@/assets/images/default-user.png"
+          />
+          <!-- <span class="hidden-xs-only">{{
             loginUser && loginUser.nickname ? loginUser.nickname : ''
-          }}</span>
+          }}</span> -->
           <i class="el-icon-arrow-down"></i>
         </div>
         <template v-slot:dropdown>

+ 117 - 0
src/views/classifyManage/treeClassify/components/upload-dialog.vue

@@ -0,0 +1,117 @@
+<template>
+  <!-- 上传 -->
+  <el-dialog title="导入文件上传" :visible.sync="dialogVisible" width="40%">
+    <el-form label-width="110px" class="zw-criterion">
+      <el-form-item label="选择文件">
+        <el-upload
+          class="avatar-uploader"
+          action="#"
+          :show-file-list="false"
+          :http-request="handlSuccess"
+          :before-upload="beforeUpload"
+        >
+          <el-button icon="el-icon-plus" size="small" type="primary"
+            >文件上传</el-button
+          >
+          <div slot="tip" class="el-upload__tip">只能上传excel文件,或批量上传打包成zip、rar压缩文件,单文件不超过10mb</div>
+        </el-upload>
+      </el-form-item>
+      <el-form-item label="上传列表">
+        <div class="imgs-box">
+          <p v-for="(item, index) in attaments" :key="index" class="imgs-p">
+            <span> {{ item.name }}</span>
+            <el-link @click="delFileList(index)" type="primary">删除</el-link>
+          </p>
+        </div>
+      </el-form-item>
+    </el-form>
+    <div slot="footer" class="dialog-footer">
+      <el-button size="small" @click="dialogVisible = false">关 闭</el-button>
+      <el-button size="small" @click="upload" type="primary">上 传</el-button>
+    </div>
+  </el-dialog>
+</template>
+
+<script>
+import {importBatch, uploadBatch} from '@/api/system/file/index.js';
+
+  export default {
+    props: {
+      defModule: ''
+    },
+    //注册组件
+    data () {
+      return {
+        showViewer: false, // 显示查看器
+        dialogVisible: false,
+        uploadShow: false,
+        module: '',
+        attaments: [], //上传文件
+        file: ''
+      };
+    },
+    created () {},
+    methods: {
+      open () {
+        this.attaments = [];
+        this.module = '';
+        this.dialogVisible = true;
+      },
+      //删除附件
+      delFileList (index) {
+        this.attaments.splice(index, 1);
+      },
+      //上传限制
+      beforeUpload (file) {
+        const isLt10M = file.size / 1024 / 1024 < 10;
+        if (!isLt10M) {
+          this.$message.error('上传文件大小不能超过 10MB!');
+        }
+        return isLt10M;
+      },
+      //图片上传
+      handlSuccess (param) {
+        this.file = param.file;
+        this.attaments.push(param.file);
+      },
+      // 文件上传
+      async upload () {
+        if (this.attaments.length == 0) {
+          return this.$message.warning('文件不能为空!');
+        }
+        this.module = this.$props.defModule;
+
+        await importBatch({
+          module: this.module,
+          multiPartFiles: this.attaments
+        });
+        this.$message.success('操作成功!');
+        this.dialogVisible = false;
+        this.$emit('success');
+      }
+    }
+  };
+</script>
+
+<style lang="scss">
+  .zw-table-header {
+    float: right;
+  }
+
+  .imgs-box .imgs-p {
+    height: 30px;
+    background: #f0f3f3;
+    line-height: 30px;
+    width: 372px;
+    margin-bottom: 5px;
+    padding: 0 10px;
+    display: flex;
+    justify-content: space-between;
+  }
+  .zw-criterion-normal {
+    padding: 20px 0 0 0;
+  }
+  .el-main {
+    overflow: hidden;
+  }
+</style>

+ 19 - 4
src/views/classifyManage/treeClassify/index.vue

@@ -14,7 +14,15 @@
           >
             新建
           </el-button>
-        </template> 
+          <!--<el-button
+            size="small"
+            icon="el-icon-upload"
+            class="ele-btn-icon"
+            @click="uploadFile()"
+          >
+            导入
+          </el-button>-->
+        </template>
         <!-- 操作列 -->
         <template v-slot:action="{ row }">
 
@@ -30,7 +38,7 @@
           <el-link
             type="primary"
             :underline="false"
-           
+
             @click="junmpEdit(row)"
           >
            下级分类
@@ -51,17 +59,21 @@
     </el-card>
 
     <list-edit ref="editRef" @done="reload" />
+    <importDialog :defModule="moudleName" ref="importDialogRef" @success="reload" />
   </div>
 </template>
 <script>
   import ListEdit from './components/list-edit.vue';
   import ClassifyManageSearch from './components/classifyManageSearch.vue';
+  import importDialog from "@/components/upload/import-dialog.vue";
+
   import { getSubPage, deleteCategory } from '@/api/classifyManage';
   export default {
-    components: { ClassifyManageSearch, ListEdit },
+    components: { ClassifyManageSearch, ListEdit, importDialog},
     data () {
       return {
         editData: null,
+        moudleName : "mainCategoryLevel",
         columns: [
           {
             prop: 'code',
@@ -135,7 +147,10 @@
             id
           }
         });
-      }
+      },
+      uploadFile () {
+        this.$refs.importDialogRef.open();
+      },
     }
   };
 </script>

+ 11 - 1
src/views/enterpriseModel/dept/index.vue

@@ -30,6 +30,7 @@
           <el-button class="ele-btn-icon" size="small" @click="foldAll">
             折叠全部
           </el-button>
+          <el-button type="primary" size="mini" icon="el-icon-upload2" plain @click="uploadFile">导入</el-button>
         </template>
         <!-- 标题列 -->
         <template v-slot:name="{ row }">
@@ -103,12 +104,16 @@
       :organization-list="data"
       @done="reload"
     />
+
+    <importDialog :defModule="moudleName" ref="importDialogRef" @success="reload" />
   </div>
 </template>
 
 <script>
 
 import OrgEdit from './components/org-edit.vue';
+import importDialog from "@/components/upload/import-dialog.vue";
+
 import {
   listOrganizations,
   removeOrganization
@@ -116,9 +121,11 @@ import {
 
 export default {
   name: 'SystemOrganization',
-  components: {OrgEdit},
+  components: {OrgEdit, importDialog},
   data() {
     return {
+      //模块名称
+      moudleName : "mainGroup",
       // 加载状态
       loading: false,
       // 列表数据
@@ -263,6 +270,9 @@ export default {
         })
         .catch(() => {
         });
+    },
+    uploadFile () {
+      this.$refs.importDialogRef.open();
     }
   }
 };

+ 31 - 9
src/views/factoryModel/station/components/edit.vue

@@ -135,7 +135,7 @@
               <el-select
                 v-model="form.extInfo.workshopPlanId"
                 placeholder="请选择"
-                @change="getListWorkshopByParentId"
+                @change="getListWorkshopByParentId(false)"
                 style="width: 100%"
               >
                 <el-option
@@ -371,9 +371,8 @@
     },
 
     props: {
-      options_groupId: {}
+      options_groupId: Array
     },
-
     watch: {
       options_groupId(nval) {
         this.toTreeData(nval);
@@ -386,6 +385,7 @@
           enabled: 1,
           extInfo: {
             factoryId: '', // 工厂
+            workshopPlanId: '', // 厂房
             workshopId: '', // 车间
             principalDep: '', // 负责人部门
             meterTimeUnit: '时', // 节拍时间单位
@@ -428,6 +428,9 @@
           'extInfo.factoryId': [
             { required: true, message: '请输入', trigger: 'change' }
           ],
+          'extInfo.workshopPlanId': [
+            { required: true, message: '请输入', trigger: 'change' }
+          ],
           'extInfo.principalDep': [
             { required: true, message: '请输入', trigger: 'change' }
           ],
@@ -523,7 +526,7 @@
     created() {
       this.getGs();
       this.getFactoryList();
-      // this.getBasicAreaList()
+      this.getBasicAreaList();
     },
     methods: {
       chooseAsset() {
@@ -574,9 +577,14 @@
             }
           }
           this.getData(row.id);
+
           // 请求下拉数据
+          if (this.form.extInfo.factoryId) {
+            this.getlistCf();
+          }
+
           if (this.form.extInfo.workshopPlanId) {
-            this.getListWorkshopByParentId();
+            this.getListWorkshopByParentId(true);
           }
           if (this.form.extInfo.workshopId) {
             this.getlistFactoryLineByParentId();
@@ -665,7 +673,7 @@
       // 格式化公司数据
       toTreeData(val) {
         this.options.principalDep = this.$util.toTreeData({
-          data: val,
+          data: JSON.parse(JSON.stringify(val)),
           idField: 'id',
           parentIdField: 'parentId'
         });
@@ -686,7 +694,15 @@
       },
 
       // 获取车间
-      getListWorkshopByParentId() {
+      getListWorkshopByParentId(bol) {
+        if (!bol) {
+          this.form.extInfo.workshopId = '';
+
+          this.options.workshopId = [];
+
+          this.form.productionLineId = '';
+          this.options.productionLineId = [];
+        }
         listWorkshopByParentId(this.form.extInfo.workshopPlanId).then((res) => {
           this.options.workshopId = res;
         });
@@ -712,10 +728,16 @@
       },
       // 选择工厂
       change_factoryId() {
+        this.form.extInfo.workshopPlanId = '';
+        this.workshopPlanList = [];
+
         this.form.extInfo.workshopId = '';
-        this.form.leaderId = '';
+
         this.options.workshopId = [];
-        this.options.leaderId = [];
+
+        this.form.productionLineId = '';
+        this.options.productionLineId = [];
+
         this.getlistCf();
       },
       getlistCf() {

+ 1 - 3
src/views/factoryModel/station/index.vue

@@ -65,7 +65,6 @@
     <edit
       ref="edit"
       @done="done"
-      :options_groupId="dict.groupId"
 
     ></edit>
   </div>
@@ -185,8 +184,7 @@
       // 获取公司数据
       getGs () {
         listOrganizations().then((list) => {
-          console.log(list);
-          this.dict.groupId = list;
+          this.dict.groupId = JSON.parse(JSON.stringify(list));
         });
       },
       // 回显车间

+ 1 - 1
src/views/factoryModel/workshop/index.vue

@@ -170,7 +170,7 @@
         let par = {
           type: 1,
           size: 9999,
-          type: 2,
+
         };
         getFactoryarea(par).then((res) => {
           this.dict.factory = res.list;

+ 124 - 0
src/views/material/BOMmanage/components/BOM-search.vue

@@ -0,0 +1,124 @@
+<!-- 搜索表单 -->
+<template>
+  <el-form
+    label-width="77px"
+    class="ele-form-search"
+    @keyup.enter.native="search"
+    @submit.native.prevent
+  >
+    <el-row :gutter="10">
+      <el-col v-bind="styleResponsive ? { md: 6 } : { span: 6 }">
+        <el-form-item label="BOM编码">
+          <el-input clearable v-model.trim="where.code" placeholder="请输入" />
+        </el-form-item>
+      </el-col>
+      <el-col v-bind="styleResponsive ? { md: 6 } : { span: 6 }">
+        <el-form-item label="BOM名称">
+          <el-input clearable v-model.trim="where.name" placeholder="请输入" />
+        </el-form-item>
+      </el-col>
+      <el-col v-bind="styleResponsive ? { md: 6 } : { span: 6 }">
+        <el-form-item label="产品编码">
+          <el-input
+            clearable
+            v-model.trim="where.categoryCode"
+            placeholder="请输入"
+          />
+        </el-form-item>
+      </el-col>
+      <el-col v-bind="styleResponsive ? { md: 6 } : { span: 6 }">
+        <el-form-item label="产品名称">
+          <el-input
+            clearable
+            v-model.trim="where.categoryName"
+            placeholder="请输入"
+          />
+        </el-form-item>
+      </el-col>
+      <el-col v-bind="styleResponsive ? { md: 6 } : { span: 6 }">
+        <el-form-item label="状态">
+          <el-select
+            clearable
+            v-model.trim="where.status"
+            placeholder="请选择"
+            class="w100"
+          >
+            <el-option
+              v-for="item in Object.entries(statusOpt)"
+              :key="item[0]"
+              :label="item[1]"
+              :value="item[0]"
+            ></el-option>
+          </el-select>
+        </el-form-item>
+      </el-col>
+      <el-col v-bind="styleResponsive ? { lg: 6, 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 ? { md: 12 } : { span: 12 }">
+        <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" icon="el-icon-refresh" class="ele-btn-icon"
+            >重置</el-button
+          >
+        </div>
+      </el-col>
+    </el-row>
+  </el-form>
+</template>
+
+<script>
+  export default {
+    props: {
+      statusOpt: Object,
+      categoryCode: String
+    },
+    data() {
+      // 默认表单数据
+      const defaultWhere = {
+        name: '',
+        code: '',
+        categoryCode: this.categoryCode,
+        categoryName: '',
+        status: '',
+
+      };
+      return {
+        defaultWhere,
+        // 表单数据
+        where: { ...defaultWhere }
+      };
+    },
+    computed: {
+      // 是否开启响应式布局
+      styleResponsive() {
+        return this.$store.state.theme.styleResponsive;
+      }
+    },
+    methods: {
+      /* 搜索 */
+      search() {
+        this.$emit('search', this.where);
+      },
+      /*  重置 */
+      reset() {
+        this.where = { ...this.defaultWhere };
+        this.search();
+      }
+    }
+  };
+</script>

+ 12 - 24
src/views/material/BOMmanage/components/StepModal1.vue

@@ -97,6 +97,17 @@
         title: '工步选择',
         // 表格列配置
         columns: [
+          {
+            columnKey: 'selection',
+            type: 'selection',
+            width: 45,
+            align: 'center',
+            selectable: (row, index) => {
+              return !this.tableData.some((it) => it.stepId == row.id);
+            },
+            reserveSelection: true,
+            fixed: 'left'
+          },
           {
             label: '序号',
             type: 'index',
@@ -195,30 +206,7 @@
         if (current) {
           this.current = current;
         }
-        if (type === '修改') {
-          this.columns = [
-            {
-              action: 'action',
-              slot: 'action',
-              align: 'center',
-              label: '选择'
-            }
-          ].concat(this.columns);
-        } else {
-          this.columns = [
-            {
-              columnKey: 'selection',
-              type: 'selection',
-              width: 45,
-              align: 'center',
-              selectable: (row, index) => {
-                return !this.tableData.some((it) => it.stepId == row.id);
-              },
-              reserveSelection: true,
-              fixed: 'left'
-            }
-          ].concat(this.columns);
-        }
+
         this.visible = true;
       },
 

+ 163 - 71
src/views/material/BOMmanage/components/attribute.vue

@@ -2,68 +2,132 @@
   <div>
     <el-form label-width="100px" ref="form" :model="attributeData">
       <el-row>
-        <el-col :span="16" label-width="100px">
-          <el-form-item label="类型" prop="type">
-            <el-select
-              style="width: 100%"
-              :disabled="true"
-              v-model="attributeData.bomType"
-              placeholder="请选择"
-            >
-              <el-option
-                v-for="item in bomTypeOptions"
-                :label="item.label"
-                :value="item.value"
-                :key="item.value"
-              >
-              </el-option>
-            </el-select>
+        <el-col :span="8" label-width="100px">
+          <el-form-item label="名称:" prop="category.name">
+            <el-input
+              placeholder=""
+              v-model="category.name"
+              disabled
+            ></el-input>
           </el-form-item>
         </el-col>
-      </el-row>
 
-      <el-row>
-        <el-col :span="16" label-width="100px">
-          <el-form-item label="编码" prop="code">
-            <el-input placeholder="" v-model="attributeData.code"></el-input>
+        <el-col :span="8" label-width="100px">
+          <el-form-item label="编码:" prop="code">
+            <el-input
+              placeholder=""
+              v-model="category.code"
+              disabled
+            ></el-input>
           </el-form-item>
         </el-col>
-      </el-row>
 
-      <el-row>
-        <el-col :span="16" label-width="100px">
-          <el-form-item label="图号" prop="code">
-            <el-input placeholder="" v-model="attributeData.imgCode"></el-input>
+        <el-col :span="8" label-width="100px">
+          <el-form-item label="牌号:" prop="brandNum">
+            <el-input
+              placeholder=""
+              v-model="category.brandNum"
+              disabled
+            ></el-input>
           </el-form-item>
         </el-col>
-      </el-row>
 
-      <el-row>
-        <el-col :span="16" label-width="100px">
-          <el-form-item label="名称" prop="name">
-            <el-input placeholder="" v-model="attributeData.name"></el-input>
+        <el-col :span="8" label-width="100px">
+          <el-form-item label="型号:" prop="modelType">
+            <el-input
+              placeholder=""
+              v-model="category.modelType"
+              disabled
+            ></el-input>
           </el-form-item>
         </el-col>
-      </el-row>
 
-      <el-row>
         <el-col :span="8" label-width="100px">
-          <el-form-item label="型号" prop="name">
+          <el-form-item label="规格:" prop="specification">
             <el-input
               placeholder=""
-              v-model="attributeData.modeType"
+              v-model="category.specification"
+              disabled
             ></el-input>
           </el-form-item>
         </el-col>
 
         <el-col :span="8" label-width="100px">
-          <el-form-item label="规格" prop="name">
+          <el-form-item label="计量单位:" prop="measuringUnit">
             <el-input
               placeholder=""
-              v-model="attributeData.specification"
+              v-model="category.measuringUnit"
+              disabled
             ></el-input>
           </el-form-item>
         </el-col>
+
+        <el-col :span="8" label-width="100px">
+          <el-form-item label="重量单位:" prop="weightUnit">
+            <el-input
+              placeholder=""
+              v-model="category.weightUnit"
+              disabled
+            ></el-input>
+          </el-form-item>
+        </el-col>
+
+        <el-col :span="8" label-width="100px">
+          <el-form-item label="包装单位:" prop="packingUnit">
+            <el-input
+              placeholder=""
+              v-model="category.packingUnit"
+              disabled
+            ></el-input>
+          </el-form-item>
+        </el-col>
+
+        <el-col :span="8" label-width="100px">
+          <el-form-item label="毛重:" prop="roughWeight">
+            <el-input
+              placeholder=""
+              v-model="category.roughWeight"
+              disabled
+            ></el-input>
+          </el-form-item>
+        </el-col>
+
+        <el-col :span="8" label-width="100px">
+          <el-form-item label="净重:" prop="netWeight">
+            <el-input
+              placeholder=""
+              v-model="category.netWeight"
+              disabled
+            ></el-input>
+          </el-form-item>
+        </el-col>
+
+        <el-col :span="8" label-width="100px">
+          <el-form-item
+            label="加工类型:"
+            prop="isConsumable"
+            v-if="[1, 23, 9, 28].includes(Number(category.categoryLevelPathId))"
+          >
+            <el-input
+              placeholder=""
+              :v-model="category.isConsumable == 1 ? '批量' : '单件'"
+              disabled
+            ></el-input>
+          </el-form-item>
+        </el-col>
+
+        <el-col :span="8" label-width="100px">
+          <el-form-item label="生产类型:" prop="produceType">
+            <el-select v-model="category.produceType" filterable multiple>
+                <el-option
+                  v-for="item in dictList"
+                  :key="item.value"
+                  :value="item.value"
+                  :label="item.label"
+                ></el-option>
+              </el-select>
+          </el-form-item>
+        </el-col>
       </el-row>
 
       <el-row>
@@ -77,10 +141,10 @@
         </el-col>
 
         <el-col :span="8" label-width="100px">
-          <el-form-item label="物料编码" prop="name">
+          <el-form-item label="bom路线" prop="name">
             <el-input
               placeholder=""
-              v-model="attributeData.materialsCode"
+              v-model="attributeData.bomTypeRouting"
             ></el-input>
           </el-form-item>
         </el-col>
@@ -110,26 +174,6 @@
           </el-form-item>
         </el-col>
 
-        <el-col :span="8" label-width="100px">
-          <el-form-item label="状态" prop="name">
-            <el-select
-              style="width: 100%"
-              v-model="attributeData.status"
-              placeholder="请选择"
-            >
-              <el-option
-                v-for="item in statusOptions"
-                :label="item.label"
-                :value="item.value"
-                :key="item.value"
-              >
-              </el-option>
-            </el-select>
-          </el-form-item>
-        </el-col>
-      </el-row>
-
-      <el-row>
         <el-col :span="8" label-width="100px">
           <el-form-item label="物料库路径" prop="name">
             <el-input
@@ -139,16 +183,10 @@
           </el-form-item>
         </el-col>
 
-        <el-col :span="8" label-width="100px">
-          <el-form-item label="版本" prop="name">
-            <el-input
-              placeholder=""
-              v-model="attributeData.versions"
-            ></el-input>
-          </el-form-item>
-        </el-col>
       </el-row>
 
+
+
       <el-row>
         <el-col :span="20" label-width="100px">
           <el-form-item label="备注" prop="name">
@@ -183,15 +221,24 @@
           </el-form-item>
         </el-col>
       </el-row>
+
+      <div class="btn_box">
+        <el-button type="primary">修改</el-button>
+      </div>
     </el-form>
   </div>
 </template>
 
 <script>
+  import { getByCode } from '@/api/system/dictionary-data';
   export default {
+    components: {},
     data() {
       return {
         form: {},
+        category: {
+          name: ''
+        },
         statusOptions: [
           {
             label: '默认',
@@ -205,22 +252,67 @@
         bomTypeOptions: [
           {
             label: 'PBOM',
-            value: 1
+            value: '1'
           },
           {
             label: 'MBOM',
-            value: 2
+            value: '2'
+          },
+          {
+            label: 'ABOM',
+            value: '3'
           }
-        ]
+        ],
+        dictList: [],
       };
     },
+
+    created() {
+      this.getDictList('productionType');
+    },
+
+    beforeDestroy() {},
+    methods: {
+      async getDictList(code) {
+      
+        let { data: res } = await getByCode(code);
+        this.dictList = res.map((item) => {
+          let values = Object.keys(item);
+          return {
+            value: Number(values[0]),
+            label: item[values[0]]
+          };
+        });
+     
+      },
+    },
     props: {
       attributeData: {
         type: Object,
         default: {}
       }
+    },
+
+    watch: {
+      attributeData(val) {
+        console.log(val);
+        console.log(Object.prototype.hasOwnProperty.call(val, 'category'));
+        if (Object.prototype.hasOwnProperty.call(val, 'category')) {
+          this.category = val.category;
+          this.category.produceType  = val.produceType
+          
+
+          this.$forceUpdate();
+        }
+      }
     }
   };
 </script>
 
-<style lang="scss" scoped></style>
+<style lang="scss" scoped>
+  .btn_box {
+    display: flex;
+    align-items: center;
+    justify-content: center;
+  }
+</style>

+ 19 - 13
src/views/material/BOMmanage/components/baseInfo.vue

@@ -1,6 +1,18 @@
 <template>
   <div class="baseInfo">
+  
+
     <el-form label-width="100px" ref="form" :model="dataInfo">
+     
+      
+      <el-col :span="6" label-width="100px">
+      <el-form-item label="类型" prop="type">
+
+        {{ dataInfo.bomType == 1 ? "PBOM" :  dataInfo.bomType == 2 ? 'MBOM' :   dataInfo.bomType == 3 ? 'ABOM'  : ''}}
+          </el-form-item>
+          </el-col>
+
+
       <el-row>
         <el-col :span="6" label-width="100px">
           <el-form-item label="BOM编码" prop="type">
@@ -47,19 +59,13 @@
             </el-select>
           </el-form-item>
         </el-col>
-      </el-row>
 
-      <el-row>
-        <el-col :span="6" label-width="100px">
-          <el-form-item label="所属工厂" prop="code">
-            <el-input
-              disabled
-              placeholder="所属工厂"
-              v-model="dataInfo.code"
-            ></el-input>
-          </el-form-item>
-        </el-col>
+
+   
+
       </el-row>
+
+    
     </el-form>
   </div>
 </template>
@@ -93,9 +99,9 @@
 
 <style lang="scss" scoped>
   .baseInfo {
-    padding: 10px 10px 0 10px;
+    padding: 6px;
     box-sizing: border-box;
     border: 1px solid #f1f2f2;
-    margin-bottom: 20px;
+    margin-bottom: 10px;
   }
 </style>

+ 86 - 48
src/views/material/BOMmanage/components/bomTreeDialog.vue

@@ -8,10 +8,15 @@
     append-to-body
     width="70%"
   >
-    <el-form label-width="100px" ref="form" :model="attributeData">
+    <el-form
+      label-width="100px"
+      ref="form"
+      :rules="rules"
+      :model="attributeData"
+    >
       <el-row>
         <el-col :span="12" label-width="100px">
-          <el-form-item label="父级节点" prop="type">
+          <el-form-item label="父级节点" prop="parentId">
             <selectTree
               ref="tree"
               class="form-ipt"
@@ -22,7 +27,7 @@
               :options="bomTreeList"
               @getValue="getTreeValue"
               :props="{
-                value: 'bomId',
+                value: 'id',
                 label: 'name',
                 children: 'children'
               }"
@@ -53,36 +58,17 @@
 
         <el-col :span="12" label-width="100px">
           <el-form-item label="编码" prop="code">
-            <el-input placeholder="" v-model="attributeData.code"></el-input>
-          </el-form-item>
-        </el-col>
-
-        <el-col :span="12" label-width="100px">
-          <el-form-item label="图号" prop="imgCode">
-            <el-input placeholder="" v-model="attributeData.imgCode"></el-input>
-          </el-form-item>
-        </el-col>
-
-        <el-col :span="12" label-width="100px">
-          <el-form-item label="名称" prop="name">
-            <el-input placeholder="" v-model="attributeData.name"></el-input>
-          </el-form-item>
-        </el-col>
-        <el-col :span="12" label-width="100px">
-          <el-form-item label="型号" prop="modeType">
             <el-input
               placeholder=""
-              v-model="attributeData.modeType"
+              @click.native="handleProduct()"
+              v-model="attributeData.code"
             ></el-input>
           </el-form-item>
         </el-col>
 
         <el-col :span="12" label-width="100px">
-          <el-form-item label="规格" prop="specification">
-            <el-input
-              placeholder=""
-              v-model="attributeData.specification"
-            ></el-input>
+          <el-form-item label="名称" prop="name">
+            <el-input placeholder="" v-model="attributeData.name"></el-input>
           </el-form-item>
         </el-col>
 
@@ -96,19 +82,19 @@
         </el-col>
 
         <el-col :span="12" label-width="100px">
-          <el-form-item label="物料编码" prop="materialsCode">
+          <el-form-item label="来源" prop="sourceData">
             <el-input
               placeholder=""
-              v-model="attributeData.materialsCode"
+              v-model="attributeData.sourceData"
             ></el-input>
           </el-form-item>
         </el-col>
 
         <el-col :span="12" label-width="100px">
-          <el-form-item label="来源" prop="sourceData">
+          <el-form-item label="bom路线" prop="bomTypeRouting">
             <el-input
               placeholder=""
-              v-model="attributeData.sourceData"
+              v-model="attributeData.bomTypeRouting"
             ></el-input>
           </el-form-item>
         </el-col>
@@ -157,7 +143,6 @@
         <el-col :span="12" label-width="100px">
           <el-form-item label="版本" prop="versions">
             <el-input
-              :disabled="versions"
               placeholder=""
               @input="versionsChange"
               v-model="attributeData.versions"
@@ -181,18 +166,25 @@
       <el-button type="primary" size="small" @click="save">保存</el-button>
       <el-button size="small" @click="handleClose">关闭</el-button>
     </div>
+
+    <standardOutput
+      ref="standardOutputRefs"
+      @selection="chooseStandardList"
+    ></standardOutput>
   </el-dialog>
 </template>
 
 <script>
   import { getBomTreeList, saveBomTreeList } from '@/api/material/BOM.js';
   import selectTree from '@/components/selectTree';
-  import producetask from '@/api/technology/production';
+
   import userSearch from './user-search.vue';
+  import standardOutput from './standardOutput.vue';
   export default {
     components: {
       userSearch,
-      selectTree
+      selectTree,
+      standardOutput
     },
     data() {
       return {
@@ -202,6 +194,16 @@
         attributeData: {
           versions: ''
         },
+
+        category: {
+          name: ''
+        },
+
+        rules: {
+          code: [{ required: true, message: '请选择编码', trigger: 'change' }],
+
+          name: [{ required: true, message: '请选择名称', trigger: 'change' }]
+        },
         bomTreeList: [],
         statusOptions: [
           {
@@ -216,44 +218,78 @@
         bomTypeOptions: [
           {
             label: 'PBOM',
-            value: 1
+            value: '1'
           },
           {
             label: 'MBOM',
-            value: 2
-          }
+            value: '2'
+          },
+          {
+            label: 'ABOM',
+            value: '3'
+          },
+       
         ]
       };
     },
 
     methods: {
       getTreeValue(data) {
-        this.attributeData.parentId = data.id;
-        this.attributeData.level = +data.level + 1;
+        this.category = {};
+        this.$set(this.attributeData, 'code', null);
+        this.$set(this.attributeData, 'name', null);
+        if (data) {
+          this.attributeData.parentId = data.id;
+          this.attributeData.level = +data.level + 1;
+        } else {
+          this.attributeData.parentId = null;
+          this.attributeData.level = null;
+        }
       },
       save() {
-        if (!this.attributeData.parentId) {
-          this.attributeData.parentId = 0;
-          this.attributeData.level = 1;
-        }
-        saveBomTreeList(this.attributeData).then((res) => {
-          if (res.code == '0') {
-            this.$message.success('保存成功');
-            this.$emit('reload', this.attributeData.versions);
-            this.handleClose();
+        this.$refs.form.validate((valid) => {
+          if (!valid) {
+            return false;
           }
+          if (!this.attributeData.parentId) {
+            this.attributeData.parentId = 0;
+            this.attributeData.level = 1;
+          }
+          this.attributeData.category = this.category;
+          saveBomTreeList(this.attributeData).then((res) => {
+            if (res.code == '0') {
+              this.$message.success('保存成功');
+              this.$emit('reload', this.attributeData.versions);
+              this.handleClose();
+            }
+          });
         });
       },
       versionsChange(versions) {
         this.attributeData.versions = versions;
         this.$forceUpdate();
       },
-      async open(type, versions, categoryId) {
+
+      handleProduct() {
+        this.$refs.standardOutputRefs.open(this.attributeData.parentId ? 1 : 9);
+      },
+      chooseStandardList(type, data) {
+        if (type == 9 || type == 1) {
+          this.category = data[0];
+          this.$set(this.attributeData, 'code', data[0].code);
+          this.$set(this.attributeData, 'name', data[0].name);
+          this.$forceUpdate();
+        }
+      },
+
+      async open(type, versions, categoryId, treeId) {
         this.attributeData = {};
         this.attributeData.bomType = type;
         this.attributeData.categoryId = categoryId;
         this.attributeData.versions = versions;
         this.versions = versions;
+
+        console.log(treeId);
         const res = await getBomTreeList({
           categoryId,
           versions,
@@ -261,6 +297,8 @@
         });
         console.log(this.attributeData);
         this.bomTreeList = res.data;
+        this.attributeData.parentId = treeId;
+        this.$forceUpdate();
         this.visible = true;
       },
       handleClose() {

+ 197 - 0
src/views/material/BOMmanage/components/detailedList.vue

@@ -0,0 +1,197 @@
+<template>
+    <div class="ele-body">
+      <el-card shadow="never">
+        <BOMSearch
+          @search="reload"
+          :statusOpt="statusOpt"
+          :categoryCode="where.categoryCode"
+        />
+        <ele-pro-table
+            ref="table"
+            :columns="columns"
+            :datasource="datasource"
+            :initLoad="false"
+            class="dict-table"
+            tool-class="ele-toolbar-actions"
+          >
+            <!-- 表头工具栏 -->
+            <template v-slot:action="{ row }">
+              <el-switch
+                :active-value="'1'"
+                :inactive-value="'0'"
+                @change="openBom(row, $event)"
+                v-model="row.status"
+              >
+              </el-switch>
+            </template>
+          </ele-pro-table>
+      </el-card>
+    </div>
+  </template>
+  
+  <script>
+    import BOMSearch from './BOM-search.vue';
+    import {  getBomPageCategoryId, startAndStop } from '@/api/material/BOM';
+  
+    export default {
+      name: 'SystemDictionary',
+      components: { BOMSearch },
+      data() {
+        return {
+          // 表格列配置
+          columns: [
+            {
+              label: '序号',
+              columnKey: 'index',
+              type: 'index',
+              width: 55,
+              align: 'center',
+              showOverflowTooltip: true
+            },
+            {
+              prop: 'code',
+              label: 'BOM编码',
+              showOverflowTooltip: true
+            },
+            {
+              prop: 'name',
+              label: 'BOM名称',
+              showOverflowTooltip: true
+            },
+            {
+              prop: 'categoryCode',
+              label: '产品编码',
+              showOverflowTooltip: true
+            },
+            {
+              prop: 'categoryName',
+              label: '产品名称',
+              showOverflowTooltip: true
+            },
+            {
+              prop: 'versions',
+              label: '版本'
+            },
+            {
+              prop: 'status ',
+              label: '状态',
+              formatter: (row) => {
+                return this.statusOpt[+row.status];
+              }
+            },
+            {
+              prop: 'createName',
+              label: '创建人',
+              showOverflowTooltip: true
+            },
+            {
+              prop: 'createTime',
+              label: '创建日期',
+              showOverflowTooltip: true
+            },
+            {
+              action: 'action',
+              slot: 'action',
+              label: '操作'
+            }
+          ],
+          statusOpt: {
+            '': '全部',
+            0: '已停用',
+            1: '已发布'
+          },
+          loading: false,
+          loadingInstance: null,
+          where: {},
+  
+          attrObj: {}
+
+        };
+      },
+      mounted() {
+     
+      },
+      props: {
+      attributeData: {
+        type: Object,
+        default: {}
+      }
+    },
+
+    watch: {
+      attributeData(val) {
+    this.attrObj = val
+
+    this.$nextTick(() => {
+          this.$refs.table.reload({
+            pageNum: 1,
+          });
+        });
+      }  
+    },
+  
+      methods: {
+
+        /* 启用关闭BOM */
+        openBom(row, boolean) {
+          this.loadingInstance = this.$loading({
+            lock: true,
+            text: boolean ? '启用中...' : '关闭中...',
+            background: 'rgba(0, 0, 0, 0.7)'
+          });
+          startAndStop({ id: row.id, status: row.status }).then(() => {
+            this.$message.success('操作成功');
+            this.loadingInstance.close();
+          });
+          setTimeout(() => {}, 2000);
+        },
+        /* 表格数据源 */
+        datasource({ where, page, limit }) {
+            if(!this.attrObj.id) {
+                return false
+            }
+          return getBomPageCategoryId({
+            ...where,
+            pageNum: page,
+            size: limit,
+            id: this.attrObj.id,
+            bomType: this.attrObj.bomType,
+          });
+        },
+   
+        /* 刷新表格 */
+        reload(where) {
+          this.$refs.table.reload({ where });
+        },
+
+  
+  
+  
+      }
+    };
+  </script>
+  
+  <style lang="scss" scoped>
+    .ele-body {
+      height: 100%;
+      ::v-deep .el-card {
+        height: 100%;
+        .el-card__body {
+          height: 100%;
+          display: flex;
+          flex-direction: column;
+          .dict-table {
+            flex: 1;
+            overflow: hidden;
+            display: flex;
+            flex-direction: column;
+            .el-table {
+              flex: 1;
+              overflow-y: auto;
+            }
+          }
+        }
+      }
+    }
+  </style>
+  

+ 13 - 1
src/views/material/BOMmanage/components/processModal.vue

@@ -147,7 +147,19 @@
       },
       open(item, selectWorkingProcess, type, currentRow) {
         this.type = type;
-        this.selectWorkingProcess = selectWorkingProcess;
+        if (
+          Object.prototype.hasOwnProperty.call(
+            selectWorkingProcess,
+            'taskParam'
+          )
+        ) {
+          this.selectWorkingProcess = selectWorkingProcess;
+        } else {
+          this.selectWorkingProcess = {
+            taskParam: []
+          };
+        }
+
         this.currentRow = currentRow;
         this.processData = item;
         this.initColumns();

+ 25 - 4
src/views/material/BOMmanage/components/routing.vue

@@ -30,7 +30,7 @@
         </template>
 
         <template v-slot:action="{ row, $index }">
-          <el-link type="primary" @click="handleDel(row, $index)">删除</el-link>
+          <el-link type="danger" @click="handleDel(row)">删除</el-link>
         </template>
       </ele-pro-table>
     </el-card>
@@ -41,6 +41,8 @@
 <script>
   import { getMbomPage } from '@/api/material/BOM';
   import routingDialog from './routingDialog.vue';
+
+  import { workingProcedureUpdate } from '@/api/material/BOM';
   export default {
     name: 'technologyRoute',
     components: {
@@ -102,6 +104,12 @@
             label: '类型',
             align: 'center',
             showOverflowTooltip: true
+          },
+          {
+            prop: 'action',
+            label: '操作',
+            align: 'center',
+            slot: 'action'
           }
         ],
 
@@ -145,9 +153,22 @@
         }
       },
 
-
-      handleDel(row, index) {
-        
+      handleDel(row) {
+        console.log(row, this.tableData);
+        workingProcedureUpdate({
+          id: this.tableData.id,
+          categoryId: this.taskParam.categoryId,
+          bomCategoryId: this.taskParam.id,
+          categoryCode: this.taskParam.categoryCode,
+          processRoute: {
+            list: this.tableData.processRoute.list.filter(
+              (item) => item.id !== row.id
+            )
+          }
+        }).then((data) => {
+          this.$message.success('删除成功');
+          this.reload();
+        });
       },
       checkStatus(row) {
         let obj = this.statusList.find((it) => it.value == row.status);

+ 21 - 14
src/views/material/BOMmanage/components/routingDialog.vue

@@ -21,12 +21,20 @@
           <el-row>
             <el-col v-bind="styleResponsive ? { lg: 5, md: 12 } : { span: 5 }">
               <el-form-item label="工艺路线组编码:">
-                <el-input clearable v-model.trim="where.code" placeholder="请输入" />
+                <el-input
+                  clearable
+                  v-model.trim="where.code"
+                  placeholder="请输入"
+                />
               </el-form-item>
             </el-col>
             <el-col v-bind="styleResponsive ? { lg: 5, md: 12 } : { span: 5 }">
               <el-form-item label="工艺路线名称:">
-                <el-input clearable v-model.trim="where.name" placeholder="请输入" />
+                <el-input
+                  clearable
+                  v-model.trim="where.name"
+                  placeholder="请输入"
+                />
               </el-form-item>
             </el-col>
             <el-col v-bind="styleResponsive ? { lg: 5, md: 12 } : { span: 5 }">
@@ -88,17 +96,7 @@
           :selection.sync="selection"
           row-key="id"
         >
-          <!-- 表头工具栏 -->
-          <template v-slot:toolbar>
-            <el-button
-              size="small"
-              type="primary"
-              icon="el-icon-plus"
-              class="ele-btn-icon"
-              @click="synchronous()"
-              >同步</el-button
-            >
-          </template>
+
 
           <template v-slot:code="{ row }">
             <el-link type="primary" :underline="false" @click="openDetail(row)">
@@ -251,7 +249,16 @@
       open(treeData, tableData) {
         this.treeData = treeData;
         console.log(tableData);
-        this.tableData = tableData;
+
+        if (
+          Object.prototype.hasOwnProperty.call(tableData.processRoute, 'list')
+        ) {
+          this.tableData = tableData;
+        } else {
+          this.tableData = tableData;
+          this.tableData.processRoute.list = [];
+        }
+
         this.visible = true;
       },
       selected() {

+ 270 - 0
src/views/material/BOMmanage/components/standardOutput.vue

@@ -0,0 +1,270 @@
+<template>
+  <el-dialog
+    :title="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">
+      <ProductSearch @search="reload" ref="searchRef" />
+
+      <ele-split-layout
+        width="244px"
+        allow-collapse
+        :right-style="{ overflow: 'hidden' }"
+      >
+        <div class="ele-border-lighter split-layout-right-content">
+          <el-tree
+            :data="treeList"
+            :props="defaultProps"
+            ref="treeRef"
+            :default-expanded-keys="current && current.id ? [current.id] : []"
+            :highlight-current="true"
+            node-key="id"
+            @node-click="handleNodeClick"
+          ></el-tree>
+        </div>
+        <!-- 表格 -->
+        <template v-slot:content>
+          <ele-pro-table
+            ref="table"
+            :columns="columns"
+            :datasource="datasource"
+            :selection.sync="selection"
+            row-key="id"
+            height="calc(100vh - 350px)"
+            class="dict-table"
+          >
+          </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 ProductSearch from '@/components/select/bom/product-search.vue';
+  import { getMaterialList } from '@/api/material/list.js';
+
+  import { getTreeByPid } from '@/api/classifyManage';
+  export default {
+    components: { ProductSearch },
+    data() {
+      return {
+        visible: false,
+        type: 1,
+        selection: [],
+        // 表格列配置
+        columns: [
+          {
+            columnKey: 'selection',
+            type: 'selection',
+            width: 45,
+            align: 'center'
+          },
+          {
+            columnKey: 'index',
+            type: 'index',
+            width: 45,
+            align: 'center',
+            reserveSelection: true
+          },
+          {
+            prop: 'code',
+            label: '编码'
+          },
+          {
+            prop: 'name',
+            label: '名称',
+            showOverflowTooltip: true
+          },
+          {
+            prop: 'brandNum',
+            label: '牌号'
+          },
+
+          {
+            prop: 'modelType',
+            label: '型号',
+            align: 'center',
+            showOverflowTooltip: true
+          },
+          {
+            prop: 'specification',
+            label: '规格',
+            align: 'center',
+            showOverflowTooltip: true
+          },
+          {
+            prop: 'measuringUnit',
+            label: '计量单位',
+            showOverflowTooltip: true,
+            minWidth: 90
+          },
+
+          {
+            prop: 'weightUnit',
+            label: '重量单位',
+            showOverflowTooltip: true,
+            minWidth: 90
+          },
+
+          {
+            prop: 'roughWeight',
+            label: '毛重',
+            showOverflowTooltip: true,
+            minWidth: 90
+          },
+
+          {
+            prop: 'netWeight',
+            label: '净重',
+            showOverflowTooltip: true,
+            minWidth: 90
+          },
+
+          {
+            prop: 'packingUnit',
+            align: 'center',
+            label: '包装单位',
+            showOverflowTooltip: true
+          },
+          {
+            prop: 'categoryLevelPath',
+            label: '分类',
+            align: 'center',
+            showOverflowTooltip: true
+          },
+
+          {
+            action: 'action',
+            slot: 'action',
+            align: 'center',
+            label: '选择'
+          }
+        ],
+        title: null,
+        categoryLevelId: null,
+        radio: null,
+        idx: null,
+
+        isCategory: true,
+
+        current: {},
+
+        treeList: [],
+        treeLoading: false,
+
+        defaultProps: {
+          children: 'children',
+          label: 'name'
+        }
+      };
+    },
+
+    watch: {},
+    methods: {
+      /* 表格数据源 */
+      datasource({ page, where, limit }) {
+        return getMaterialList({
+          ...where,
+          pageNum: page,
+          size: limit,
+          categoryLevelId: this.isCategory ? this.categoryLevelId : null
+        });
+      },
+      handleNodeClick(data) {
+        this.isCategory = true;
+        this.categoryLevelId = data.id;
+        this.$refs.table.reload({ pageNum: 1, where: {} });
+        this.$refs.searchRef.reset2();
+      },
+      /* 刷新表格 */
+      reload(where) {
+        this.isCategory = false;
+        this.$refs.table.reload({ pageNum: 1, where: where });
+      },
+      open(type) {
+        this.type = type;
+        this.getTreeData();
+        this.visible = true;
+      },
+
+      async getTreeData() {
+        try {
+          this.treeLoading = true;
+
+          const res = await getTreeByPid(this.type);
+          this.treeLoading = false;
+          if (res?.code === '0') {
+            this.treeList = res.data;
+
+            this.$nextTick(() => {
+              // 默认高亮第一级树节点
+              if (this.treeList[0]) {
+                this.rootTreeId = this.treeList[0].id;
+                this.$nextTick(() => {
+                  this.$refs.treeRef.setCurrentKey(this.treeList[0].id);
+                });
+              }
+            });
+            return this.treeList;
+          }
+        } catch (error) {}
+        this.treeLoading = false;
+      },
+      handleClose() {
+        this.visible = false;
+        this.current = null;
+        this.radio = '';
+      },
+      selected() {
+        if (this.selection.length <= 0) {
+          return this.$message.warning('请至少选择一条数据');
+        }
+        this.$emit('selection', this.type,this.selection);
+        this.handleClose();
+      }
+    }
+  };
+</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;
+  }
+</style>

+ 153 - 210
src/views/material/BOMmanage/components/workingProcedure.vue

@@ -157,123 +157,8 @@
             </template>
           </ele-pro-table>
         </el-tab-pane>
-        <el-tab-pane label="质检参数" name="质检参数">
-          <ele-pro-table
-            ref="qualityTable"
-            :datasource="datasource"
-            :immediate="true"
-            :need-page="false"
-            :columns="columns"
-          >
-            <!-- 表头工具栏 -->
-            <template v-if="!isView" v-slot:toolbar>
-              <el-button
-                size="small"
-                icon="el-icon-plus"
-                class="ele-btn-icon"
-                type="primary"
-                @click.native="openParam('质检')"
-                >添加参数</el-button
-              >
-            </template>
-
-            <template v-slot:sort="{ row }">
-              <div v-if="isView">{{ row.sort }}</div>
-              <el-input v-else v-model="row.sort"></el-input>
-            </template>
-
-            <!-- 默认值 -->
-            <template v-slot:defaultValue="{ row }">
-              <div v-if="isView">
-                {{ row.defaultValue }}
-              </div>
-              <div v-else>
-                <el-input
-                  v-if="
-                    row.textType == 1 ||
-                    row.textType == 4 ||
-                    row.textType == 3 ||
-                    row.textType == 5
-                  "
-                  v-model="row.defaultValue"
-                  placeholder="请输入"
-                ></el-input>
-                <el-select
-                  v-if="row.textType == 2"
-                  v-model="row.defaultValue"
-                  placeholder="请选择"
-                >
-                  <el-option label="TRUE" :value="'TRUE'" />
-                  <el-option label="FALSE" :value="'FALSE'" />
-                </el-select>
-              </div>
-            </template>
-
-            <!-- 上限 -->
-            <template v-slot:maxValue="{ row }">
-              <div v-if="isView">
-                {{ row.maxValue }}
-              </div>
-              <div v-else>
-                <el-input
-                  v-if="row.textType == 3"
-                  v-model="row.maxValue"
-                  placeholder="请输入"
-                ></el-input>
-              </div>
-            </template>
-            <!-- 下限 -->
-            <template v-slot:minValue="{ row }">
-              <div v-if="isView">
-                {{ row.minValue }}
-              </div>
-              <div v-else>
-                <el-input
-                  v-if="row.textType == 3"
-                  v-model="row.minValue"
-                  placeholder="请输入"
-                ></el-input>
-              </div>
-            </template>
-
-            <!-- 单位 -->
-            <template v-slot:unitName="{ row }">
-              <div v-if="isView">
-                {{ row.unitName }}
-              </div>
-              <div v-else>
-                <DictSelection
-                  v-if="row.textType != 2 && row.textType != 5"
-                  dictName="工艺参数单位"
-                  clearable
-                  filterable
-                  v-model="row.unitName"
-                >
-                </DictSelection>
-
-                <span v-if="row.textType == 5"> h(小时)</span>
-              </div>
-            </template>
-
-            <!-- 操作列 -->
-            <template v-slot:action="{ row }">
-              <el-popconfirm
-                class="ele-action"
-                title="确定要删除当前参数吗?"
-                @confirm="remove(row, '工艺')"
-              >
-                <template v-slot:reference>
-                  <el-link
-                    type="danger"
-                    :underline="false"
-                    icon="el-icon-delete"
-                  >
-                    删除
-                  </el-link>
-                </template>
-              </el-popconfirm>
-            </template>
-          </ele-pro-table>
+        <el-tab-pane label="质检项参数" name="质检项参数">
+          <term></term>
         </el-tab-pane>
         <el-tab-pane label="生产节拍" name="生产节拍">
           <el-form label-width="100px" ref="form" :model="beatParam">
@@ -619,6 +504,27 @@
             </template>
           </ele-pro-table>
         </el-tab-pane>
+
+        <el-tab-pane label="关键设备" name="关键设备">
+          <ele-pro-table
+            ref="deviceTabRef"
+            :columns="standardCol"
+            :datasource="datasource"
+            :need-page="false"
+            :immediate="true"
+          >
+            <!-- 表头工具栏 -->
+            <template v-if="!isView" v-slot:toolbar>
+              <el-button type="primary" @click="add">添加</el-button>
+            </template>
+            <template v-slot:action="{ row, $index }">
+              <el-link type="danger" @click="handleDel(row, $index)"
+                >删除</el-link
+              >
+            </template>
+          </ele-pro-table>
+        </el-tab-pane>
+
         <el-tab-pane label="制造资源" name="制造资源">
           <ele-pro-table
             ref="resourceTable"
@@ -733,6 +639,9 @@
           </ele-pro-table>
         </el-tab-pane>
         <el-tab-pane label="替代料" name="替代料">
+
+
+
           <ele-pro-table
             ref="replaceMaterialTable"
             :columns="columns1"
@@ -743,7 +652,16 @@
             <!-- 表头工具栏 -->
             <template v-if="!isView" v-slot:toolbar>
               <el-button type="primary" @click="add">添加</el-button>
+              <div class="toolbar_box">
+                <div
+                  ><span>基本数量</span>
+                  <el-input placeholder="请输入" v-model.number="baseCount2">
+                  </el-input>
+                  <DictSelection dictName="计量单位" v-model="baseCountUnit2"
+                /></div>
+              </div>
             </template>
+
             <template v-slot:action="{ row, $index }">
               <el-link type="primary" @click="handleDel(row, $index)"
                 >删除</el-link
@@ -969,102 +887,23 @@
           </ele-pro-table>
         </el-tab-pane>
 
-        <el-tab-pane label="" name="工艺文件">
+        <el-tab-pane label="标准产出" name="标准产出">
           <ele-pro-table
-            ref="fileTable"
-            :columns="jobColumns1"
+            ref="standard"
+            :columns="standardCol"
             :datasource="datasource"
             :need-page="false"
             :immediate="true"
           >
             <!-- 表头工具栏 -->
             <template v-if="!isView" v-slot:toolbar>
-              <el-button type="primary" @click="addFile">添加</el-button>
+              <el-button type="primary" @click="add">添加</el-button>
             </template>
             <template v-slot:action="{ row, $index }">
-              <el-link type="primary" @click="handleDel(row, $index)"
+              <el-link type="danger" @click="handleDel(row, $index)"
                 >删除</el-link
               >
             </template>
-            <template v-slot:type="{ row }">
-              <div v-if="isView">{{ row.type }}</div>
-              <el-input
-                v-else
-                v-model="row.type"
-                placeholder="请输入"
-              ></el-input>
-            </template>
-
-            <template v-slot:code="{ row }">
-              <div v-if="isView">{{ row.code }}</div>
-              <el-input
-                v-else
-                v-model="row.code"
-                placeholder="请输入"
-              ></el-input>
-            </template>
-
-            <template v-slot:versions="{ row }">
-              <div v-if="isView">{{ row.versions }}</div>
-              <el-input
-                v-else
-                v-model="row.versions"
-                placeholder="请输入"
-              ></el-input>
-            </template>
-
-            <template v-slot:status="{ row }">
-              <div v-if="isView">{{
-                statusOption.filter((item) => item.value == row.status)[0].label
-              }}</div>
-              <div v-else>
-                <template>
-                  <el-select v-model="row.status" placeholder="请选择">
-                    <el-option
-                      v-for="item in statusOption"
-                      :label="item.label"
-                      :value="item.value"
-                      :key="item.value"
-                    >
-                    </el-option>
-                  </el-select>
-                </template>
-              </div>
-            </template>
-
-            <template v-slot:path="{ row }">
-              <div v-if="isView">附件</div>
-              <div v-else
-                ><div class="downLoad">
-                  <fileUpload
-                    v-model="jobFiledList"
-                    :show-file-list="false"
-                    module="main"
-                    @input="uploadedJobSuccess($event, row)"
-                    :showLib="false"
-                    :limit="1"
-                  />
-                  <div v-if="row.path">
-                    <el-button
-                      style="margin-left: 10px"
-                      size="mini"
-                      type="primary"
-                      @click="downloadFile(row.path)"
-                      >下载</el-button
-                    >
-                  </div></div
-                >
-              </div>
-            </template>
-
-            <template v-slot:remark="{ row }">
-              <div v-if="isView">{{ row.remark }}</div>
-              <el-input
-                v-else
-                v-model="row.remark"
-                placeholder="请输入"
-              ></el-input>
-            </template>
           </ele-pro-table>
         </el-tab-pane>
       </el-tabs>
@@ -1078,6 +917,11 @@
       @selection="addProductList"
     ></ProductModalMultiple>
 
+    <standardOutput
+      ref="standardOutputRefs"
+      @selection="chooseStandardList"
+    ></standardOutput>
+
     <div class="btns">
       <el-button type="primary" size="small" @click="save">{{
         isView ? '确定' : '保存'
@@ -1098,6 +942,8 @@
   import ProductModalMultiple from './ProductModalMultiple.vue';
   import userSearch from './user-search.vue';
   import jobDialog from './jobDialog.vue';
+  import standardOutput from './standardOutput.vue';
+  import term from '../qualityTesting/term';
   export default {
     components: {
       userSearch,
@@ -1105,13 +951,17 @@
       fileUpload,
       ProductModal,
       jobDialog,
-      ProductModalMultiple
+      ProductModalMultiple,
+      standardOutput,
+      term
     },
     mixins: [dictMixins],
     data() {
       return {
         baseCount: '',
         baseCountUnit: '',
+        baseCount2: '',
+        baseCountUnit2: '',
         isView: false,
         filedList: [],
         jobFiledList: [],
@@ -1406,6 +1256,50 @@
           }
         ],
 
+        standardCol: [
+          {
+            prop: 'code',
+            label: '编码'
+          },
+          {
+            prop: 'name',
+            label: '名称',
+            showOverflowTooltip: true
+          },
+          {
+            prop: 'brandNum',
+            label: '牌号'
+          },
+
+          {
+            prop: 'modelType',
+            label: '型号',
+            align: 'center',
+            showOverflowTooltip: true
+          },
+          {
+            prop: 'specification',
+            label: '规格',
+            align: 'center',
+            showOverflowTooltip: true
+          },
+          {
+            prop: 'measuringUnit',
+            label: '计量单位',
+            showOverflowTooltip: true,
+            minWidth: 90
+          },
+
+          {
+            columnKey: 'action',
+            label: '操作',
+            align: 'center',
+            resizable: false,
+            slot: 'action',
+            showOverflowTooltip: true
+          }
+        ],
+
         rowData: {},
         treeData: {},
         currentIndex: 0,
@@ -1522,7 +1416,12 @@
           type = 'aptitudeParam';
         } else if (this.activeName === '工艺文件') {
           type = 'fileParam';
+        } else if (this.activeName === '标准产出') {
+          type = 'standardOutput';
+        } else if (this.activeName === '关键设备') {
+          type = 'standardDevice';
         }
+
         this.tableData.taskParam[this.currentIndex][type].splice(index, 1);
       },
       addProductList(list) {
@@ -1600,6 +1499,12 @@
         if (this.activeName === '材料定额') {
           this.$refs.productMultipleRefs.open(1);
           return;
+        } else if (this.activeName === '标准产出') {
+          this.$refs.standardOutputRefs.open(9);
+          return;
+        } else if (this.activeName === '关键设备') {
+          this.$refs.standardOutputRefs.open(4);
+          return;
         } else if (this.activeName === '制造资源') {
           type = 'resource';
         } else if (this.activeName === '替代料') {
@@ -1645,11 +1550,6 @@
           this.$refs.table.setData(
             this.tableData.taskParam[this.currentIndex].produceList || []
           );
-        } else if (this.activeName === '质检参数') {
-          // 质检参数
-          this.$refs.qualityTable.setData(
-            this.tableData.taskParam[this.currentIndex].qualityParam || []
-          );
         } else if (this.activeName === '生产节拍') {
           console.log(this.tableData.taskParam[this.currentIndex].beatParam);
           this.beatParam =
@@ -1695,6 +1595,14 @@
               this.tableData.taskParam[this.currentIndex].fileParam
             );
           }
+        } else if (this.activeName === '标准产出') {
+          this.$refs.standard.setData(
+            this.tableData.taskParam[this.currentIndex].standardOutput || []
+          );
+        } else if (this.activeName === '关键设备') {
+          this.$refs.deviceTabRef.setData(
+            this.tableData.taskParam[this.currentIndex].standardDevice || []
+          );
         }
       },
       openParam(type) {
@@ -1710,16 +1618,38 @@
         let dom = null;
         if (this.activeName === '工艺参数') {
           dom = this.$refs.table;
-        } else if (this.activeName === '质检参数') {
-          dom = this.$refs.qualityTable;
         }
         dom.setData([...data, ...dom.getData()]);
         this.$set(
           this.tableData.taskParam[this.currentIndex],
-          this.activeName === '工艺参数' ? 'produceList' : 'qualityParam',
+          this.activeName === '工艺参数' ? 'produceList' : '',
           dom.getData()
         );
       },
+
+      chooseStandardList(type, data) {
+        let dom = null;
+
+        if (type == 9) {
+          dom = this.$refs.standard;
+          dom.setData([data[0]]);
+
+          this.$set(
+            this.tableData.taskParam[this.currentIndex],
+            'standardOutput',
+            dom.getData()
+          );
+        } else if (type == 4) {
+          dom = this.$refs.deviceTabRef;
+          dom.setData([data[0]]);
+
+          this.$set(
+            this.tableData.taskParam[this.currentIndex],
+            'standardDevice',
+            dom.getData()
+          );
+        }
+      },
       remove(row, type) {
         let dom = null;
         if (type === '工艺') {
@@ -1769,6 +1699,13 @@
           (item) => item.id === rowData.id
         );
         this.activeName = '工艺参数';
+
+        this.baseCount = rowData.baseCount;
+        this.baseCountUnit = rowData.baseCountUnit;
+
+        this.baseCount2 = rowData.baseCount2;
+        this.baseCountUnit2 = rowData.baseCountUnit2;
+
         this.visible = true;
         setTimeout(() => {
           console.log(this.$refs);
@@ -1807,6 +1744,12 @@
             this.baseCount;
           this.tableData.taskParam[this.currentIndex].baseCountUnit =
             this.baseCountUnit;
+
+            this.tableData.taskParam[this.currentIndex].baseCount2 =
+            this.baseCount2;
+          this.tableData.taskParam[this.currentIndex].baseCountUnit2 =
+            this.baseCountUnit2;
+
           workingProcedureUpdate({
             id: this.tableData.id,
             categoryId: this.treeData.categoryId,

+ 89 - 21
src/views/material/BOMmanage/details.vue

@@ -4,7 +4,15 @@
       <ele-split-layout
         width="260px"
         allow-collapse
+        :resizable="true"
+        :min-size="200"
+        :max-size="-200"
+        :left-style="{
+          overflow: 'hidden',
+          width: '100%'
+        }"
         :right-style="{ overflow: 'hidden' }"
+        :responsive="false"
       >
         <div class="ele-border-lighter sys-organization-list">
           <div class="radio_box rx-cc">
@@ -16,6 +24,7 @@
               <el-radio-button :label="1">PBOM</el-radio-button>
               <el-radio-button :label="2">MBOM</el-radio-button>
               <el-radio-button :label="3">ABOM</el-radio-button>
+
             </el-radio-group>
           </div>
 
@@ -36,7 +45,11 @@
             :highlight-current="true"
             node-key="id"
             @node-click="handleNodeClick"
-          ></el-tree>
+          >
+            <span class="custom-tree-node" slot-scope="{ node, data }">
+              {{ node.label }} / {{ data.code }}
+            </span>
+          </el-tree>
         </div>
         <template v-slot:content>
           <div class="pbom-box">
@@ -50,7 +63,7 @@
               >
               <el-button
                 v-if="
-                  currentNodeData.bomType == 2 &&
+                (currentNodeData.bomType == 2  || currentNodeData.bomType == 3) &&
                   currentNodeData.children?.length <= 0
                 "
                 type="danger"
@@ -61,13 +74,14 @@
                 >删除</el-button
               >
               <el-button
+                v-if="currentNodeData.bomType == 1"
                 type="primary"
                 size="mini"
                 icon="el-icon-download"
                 plain
                 >导出</el-button
               >
-              <el-button type="primary" size="mini" icon="el-icon-upload2" plain
+              <el-button   @click="uploadFile" v-if="currentNodeData.bomType == 1"  type="primary" size="mini" icon="el-icon-upload2" plain
                 >导入</el-button
               >
               <el-button
@@ -75,10 +89,22 @@
                 size="mini"
                 icon="el-icon-refresh"
                 plain
-                @click="transformation"
+                @click="transformation('M')"
                 v-if="currentNodeData.bomType == 1"
                 >转换MBOM</el-button
               >
+
+              <el-button
+                type="primary"
+                size="mini"
+                icon="el-icon-refresh"
+                plain
+                @click="transformation('A')"
+                v-if="currentNodeData.bomType == 1"
+                >转换ABOM</el-button
+              >
+
+   
               <div v-if="!noBack" class="back-btn">
                 <el-button size="mini" icon="el-icon-back" @click="back"
                   >返回</el-button
@@ -86,10 +112,8 @@
               </div>
             </div>
 
-            <baseInfo
-              :dataInfo="currentNodeData"
-              v-if="currentNodeData.bomType == 2"
-            />
+            <baseInfo :dataInfo="currentNodeData" />
+
             <el-tabs
               v-model="activeName"
               class="tab-box"
@@ -99,15 +123,19 @@
               <el-tab-pane label="属性" name="属性">
                 <attribute :attributeData="currentNodeData"></attribute>
               </el-tab-pane>
-              <el-tab-pane label="文档" name="文档">
-                <document></document>
+              <el-tab-pane  :label="currentNodeData.bomType == 1 ? 'PBOM明细表' : currentNodeData.bomType == 2 ? 'MBOM明细表' : 'ABOM明细表' " name="明细表">
+                <!-- <document></document> -->
+                 <detailedList  :attributeData="currentNodeData"></detailedList>
               </el-tab-pane>
               <el-tab-pane
                 v-if="currentNodeData.bomType == 2"
                 label="工艺路线"
                 name="工艺路线"
               >
-                <routing :taskParam="currentNodeData"></routing>
+                <routing
+                  ref="routingRef"
+                  :taskParam="currentNodeData"
+                ></routing>
               </el-tab-pane>
               <el-tab-pane
                 v-if="currentNodeData.bomType == 2"
@@ -125,6 +153,8 @@
       </ele-split-layout>
     </el-card>
     <bomTreeDialog ref="bomTreeDialogRef" @reload="bomTreeDialogReload" />
+
+    <importDialog :defModule="moudleName" ref="importDialogRef" @success="reload" />
   </div>
 </template>
 
@@ -133,24 +163,30 @@
     getBomTreeList,
     getBomGetById,
     convert,
+    convertABom,
+    convertCBom,
     deleteBomTreeList
   } from '@/api/material/BOM.js';
   import { getTreeByGroup } from '@/api/classifyManage';
   import attribute from './components/attribute.vue';
   import routing from './components/routing.vue';
   import baseInfo from './components/baseInfo.vue';
-  import document from './components/document.vue';
+  // import document from './components/document.vue';
   import workmanship from './components/workmanship.vue';
   import bomTreeDialog from './components/bomTreeDialog.vue';
+  import importDialog from "./qualityTesting/import-dialog.vue";
+  import detailedList from './components/detailedList.vue'
   export default {
     name: 'BOMmanage',
     components: {
       attribute,
       baseInfo,
-      document,
+      // document,
       workmanship,
       bomTreeDialog,
-      routing
+      routing,
+      importDialog,
+      detailedList
     },
     data() {
       return {
@@ -173,7 +209,10 @@
         categoryId: 1,
         versions: null,
         loadingInstance: null,
-        noBack: false
+        noBack: false,
+        treeId: null,
+
+        moudleName : "mainUser",
       };
     },
     mounted() {
@@ -198,14 +237,21 @@
         this.versions = this.$route.query.versions;
         this.categoryId = this.$route.query.categoryId;
         this.noBack = this.$route.query.noBack;
+
         (this.currentNodeData = {
-          bomType: 1,
+          bomType: this.$route.query.bType || 1,
           children: []
         }),
           this.getTreeData();
       },
       handleClick(tab) {
-        console.log(tab);
+        if (
+          tab.name === '工艺路线' &&
+          this.currentNodeData.children?.length < 1
+        ) {
+          this.$refs.routingRef.reload();
+        }
+
         if (tab.name === '工艺' && this.currentNodeData.children?.length < 1) {
           this.$refs.workmanshipRef.reload();
         }
@@ -243,13 +289,14 @@
       back() {
         this.$router.go(-1);
       },
-      transformation() {
+      transformation(tt) {
         this.loadingInstance = this.$loading({
           lock: true,
           text: '转换中...',
           background: 'rgba(0, 0, 0, 0.7)'
         });
-        convert({ versions: this.versions, categoryId: this.categoryId }).then(
+        let ULR = tt == 'M' ? convert : tt == 'A' ? convertABom : ''
+        ULR({ versions: this.versions, categoryId: this.categoryId }).then(
           (data) => {
             if (data.code == '0') {
               this.loadingInstance.close();
@@ -262,7 +309,8 @@
         this.$refs.bomTreeDialogRef.open(
           this.currentNodeData.bomType,
           this.versions,
-          this.categoryId
+          this.categoryId,
+          this.treeId
         );
       },
       async getTreeData() {
@@ -294,6 +342,7 @@
       },
 
       handleNodeClick(data) {
+        this.treeId = data.id;
         this.handBomDetails(data.id);
       },
 
@@ -302,6 +351,16 @@
           getBomGetById(id).then((res) => {
             this.versions = res.data.versions;
             this.currentNodeData = res.data;
+
+            if (
+              this.activeName == '工艺路线' &&
+              this.currentNodeData.children?.length < 1
+            ) {
+              this.$nextTick(() => {
+                this.$refs.routingRef.reload();
+              });
+            }
+
             if (
               this.activeName == '工艺' &&
               this.currentNodeData.children?.length < 1
@@ -317,7 +376,16 @@
             children: []
           };
         }
-      }
+      },
+
+      uploadFile () {
+      this.$refs.importDialogRef.open();
+    },
+    
+    reload(where) {
+      this.getTreeData();
+      },
+
     }
   };
 </script>

+ 48 - 29
src/views/material/BOMmanage/index.vue

@@ -6,37 +6,43 @@
         :statusOpt="statusOpt"
         :categoryCode="where.categoryCode"
       />
-      <ele-pro-table
-        ref="table"
-        :columns="columns"
-        :datasource="datasource"
-        :initLoad="false"
-        class="dict-table"
-        tool-class="ele-toolbar-actions"
-      >
-        <!-- 表头工具栏 -->
-        <template v-slot:action="{ row }">
-          <el-link
-            style="margin-right: 20px"
-            type="primary"
-            @click="handelDetail(row)"
-            >详情</el-link
-          >
-          <el-switch
-            :active-value="'1'"
-            :inactive-value="'0'"
-            @change="openBom(row, $event)"
-            v-model="row.status"
-          >
-          </el-switch>
-        </template>
-      </ele-pro-table>
+      <el-tabs v-model="activeName" type="border-card" @tab-click="handleClick">
+        <el-tab-pane label="PBOM" name="1"> </el-tab-pane>
+        <el-tab-pane label="MBOM" name="2"> </el-tab-pane>
+        <el-tab-pane label="ABOM" name="3"> </el-tab-pane>
+
+        <ele-pro-table
+          ref="table"
+          :columns="columns"
+          :datasource="datasource"
+          :initLoad="false"
+          class="dict-table"
+          tool-class="ele-toolbar-actions"
+        >
+          <!-- 表头工具栏 -->
+          <template v-slot:action="{ row }">
+            <el-link
+              style="margin-right: 20px"
+              type="primary"
+              @click="handelDetail(row)"
+              >详情</el-link
+            >
+            <el-switch
+              :active-value="'1'"
+              :inactive-value="'0'"
+              @change="openBom(row, $event)"
+              v-model="row.status"
+            >
+            </el-switch>
+          </template>
+        </ele-pro-table>
+      </el-tabs>
     </el-card>
   </div>
 </template>
 
 <script>
-  import BOMSearch from '../materialBOM/components/BOM-search.vue';
+  import BOMSearch from './components/BOM-search.vue';
   import { getBomPageList, startAndStop } from '@/api/material/BOM';
 
   export default {
@@ -108,7 +114,9 @@
         },
         loading: false,
         loadingInstance: null,
-        where: {}
+        where: {},
+
+        activeName: "1"
       };
     },
     mounted() {
@@ -129,7 +137,6 @@
             pageNum: 1,
             size: 10
           }).then((data) => {
-     
             if (data.count > 1) {
               this.$refs.table.setData(data.list || []);
             } else {
@@ -162,6 +169,7 @@
       datasource({ where, page, limit }) {
         return getBomPageList({
           ...where,
+          bomType:  Number(this.activeName),
           pageNum: page,
           size: limit
         });
@@ -169,7 +177,7 @@
       handelDetail(row, noBack) {
         this.$router.push({
           path: '/material/BOMmanage/details',
-          query: { versions: row.versions, categoryId: row.categoryId, noBack }
+          query: { versions: row.versions, categoryId: row.categoryId, noBack, bType:this.activeName }
         });
       },
       /* 刷新表格 */
@@ -224,6 +232,17 @@
           .catch((e) => {
             this.loading = false;
           });
+      },
+
+      handleClick(tab) {
+        this.activeName = tab.name
+        getBomPageList({
+          pageNum: 1,
+          size: 10,
+          bomType:  Number(this.activeName)
+        }).then((data) => {
+          this.$refs.table.setData(data.list || []);
+        });
       }
     }
   };

+ 126 - 0
src/views/material/BOMmanage/qualityTesting/import-dialog.vue

@@ -0,0 +1,126 @@
+<template>
+  <!-- 上传 -->
+  <el-dialog title="导入文件上传" :visible.sync="dialogVisible" width="40%">
+    <el-form label-width="110px" class="zw-criterion">
+      <el-form-item label="选择文件">
+        <el-upload
+          class="avatar-uploader"
+          action="#"
+          :show-file-list="false"
+          :http-request="handlSuccess"
+          :before-upload="beforeUpload"
+        >
+          <el-button icon="el-icon-plus" size="small" type="primary"
+            >文件上传</el-button
+          >
+          <div slot="tip" class="el-upload__tip"
+            >只能上传excel文件</div
+          >
+        </el-upload>
+      </el-form-item>
+      <el-form-item label="上传列表">
+        <div class="imgs-box">
+          <p v-for="(item, index) in attaments" :key="index" class="imgs-p">
+            <span> {{ item.name }}</span>
+            <el-link @click="delFileList(index)" type="primary">删除</el-link>
+          </p>
+        </div>
+      </el-form-item>
+    </el-form>
+    <div slot="footer" class="dialog-footer">
+      <el-button size="small" @click="dialogVisible = false">关 闭</el-button>
+      <el-button size="small" :loading="loading"  @click="upload" type="primary">上 传</el-button>
+    </div>
+  </el-dialog>
+</template>
+
+<script>
+  import { importPBom } from '@/api/system/file/index.js';
+
+  export default {
+    props: {
+      defModule: ''
+    },
+    //注册组件
+    data() {
+      return {
+        showViewer: false, // 显示查看器
+        dialogVisible: false,
+        uploadShow: false,
+        module: '',
+        attaments: [], //上传文件
+        file: '',
+
+        loading: false
+      };
+    },
+    created() {},
+    methods: {
+      open() {
+        this.attaments = [];
+        this.module = '';
+        this.dialogVisible = true;
+      },
+      //删除附件
+      delFileList(index) {
+        this.attaments.splice(index, 1);
+      },
+      //上传限制
+      beforeUpload(file) {
+        const isLt10M = file.size / 1024 / 1024 < 10;
+        if (!isLt10M) {
+          this.$message.error('导入单文件大小不能超过 10MB!');
+        }
+        return isLt10M;
+      },
+      //图片上传
+      handlSuccess(param) {
+        this.file = param.file;
+        this.attaments.push(param.file);
+      },
+      // 文件上传
+      async upload() {
+        if (this.attaments.length == 0) {
+          return this.$message.warning('文件不能为空!');
+        }
+        this.module = this.$props.defModule;
+
+        this.loading = true;
+        await importPBom({
+          module: this.module,
+          multiPartFiles: this.attaments
+        });
+
+        setTimeout(() => {
+          this.loading = false;
+        }, 10000);
+        this.$message.success('操作成功!');
+        this.dialogVisible = false;
+        this.$emit('success');
+      }
+    }
+  };
+</script>
+
+<style lang="scss">
+  .zw-table-header {
+    float: right;
+  }
+
+  .imgs-box .imgs-p {
+    height: 30px;
+    background: #f0f3f3;
+    line-height: 30px;
+    width: 372px;
+    margin-bottom: 5px;
+    padding: 0 10px;
+    display: flex;
+    justify-content: space-between;
+  }
+  .zw-criterion-normal {
+    padding: 20px 0 0 0;
+  }
+  .el-main {
+    overflow: hidden;
+  }
+</style>

+ 224 - 0
src/views/material/BOMmanage/qualityTesting/inspectionClassify/components/edit.vue

@@ -0,0 +1,224 @@
+<!-- 用户编辑弹窗 -->
+<template>
+  <el-dialog
+    class="ele-dialog-form"
+    :title="title"
+    :visible.sync="visible"
+    :before-close="handleClose"
+    :close-on-click-modal="false"
+    :close-on-press-escape="false"
+    width="1000px"
+    append-to-body
+  >
+    <el-form ref="form" :model="form" :rules="rules" label-width="100px">
+      <el-row>
+        <el-col :span="24">
+          <el-tabs v-model="activeName" type="card">
+            <el-tab-pane
+              :label="item.name"
+              :name="item.name"
+              v-for="item in activeList"
+              :key="item.name"
+            >
+              <el-table
+                v-show="activeName == '质检项' "
+                style="margin-top: 15px"
+                :data="form.parameterStandards"
+                border
+                height="40vh"
+              >
+                <el-table-column
+                  :label="form.singleWeightDivision"
+                  align="center"
+                >
+                  <el-table-column
+                    label="参数上限"
+                    align="center"
+                    v-if="form.parameterType == 3"
+                  >
+                    <template slot-scope="scope">
+                      <el-form-item label-width="0" prop="finalValue">
+                        <el-input
+                          clearable
+                          :disabled="type == 'detail'"
+                          v-model="scope.row.finalValue"
+                          placeholder="请输入"
+                        />
+                      </el-form-item>
+                    </template>
+                  </el-table-column>
+                  <el-table-column
+                    label="参数下限"
+                    align="center"
+                    v-if="form.parameterType == 3"
+                  >
+                    <template slot-scope="scope">
+                      <el-form-item label-width="0" prop="initialValue">
+                        <el-input
+                          :disabled="type == 'detail'"
+                          clearable
+                          v-model="scope.row.initialValue"
+                          placeholder="请输入"
+                        />
+                      </el-form-item>
+                    </template>
+                  </el-table-column>
+                  <el-table-column
+                    label="默认值"
+                    align="center"
+                    v-if="form.parameterType != 3"
+                  >
+                    <template slot-scope="scope">
+                      <el-form-item label-width="0" prop="defaultValue">
+                        <el-input
+                          clearable
+                          :disabled="type == 'detail'"
+                          v-model="scope.row.defaultValue"
+                          placeholder="请输入"
+                        />
+                      </el-form-item>
+                    </template>
+                  </el-table-column>
+                </el-table-column>
+                <el-table-column :label="form.tolerance" align="center">
+                  <el-table-column label="质检标准" align="center">
+                    <template slot-scope="scope">
+                      <el-form-item label-width="0" prop="inspectionStandard">
+                        <el-input
+                          clearable
+                          v-model="scope.row.toleranceValue"
+                          placeholder="请输入"
+                          :disabled="type == 'detail'"
+                        >
+                          <DictSelection
+                            style="width: 100px"
+                            slot="prepend"
+                            clearable
+                            :disabled="type == 'detail'"
+                            dictName="数学字符"
+                            v-model="scope.row.symbol"
+                          ></DictSelection>
+                        </el-input>
+                        <!-- </el-form-item> -->
+                      </el-form-item>
+                    </template>
+                  </el-table-column>
+           
+                </el-table-column>
+              </el-table>
+
+            </el-tab-pane></el-tabs
+          >
+
+
+        </el-col>
+      </el-row>
+    </el-form>
+
+    <template v-slot:footer>
+      <el-button @click="handleClose">取消</el-button>
+      <el-button
+        type="primary"
+        :loading="loading"
+        @click="save"
+        v-if="type != 'detail'"
+      >
+        保存
+      </el-button>
+    </template>
+  </el-dialog>
+</template>
+
+<script>
+  export default {
+    components: {},
+
+    data() {
+      const defaultForm = function () {
+        return {
+          parameterStandards: [],
+          linePoints: []
+        };
+      };
+      return {
+        defaultForm,
+        // 表单数据
+        form: { ...defaultForm() },
+        activeName: '质检项',
+        activeList: [{ name: '质检项' }],
+        // 表单验证规则
+        rules: {
+     
+        },
+        visible: false,
+
+        title: null,
+        loading: false
+      };
+    },
+
+    created() {},
+    methods: {
+      open(row) {
+        this.form = JSON.parse(JSON.stringify(row));
+        this.visible = true;
+      },
+ 
+
+      handleDeleteItem(index, list) {
+        this.form[list].splice(index, 1);
+      },
+      /* 保存编辑 */
+      save() {},
+      restForm() {
+        this.form = { ...this.defaultForm() };
+        this.$nextTick(() => {
+          this.$refs.form.clearValidate();
+        });
+      },
+      handleClose() {
+        this.restForm();
+        this.visible = false;
+      }
+    }
+  };
+</script>
+
+<style lang="scss" scoped>
+  .location-warp {
+    display: flex;
+
+    .detail {
+      margin-left: 10px;
+    }
+  }
+
+  :deep(
+      .el-dialog:not(.ele-dialog-form)
+        .el-dialog__body
+        .el-form
+        .el-form-item:last-child
+    ) {
+    margin-bottom: 22px;
+  }
+  :deep(
+      .el-dialog:not(.ele-dialog-form)
+        .el-dialog__body
+        .el-form
+        .el-table__body
+        .el-table__row
+        .el-form-item:last-child
+    ) {
+    margin-bottom: 0 !important;
+  }
+  .add-product {
+    width: 100%;
+    display: flex;
+    align-items: center;
+    justify-content: flex-end;
+    font-size: 30px;
+    color: #1890ff;
+    margin: 10px 0;
+    cursor: pointer;
+  }
+</style>

+ 165 - 0
src/views/material/BOMmanage/qualityTesting/inspectionClassify/components/user-list.vue

@@ -0,0 +1,165 @@
+<template>
+  <div>
+    <user-search @search="reload" ref="searchRef"> </user-search>
+    <!-- 数据表格 -->
+    <ele-pro-table
+      ref="table"
+      :columns="columns"
+      :datasource="datasource"
+      height="calc(100vh - 365px)"
+      full-height="calc(100vh - 116px)"
+      tool-class="ele-toolbar-form"
+      cache-key="systemOrgUserTable"
+    >
+      <!-- 编码列 -->
+
+      <template v-slot:name="{ row }">
+        {{ row.qualityStandard.name }}
+      </template>
+
+      <template v-slot:code="{ row }">
+        <el-link
+          @click="openDetail(row.qualityStandard)"
+          type="primary"
+          :underline="false"
+        >
+          {{ row.qualityStandard.code }}
+        </el-link>
+      </template>
+
+      <template v-slot:type="{ row }">
+        {{ getDictValue('质检标准类型', row.qualityStandard.type) }}
+      </template>
+
+      <template v-slot:standardCode="{ row }">
+        {{ row.qualityStandard.standardCode }}
+      </template>
+
+      <template v-slot:status="{ row }">
+        {{ row.qualityStandard.status == 1 ? '启用' : '停用' }}
+      </template>
+
+      <template v-slot:mode="{ row }">
+        {{ getDictValue('质检方式', row.mode) }}
+      </template>
+
+      <template v-slot:version="{ row }">
+        {{ row.qualityStandard.version }}
+      </template>
+    </ele-pro-table>
+
+    <Detail ref="detailRef"></Detail>
+  </div>
+</template>
+
+<script>
+  import userSearch from './user-search.vue';
+  import { getList } from '@/api/material/inspectionClassify';
+  import dictMixins from '@/mixins/dictMixins';
+  import Detail from './edit.vue';
+
+  export default {
+    mixins: [dictMixins],
+    components: { userSearch, Detail },
+    props: {
+      // 类别id
+
+      rootId: [Number, String]
+    },
+    data() {
+      return {
+        // 当前编辑数据
+        current: null,
+
+        // 表格列配置
+        columns: [
+          {
+            columnKey: 'index',
+            type: 'index',
+            label: '序号',
+            width: 55,
+            align: 'center'
+          },
+
+          {
+            prop: 'code',
+            label: '标准编码',
+            showOverflowTooltip: true,
+            minWidth: 110,
+            slot: 'code'
+          },
+
+          {
+            prop: 'name',
+            label: '标准名称',
+            showOverflowTooltip: true,
+            minWidth: 110,
+            slot: 'name'
+          },
+
+          {
+            label: '标准类型',
+            prop: 'type',
+            slot: 'type'
+          },
+
+          {
+            label: '标准代码',
+            prop: 'standardCode'
+          },
+
+          {
+            prop: 'status',
+            label: '状态',
+            align: 'center',
+            minWidth: 110,
+            slot: 'status'
+          },
+
+          {
+            prop: 'version',
+            label: '版本号',
+            align: 'center',
+            minWidth: 110,
+            slot: 'version'
+          }
+        ]
+      };
+    },
+    created() {
+      this.requestDict('质检方式');
+      this.requestDict('质检标准类型');
+    },
+    methods: {
+      /* 表格数据源 */
+      datasource({ page, limit, where }) {
+        return getList({
+          ...where,
+          pageNum: page,
+          size: limit,
+          categoryLevelId: this.categoryLevelId || 12,
+          rootCategoryLevelId: this.rootId
+        });
+      },
+      /* 刷新表格 */
+      reload(where) {
+        this.$refs.table.reload({
+          pageNum: 1,
+          where: where,
+          categoryLevelId: this.categoryLevelId,
+          rootCategoryLevelId: this.rootId
+        });
+      },
+
+      clickSearch(info) {
+        this.categoryLevelId = info.id;
+        this.rootCategoryLevelId = info.rootCategoryLevelId;
+        this.reload();
+      },
+
+      openDetail(row) {
+        this.$refs.detailRef.open(row);
+      }
+    }
+  };
+</script>

+ 84 - 0
src/views/material/BOMmanage/qualityTesting/inspectionClassify/components/user-search.vue

@@ -0,0 +1,84 @@
+<!-- 搜索表单 -->
+<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="质检名称:">
+          <el-input clearable v-model="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 clearable  v-model="where.status" placeholder="请选择状态">
+            <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-col v-bind="styleResponsive ?{ lg: 6, md: 12 } : { span: 6 }">
+        <el-form-item label="组织机构:">
+          <auth-selection data-type="Array" v-model="where.deptIds" style="width: 100%"></auth-selection>
+        </el-form-item>
+      </el-col>
+      <el-col v-bind="styleResponsive ? { lg: 6, md: 12 } : { span: 6 }">
+        <el-form-item label-width="50px">
+          <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>
+        </el-form-item>
+      </el-col>
+    </el-row>
+  </el-form>
+</template>
+
+<script>
+export default {
+  data() {
+    // 默认表单数据
+    const defaultWhere = {
+      name: '',
+      status: ''
+    };
+
+
+    return {
+      // 表单数据
+      where: { ...defaultWhere },
+
+      statusList: [
+        {
+          value: 0,
+          label: '停用'
+        },
+        {
+          value: 1,
+          label: '启用'
+        }
+      ]
+    };
+  },
+  computed: {
+    // 是否开启响应式布局
+    styleResponsive() {
+      return this.$store.state.theme.styleResponsive;
+    }
+  },
+  methods: {
+    /* 搜索 */
+    search() {
+      console.log(this.where);
+      this.$emit('search', this.where);
+    },
+    /*  重置 */
+    reset() {
+      this.where = { ...this.defaultWhere };
+      this.search();
+    }
+  }
+};
+</script>

+ 105 - 0
src/views/material/BOMmanage/qualityTesting/inspectionClassify/index.vue

@@ -0,0 +1,105 @@
+<template>
+  <el-dialog
+    title="质检"
+    :visible.sync="visible"
+    :before-close="handleClose"
+    :close-on-click-modal="false"
+    :close-on-press-escape="false"
+    append-to-body
+    width="80%"
+  >
+    <div class="ele-body">
+      <el-card shadow="never" v-loading="loading">
+        <ele-split-layout
+          width="266px"
+          allow-collapse
+          :right-style="{ overflow: 'hidden' }"
+        >
+          <div>
+            <div class="ele-border-lighter sys-organization-list">
+              <AssetTree
+                @handleNodeClick="handleNodeClick"
+                @setRootId="setRootId"
+                :id="rootId"
+                ref="treeList"
+              />
+            </div>
+          </div>
+          <template v-slot:content>
+            <user-list
+              v-if="current"
+              :category-id="current.id"
+              :root-id="rootId"
+              ref="searchRef"
+            />
+          </template>
+        </ele-split-layout>
+      </el-card>
+    </div>
+  </el-dialog>
+</template>
+
+<script>
+  import AssetTree from '@/components/AssetTree';
+  import userList from './components/user-list.vue';
+
+  export default {
+    components: {
+      AssetTree,
+      userList
+    },
+    data() {
+      return {
+        // 加载状态
+        loading: false,
+        // 表格选中数据
+        selection: [],
+        current: null,
+        rootId: '12',
+        visible: false
+      };
+    },
+    computed: {},
+    methods: {
+      handleNodeClick(info) {
+        this.current = info;
+        this.$nextTick(() => {
+          console.log(info);
+          this.$refs.searchRef.clickSearch(info);
+        });
+      },
+      // 获取根节点id
+      setRootId(id) {
+        if (id) {
+          this.rootId = id;
+        }
+      },
+
+      open() {
+        this.visible = true;
+      },
+
+      handleClose() {
+        this.visible = false;
+      }
+    }
+  };
+</script>
+
+<style lang="scss" scoped>
+  .sys-organization-list {
+    height: calc(100vh - 264px);
+    box-sizing: border-box;
+    border-width: 1px;
+    border-style: solid;
+    overflow: auto;
+  }
+
+  .sys-organization-list :deep(.el-tree-node__content) {
+    height: 40px;
+
+    & > .el-tree-node__expand-icon {
+      margin-left: 10px;
+    }
+  }
+</style>

+ 0 - 0
src/views/material/BOMmanage/qualityTesting/spot.vue


+ 20 - 0
src/views/material/BOMmanage/qualityTesting/term.vue

@@ -0,0 +1,20 @@
+<template>
+    <div>
+        质检项
+        <el-button @click="() => this.$refs.termRef.open()">弹出</el-button>
+
+        <termPop ref="termRef"></termPop>
+    </div>
+</template>
+
+<script>
+import termPop from './inspectionClassify/index.vue'
+export default {
+    components: { termPop },
+    data() {
+        return {};
+    },
+};
+</script>
+
+<style lang="scss" scoped></style>

+ 30 - 30
src/views/material/product/components/index-data.vue

@@ -25,24 +25,16 @@
         >
           新建
         </el-button>
-        <div class="upload" v-if="rootTreeId == 6">
-          <el-upload
-            v-if="!isLoading"
-            :show-file-list="false"
-            class="upload-demo"
-            action=""
-            :before-upload="beforeUpload"
-            :on-success="successUpload"
-            :on-error="errorUpload"
-          >
-            <slot>
-              <el-button size="small" type="primary">导入</el-button>
-            </slot>
-          </el-upload>
-          <el-button v-else size="small" type="primary" :loading="isLoading"
-            >导入</el-button
-          >
-        </div>
+
+        <el-button
+          type="primary"
+          size="mini"
+          icon="el-icon-upload2"
+          plain
+          @click="uploadFile"
+          >导入</el-button
+        >
+
         <!-- <el-button
           v-if="rootTreeId == 9"
           size="small"
@@ -77,7 +69,7 @@
           size="small"
           type="primary"
           @click="handleLink('6')"
-          >关联备品备件</el-button 
+          >关联备品备件</el-button
         >-->
       </template>
       <template v-slot:action="{ row }">
@@ -115,13 +107,8 @@
           结构BOM
         </el-link>
 
-
-        <el-link
-          type="primary"
-          v-if="row.isProduct == 1"
-          :underline="false"
-        >
-        BOM管理
+        <el-link type="primary" v-if="row.isProduct == 1" :underline="false">
+          BOM管理
         </el-link>
 
         <el-link
@@ -213,6 +200,12 @@
         >
       </span>
     </el-dialog>
+
+    <importDialog
+      :defModule="moudleName"
+      ref="importDialogRef"
+      @success="reload"
+    />
   </div>
 </template>
 
@@ -228,8 +221,11 @@
   import linkMaterialDialog from './link-material-dialog.vue';
   import goodsAllocation from './goodsAllocation.vue';
   import aridRegion from './aridRegion';
+  import importDialog from '@/components/upload/import-dialog.vue';
+
   export default {
     components: {
+      importDialog,
       MaterialModal,
       ParamEdit,
       mouldDialog,
@@ -246,10 +242,11 @@
       rootTreeId: [Number, String],
 
       oneProduct: Boolean
-
     },
     data() {
       return {
+        moudleName : "mainCategory",
+
         errorData: [],
         exportErrorDioalogVisible: false,
         // 表格列配置
@@ -370,11 +367,10 @@
     methods: {
       toBomManager(row) {
         this.$router.push({
-          path: '/material/BOMmanage',
+          path: '/material/BOMmanage/details',
           query: {
             categoryId: row.id,
             code: row.code
-
           }
         });
       },
@@ -434,7 +430,7 @@
             id: row.id ? row.id : null,
             status: status,
             rootId: this.rootId,
-            oneProduct:this.oneProduct,
+            oneProduct: this.oneProduct,
             t: new Date().getTime()
           }
         });
@@ -499,6 +495,10 @@
 
       handleAridRegion(row) {
         this.$refs.aridRegionRef.open(row);
+      },
+
+      uploadFile () {
+        this.$refs.importDialogRef.open();
       }
     },
     watch: {

+ 129 - 59
src/views/material/product/detail.vue

@@ -16,7 +16,6 @@
 
         <el-row :gutter="24">
           <el-col :span="8">
-
             <el-form-item label="分类" prop="categoryLevelName">
               <el-input
                 v-model="form.categoryLevelName"
@@ -27,15 +26,18 @@
 
           <el-col :span="8" v-if="ruleCode == '自定义'" key="1">
             <el-form-item label="编码" prop="code">
-              <el-input v-model="form.code" readonly @click.native="openCode"  :disabled="status == 0" />
+              <el-input
+                v-model="form.code"
+                readonly
+                @click.native="openCode"
+                :disabled="status == 0"
+              />
             </el-form-item>
           </el-col>
 
-
-      
           <el-col :span="8" v-else key="2">
             <el-form-item label="编码" prop="code">
-              <el-input v-model="form.code"   :disabled="status == 0" />
+              <el-input v-model="form.code" :disabled="status == 0" />
             </el-form-item>
           </el-col>
 
@@ -45,6 +47,50 @@
             </el-form-item>
           </el-col>
 
+          <el-col :span="8">
+            <el-form-item label="图号/件号" prop="imgCode">
+              <el-input v-model="form.imgCode" />
+            </el-form-item>
+          </el-col>
+
+          <el-col :span="8">
+            <el-form-item label="生产类型" prop="produceType">
+              <el-select
+                style="width: 100%"
+                v-model="form.produceType"
+                filterable
+                multiple
+              >
+                <el-option
+                  v-for="item in dictList"
+                  :key="item.value"
+                  :value="item.value"
+                  :label="item.label"
+                ></el-option>
+              </el-select>
+            </el-form-item>
+          </el-col>
+
+          <el-col
+            :span="8"
+            v-if="[1, 23, 9, 28].includes(Number(categoryLevelPathId))"
+          >
+            <el-form-item label="加工类型" prop="isConsumable">
+              <el-select
+                v-model="form.isConsumable"
+                size="small"
+                style="width: 100%"
+              >
+                <el-option :value="1" label="批量"></el-option>
+                <el-option :value="0" label="单件"></el-option>
+              </el-select>
+            </el-form-item>
+          </el-col>
+          <el-col :span="8">
+            <el-form-item label="批准文号" prop="approvalNumber">
+              <el-input v-model="form.approvalNumber" />
+            </el-form-item>
+          </el-col>
           <el-col :span="8">
             <el-form-item label="牌号" prop="brandNum">
               <el-input v-model="form.brandNum" />
@@ -62,6 +108,12 @@
             </el-form-item>
           </el-col>
 
+          <el-col :span="8">
+            <el-form-item label="包装规格" prop="packingSpecification">
+              <el-input v-model="form.packingSpecification" />
+            </el-form-item>
+          </el-col>
+
           <el-col :span="8">
             <el-form-item label="计量单位" prop="measuringUnit">
               <DictSelection
@@ -117,22 +169,6 @@
             </el-form-item>
           </el-col>
 
-          <el-col
-            :span="8"
-            v-if="[1, 23, 9, 28].includes(Number(categoryLevelPathId))"
-          >
-            <el-form-item label="加工类型" prop="isConsumable">
-              <el-select
-                v-model="form.isConsumable"
-                size="small"
-                style="width: 100%"
-              >
-                <el-option :value="1" label="批量"></el-option>
-                <el-option :value="0" label="单件"></el-option>
-              </el-select>
-            </el-form-item>
-          </el-col>
-
           <el-col :span="8">
             <el-form-item label="净重">
               <div class="form-line">
@@ -140,24 +176,7 @@
               </div>
             </el-form-item>
           </el-col>
-          <el-col :span="8">
-            <el-form-item label="所属部门">
-              <deptSelect
-                v-model="form.chargeDeptId"
-                @changeGroup="searchDeptNodeClick"
-              />
-            </el-form-item>
-          </el-col>
-          <el-col :span="8">
-            <el-form-item label="负责人">
-              <personSelect
-                ref="directorRef"
-                v-model="form.chargeUserId"
-                @selfChange="handleDirectorChange"
-                :init="false"
-              />
-            </el-form-item>
-          </el-col>
+
           <el-col :span="8">
             <el-form-item label="级别">
               <template>
@@ -177,6 +196,17 @@
               </template>
             </el-form-item>
           </el-col>
+
+
+          <el-col :span="8" v-for="(f, idx) in fileList" :key="idx">
+            <el-form-item :label="f.label">
+              <template>
+                <div class="form-line">
+                  <el-input v-model="form.extField[f.prop]" />
+                </div>
+              </template>
+            </el-form-item>
+          </el-col>
         </el-row>
       </el-form>
     </el-card>
@@ -234,12 +264,13 @@
   import personSelect from '@/components/CommomSelect/person-select.vue';
   import linkMsg from './components/link-msg.vue';
   import { getDetails } from '@/api/classifyManage/itemInformation';
-
-  import { getCode } from '@/api/codeManagement';
+  import { getByCode } from '@/api/system/dictionary-data';
+  import { getCode, rootCategoryCode, fieldModel } from '@/api/codeManagement';
 
   import { addMaterial } from '@/api/material/list.js';
   import { deepClone } from '@/utils/index';
   import { finishPageTab, reloadPageTab } from '@/utils/page-tab-util';
+
   export default {
     name: 'ManageMaterial',
     components: {
@@ -284,8 +315,14 @@
         form: {
           categoryLevelGroupName: '',
           categoryLevelName: '',
-          isConsumable: 1
+          isConsumable: 1,
+
+          extField: {
+
+          }
         },
+
+       
         remarkform: {
           remarkAttach: []
         },
@@ -300,6 +337,10 @@
         },
 
         categoryLevelPathId: null,
+
+        dictList: [],
+
+        fileList: [],
         // 表单验证规则
         rules: {
           categoryLevelGroupName: [
@@ -332,30 +373,46 @@
         ruleCode: null,
         codeShow: false,
 
-        status: null,
-
+        status: null
       };
     },
+
     async created() {
+      this.getFieldModel();
       this.status = this.$route.query.status;
 
       if (this.$route.query.id) {
         this._getDetails();
       }
+      this.getDictList('productionType');
     },
     methods: {
       async _getDetails() {
         const data = await getDetails(this.$route.query.id);
         const info = deepClone(data);
+
         this.form = {
           ...info.category
         };
+        let productType_ = this.form.produceType;
+        if (productType_ != undefined && productType_ != null) {
+          let intproductType = [];
+          for (const [index, value] of productType_.entries()) {
+            intproductType.push(value.toString());
+          }
+          this.form.produceType = intproductType;
+        }
 
         this.categoryLevelPathId = info.category.categoryLevelPathIdParent;
         this.judgeSet(info);
-        this.searchDeptNodeClick(this.form.chargeDeptId);
 
-        this.$forceUpdate()
+        if (this.status == 1) {
+          rootCategoryCode(this.categoryLevelPathId).then((res) => {
+            this.$set(this.form, 'code', res);
+          });
+        }
+
+        this.$forceUpdate();
       },
       // 判断字段类型并赋值
       judgeSet(info) {
@@ -395,22 +452,23 @@
           this.categoryWms = info.categoryWms;
         }
       },
-      // 选择所属部门
-      searchDeptNodeClick(id, info) {
-        // 根据部门获取人员
-        const params = { executeGroupId: id ? id : '' };
-        this.$nextTick(() => {
-          this.$refs.directorRef.getList(params);
+
+      getFieldModel() {
+        fieldModel({ fieldModel: 't_main_category' }).then((res) => {
+
+          this.fileList = res;
+
+          this.fileList.forEach((f) => {
+            this.$set(this.form.extField,  f.prop,  ''); // 初始化动态模型属性
+          });
         });
       },
-      //选择负责人
-      handleDirectorChange(id, info) {},
+
       // 确定分类
       async confirmCategory(node, title, PathInfo, ruleCode) {
-   
-      if(this.status != 0) {
-        this.$set(this.form, 'code', null);
-      }
+        if (this.status != 0) {
+          this.$set(this.form, 'code', null);
+        }
         this.categoryLevelPathId = PathInfo.categoryLevelPathId.split(',')[0];
 
         if (title == '选择产品分类') {
@@ -425,7 +483,7 @@
 
           this.ruleCode = ruleCode;
 
-          if (ruleCode && ruleCode != '自定义'  && this.status != 0) {
+          if (ruleCode && ruleCode != '自定义' && this.status != 0) {
             const code = await getCode(ruleCode);
             this.$set(this.form, 'code', code);
           }
@@ -433,6 +491,18 @@
 
         this.$forceUpdate();
       },
+
+      async getDictList(code) {
+        let { data: res } = await getByCode(code);
+        this.dictList = res.map((item) => {
+          let values = Object.keys(item);
+          return {
+            value: Number(values[0]),
+            label: item[values[0]]
+          };
+        });
+      },
+
       openCategory() {
         this.$refs.categoryRefs.open();
       },

+ 4 - 2
src/views/system/organization/components/org-user-edit.vue

@@ -21,7 +21,7 @@
           </el-form-item>
 
           <el-form-item label="所属工厂:">
-            <el-select style="width: 100%" clearable v-model="form.factoryId" multiple  filterable placeholder="请选择所属工厂">
+            <el-select style="width: 100%" clearable v-model="form.factoryId"   filterable placeholder="请选择所属工厂">
               <el-option
                 v-for="item in factoryList"
                 :label="item.name"
@@ -159,7 +159,7 @@ export default {
       phone: '',
       age: '',
       accountId: '',
-      factoryId: [],
+      factoryId: '',
       workTypeId: ''
     };
     return {
@@ -329,6 +329,8 @@ export default {
           getUserDetail(this.data.id).then((res) => {
             this.form = {...res};
 
+            
+
             // this.deptTree = []
             // this.form.deptIds = []
             // if (this.form.deptTree) {

+ 11 - 1
src/views/system/organization/components/org-user-list.vue

@@ -22,6 +22,7 @@
           >
             添加
           </el-button>
+          <el-button type="primary" size="mini" icon="el-icon-upload2" plain @click="uploadFile">导入</el-button>
         </org-user-search>
       </template>
       <!-- 角色列 -->
@@ -86,12 +87,16 @@
       :organization-id="organizationId"
       @done="reload"
     />
+
+    <importDialog :defModule="moudleName" ref="importDialogRef" @success="reload" />
   </div>
 </template>
 
 <script>
   import OrgUserSearch from './org-user-search.vue';
   import OrgUserEdit from './org-user-edit.vue';
+  import importDialog from "@/components/upload/import-dialog.vue";
+
   import {
     getUserPage,
     removePersonnel,
@@ -99,7 +104,7 @@
   } from '@/api/system/organization';
 
   export default {
-    components: { OrgUserSearch, OrgUserEdit },
+    components: {importDialog, OrgUserSearch, OrgUserEdit},
     props: {
       // 机构id
       organizationId: [Number, String],
@@ -109,6 +114,8 @@
     },
     data() {
       return {
+        moudleName : "mainUser",
+
         // 表格列配置
         columns: [
           {
@@ -259,6 +266,9 @@
             row.status = !row.status ? 1 : 0;
             // this.$message.error(e.message);
           });
+      },
+      uploadFile () {
+        this.$refs.importDialogRef.open();
       }
     },
     watch: {

+ 20 - 1
src/views/technology/production/index.vue

@@ -13,6 +13,17 @@
           <el-button size="small" type="danger" icon="el-icon-delete" class="ele-btn-icon" @click="removeBatch">
             删除
           </el-button>
+          <el-button
+            size="small"
+            type="primary"
+            icon="el-icon-download"
+            class="ele-btn-icon"
+            plain
+
+            @click="uploadFile()"
+          >
+            导入
+          </el-button>
         </template>
 
         <template v-slot:name="{ row }">
@@ -53,6 +64,8 @@
     <user-setting :visible.sync="showSetting" :data="current" ref="userSetting" />
 
     <SampleParam v-if="sampleShow" :taskId="taskId" @close="close"></SampleParam>
+
+    <importDialog :defModule="moudleName" ref="importDialogRef" @success="reload" />
   </div>
 </template>
 
@@ -63,6 +76,7 @@ import UserSetting from './components/user-setting.vue';
 import SampleParam from './components/sampleParam.vue'
 import producetask from '@/api/technology/production';
 import control from '@/api/technology/control';
+import importDialog from "@/components/upload/import-dialog.vue";
 
 export default {
   name: 'technologyProduction',
@@ -70,10 +84,12 @@ export default {
     UserSearch,
     UserEdit,
     UserSetting,
-    SampleParam
+    SampleParam,
+    importDialog
   },
   data() {
     return {
+      moudleName : "mainProduceTask",
       // 表格列配置
       columns: [
         {
@@ -266,6 +282,9 @@ export default {
 
     close(done) {
         this.sampleShow = false
+    },
+    uploadFile () {
+      this.$refs.importDialogRef.open();
     }
   }
 };

+ 1 - 0
src/views/technology/route/components/user-taskinstance.vue

@@ -175,6 +175,7 @@
         let len = this.$refs.table.getData().length + 1;
         let arrM = arr.map((item, index) => {
           return { ...item.detail, orderNum: len + index };
+
         });
         arrM.forEach((element) => {
           if (element.id) {

+ 16 - 4
src/views/technology/stepManagement/index.vue

@@ -32,6 +32,7 @@
           >
             删除
           </el-button>
+          <!--
           <el-button
             size="small"
             type="primary"
@@ -41,12 +42,15 @@
           >
             导出
           </el-button>
+          -->
           <el-button
             size="small"
             type="primary"
             icon="el-icon-download"
             class="ele-btn-icon"
             plain
+
+            @click="uploadFile()"
           >
             导入
           </el-button>
@@ -117,6 +121,8 @@
       :taskId="taskId"
       @close="close"
     ></SampleParam>
+
+    <importDialog :defModule="moudleName" ref="importDialogRef" @success="reload" />
   </div>
 </template>
 
@@ -127,6 +133,7 @@
   import SampleParam from './components/sampleParam.vue';
   import stepManagement from '@/api/technology/stepManagement';
   import control from '@/api/technology/control';
+  import importDialog from "@/components/upload/import-dialog.vue";
 
   export default {
     name: 'technologyProduction',
@@ -134,10 +141,12 @@
       UserSearch,
       UserEdit,
       UserSetting,
-      SampleParam
+      SampleParam,
+      importDialog
     },
     data() {
       return {
+        moudleName : "mainProduceStep",
         // 表格列配置
         columns: [
           {
@@ -190,7 +199,7 @@
               return ['生效', '失效'][_row.status];
             }
           },
-     
+
           {
             prop: 'sort',
             label: '排序',
@@ -199,8 +208,8 @@
             align: 'center',
             minWidth: 110
           },
-       
-  
+
+
           {
             columnKey: 'action',
             label: '操作',
@@ -348,6 +357,9 @@
 
       close(done) {
         this.sampleShow = false;
+      },
+      uploadFile () {
+        this.$refs.importDialogRef.open();
       }
     }
   };

+ 40 - 2
src/views/workforceManagement/team/components/userTable.vue

@@ -5,6 +5,7 @@
       :needPage="false"
       :columns="columns"
       :datasource="datasource"
+      :selection.sync="selection"
       cache-key="systemRoleTable21"
     >
       <!-- 表头工具栏 -->
@@ -18,6 +19,16 @@
         >
           新增
         </el-button>
+
+        <el-button
+          size="small"
+          @click="handAllDel"
+          icon="el-icon-delete"
+          type="danger"
+        >
+          删除
+        </el-button>
+
       </template>
       <!-- 操作列 -->
       <template v-slot:action="{ row }">
@@ -59,12 +70,20 @@
     data () {
       return {
         columns: [
+        {
+          columnKey: 'selection',
+            type: 'selection',
+            width: 45,
+            align: 'center',
+            fixed: 'left'
+          },
+
           {
             width: 45,
             type: 'index',
             columnKey: 'index',
             align: 'center',
-            fixed:'left'
+          
           },
           {
             prop: 'name',
@@ -91,7 +110,8 @@
         ],
         datasource: [],
 
-        deleteUserIds: []
+        deleteUserIds: [],
+        selection: []
       };
     },
     methods: {
@@ -104,6 +124,24 @@
         }
 
       },
+
+      handAllDel() {
+        console.log(this.selection);
+        console.log(this.datasource)
+
+        this.selection.forEach((e) => {
+          this.datasource.forEach((f,i) => {
+            if(e.id == f.id){
+              this.datasource.splice(i, 1);
+              this.deleteUserIds.push((f.id));
+              this.$emit('deleteIds', this.deleteUserIds);
+            }
+
+          })
+        });
+
+      },
+
       handlAdd () {
         this.$refs.staffSelection.open(
           JSON.parse(JSON.stringify(this.datasource))

+ 1 - 1
vue.config.js

@@ -31,7 +31,7 @@ module.exports = {
     proxy: {
       // 当我们的本地的请求 有/api的时候,就会代理我们的请求地址向另外一个服务器发出请求
       '/api': {
-        // target: 'http://124.71.68.31:50001',
+        // target: 'http://192.168.1.124:50001',
         // target: 'http://192.168.1.147:18086',
         target: 'http://192.168.1.125:18086',
         changeOrigin: true, // 只有这个值为true的情况下 才表示开启跨域