Просмотр исходного кода

资产台账所有页面详情新增'生产记录',运维管理新增’运行记录‘。

yijing 1 год назад
Родитель
Сommit
649c3b5db7
29 измененных файлов с 3268 добавлено и 77 удалено
  1. 178 0
      src/api/produceOrder/index.js
  2. 10 6
      src/views/ledgerAssets/boat/components/boat-list.vue
  3. 9 3
      src/views/ledgerAssets/boat/detail.vue
  4. 2 2
      src/views/ledgerAssets/components/details/inventory.vue
  5. 389 0
      src/views/ledgerAssets/components/details/produceOrder/produce-order.vue
  6. 5 1
      src/views/ledgerAssets/equipment/components/detailedList.vue
  7. 5 1
      src/views/ledgerAssets/equipment/detail.vue
  8. 5 8
      src/views/ledgerAssets/equipment/detailsPop.vue
  9. 10 6
      src/views/ledgerAssets/meter/components/equipment-list.vue
  10. 5 2
      src/views/ledgerAssets/meter/detail.vue
  11. 31 9
      src/views/ledgerAssets/mould/components/mould-list.vue
  12. 9 3
      src/views/ledgerAssets/mould/detail.vue
  13. 3 4
      src/views/ledgerAssets/mould/edit.vue
  14. 10 6
      src/views/ledgerAssets/office/components/data-list.vue
  15. 4 1
      src/views/ledgerAssets/office/detail.vue
  16. 3 2
      src/views/ledgerAssets/sparepart/components/sparepart-list.vue
  17. 9 3
      src/views/ledgerAssets/sparepart/detail.vue
  18. 11 7
      src/views/ledgerAssets/turnoverCar/components/turnovercar-list.vue
  19. 9 3
      src/views/ledgerAssets/turnoverCar/detail.vue
  20. 5 5
      src/views/ledgerAssets/turnoverDisks/components/equipment-list.vue
  21. 5 2
      src/views/ledgerAssets/turnoverDisks/detail.vue
  22. 25 3
      src/views/maintenance/components/programRulesDialog.vue
  23. 70 0
      src/views/maintenance/runRecord/index.vue
  24. 187 0
      src/views/maintenance/runRecord/plan/components/plan-search.vue
  25. 737 0
      src/views/maintenance/runRecord/plan/details.vue
  26. 271 0
      src/views/maintenance/runRecord/plan/index.vue
  27. 177 0
      src/views/maintenance/runRecord/workOrder/components/work-search.vue
  28. 798 0
      src/views/maintenance/runRecord/workOrder/details.vue
  29. 286 0
      src/views/maintenance/runRecord/workOrder/index.vue

+ 178 - 0
src/api/produceOrder/index.js

@@ -0,0 +1,178 @@
+import request from '@/utils/request';
+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));
+}
+/**
+ * 分页
+ */
+export async function getPage(params) {
+  const res = await request.post('/mes/workorder/page', params);
+  if (res.data.code == 0) {
+    return res.data.data;
+  }
+  return Promise.reject(new Error(res.data.message));
+}
+/**
+ * 新增
+ */
+export async function save(data) {
+  const res = await request.post('/mes/workorder/save', data);
+  if (res.data.code == 0) {
+    return res.data.data;
+  }
+  return Promise.reject(new Error(res.data.message));
+}
+/**
+ * 修改
+ */
+export async function update(data) {
+  const res = await request.put('/mes/workorder/update', data);
+  if (res.data.code == 0) {
+    return res.data.data;
+  }
+  return Promise.reject(new Error(res.data.message));
+}
+
+// 批量完结
+export async function batchCompletion(params) {
+  const res = await request.post('/mes/workorder/batchCompletion', params);
+  if (res.data.code == 0) {
+    return res.data.data;
+  }
+  return Promise.reject(new Error(res.data.message));
+}
+
+// 取消完结
+export async function cancelCompletion(id) {
+  const res = await request.get(`/mes/workorder/cancelCompletion/${id}`);
+  if (res.data.code == 0) {
+    return res.data.data;
+  }
+  return Promise.reject(new Error(res.data.message));
+}
+// 领料保存
+export async function batchSave(data) {
+  const res = await request.post(`/mes/pickorder/batchSave`, data);
+  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(`/mes/workorder/getById/${id}`);
+  if (res.data.code == 0) {
+    return res.data.data;
+  }
+  return Promise.reject(new Error(res.data.message));
+}
+
+// 拆分
+export async function splitWork(params) {
+  const res = await request.post(`/mes/workorder/splitBatch`, params);
+  if (res.data.code == 0) {
+    return res.data.data;
+  }
+  return Promise.reject(new Error(res.data.message));
+}
+// 报工
+export async function report(params) {
+  const res = await request.post(`/mes/workreport/report`, params);
+  if (res.data.code == 0) {
+    return res.data.data;
+  }
+  return Promise.reject(new Error(res.data.message));
+}
+// 报工 统计数据
+export async function reportCount(params) {
+  const res = await request.get(`/mes/workreport/count`, { params });
+  if (res.data.code == 0) {
+    return res.data.data;
+  }
+  return Promise.reject(new Error(res.data.message));
+}
+
+// 详情页-tab列表
+export async function reportPage(data) {
+  const res = await request.post('/mes/workreport/page', data);
+  if (res.data.code == 0) {
+    return res.data.data;
+  }
+  return Promise.reject(new Error(res.data.message));
+}
+// 打印详情页-tab列表
+export async function printWorkOrderInfo(workOrderId) {
+  const res = await request.get(
+    `/mes/workreport/printWorkOrderInfo/${workOrderId}`
+  );
+  if (res.data.code == 0) {
+    return res.data.data;
+  }
+  return Promise.reject(new Error(res.data.message));
+}
+
+// 获取详情页数据
+export async function getInfoById(id) {
+  const res = await request.get(`/mes/workreport/getById/${id}`);
+  if (res.data.code == 0) {
+    return res.data.data;
+  }
+  return Promise.reject(new Error(res.data.message));
+}
+
+// 冲销接口
+export async function writeOffWork(data) {
+  const res = await request.post(`/mes/workreport/writeOff`, data);
+  if (res.data.code == 0) {
+    return res.data.data;
+  }
+  return Promise.reject(new Error(res.data.message));
+}
+//包装要求
+export async function getPackageList(code) {
+  const res = await request.get(`/aps/workorder/getPackageList/${code}`);
+  if (res.data.code == 0) {
+    return res.data.data;
+  }
+  return Promise.reject(new Error(res.data.message));
+}
+//根据工序ID查询设备信息
+export async function getDeviceByTaskId(params) {
+  const res = await request.get(
+    `/main/producetask/getDeviceByTaskId/${params.taskId}/${params.rootCategoryLevelId}`
+  );
+  if (res.data.code == 0) {
+    return res.data.data;
+  }
+  return Promise.reject(new Error(res.data.message));
+}
+
+// 获取槽数
+export async function getSoltNum(id) {
+  const res = await request.get(`/main/categorypallet/getByCategoryId/${id}`);
+  if (res.data.code == 0) {
+    return res.data.data;
+  }
+  return Promise.reject(new Error(res.data.message));
+}
+
+// 打印前查询
+export async function queryPrint(data) {
+  const res = await request.post(`/mes/workorder/queryPrint`, data);
+  if (res.data.code == 0) {
+    return res.data.data;
+  }
+  return Promise.reject(new Error(res.data.message));
+}
+// 修改优先级
+export async function updatePriority(data) {
+  const res = await request.post(`/mes/workorder/updatePriority`, data);
+  if (res.data.code == 0) {
+    return res.data.data;
+  }
+  return Promise.reject(new Error(res.data.message));
+}

+ 10 - 6
src/views/ledgerAssets/boat/components/boat-list.vue

@@ -71,7 +71,11 @@
   import printSr from '@/views/ledgerAssets/components/printSr';
   import printTg from '@/views/ledgerAssets/components/printTg';
   import { getByCode } from '@/api/system/dictionary-data';
-  import { businessStatus, networkStatus,sourceStatus } from '@/utils/dict/warehouse';
+  import {
+    businessStatus,
+    networkStatus,
+    sourceStatus
+  } from '@/utils/dict/warehouse';
   import BoatSearch from './boat-search.vue';
   import {
     getBoatList,
@@ -189,9 +193,8 @@
             label: '生命周期',
             showOverflowTooltip: true,
             minWidth: 110,
-            formatter:(_row)=>{
-              return sourceStatus[_row.lifeCycle]
-
+            formatter: (_row) => {
+              return sourceStatus[_row.lifeCycle];
             }
           },
           {
@@ -345,11 +348,12 @@
       },
 
       // 跳转到详情页
-      details({ id }) {
+      details({ id, code }) {
         this.$router.push({
           path: '/ledgerAssets/boat/detail',
           query: {
-            id
+            id,
+            code
           }
         });
       },

+ 9 - 3
src/views/ledgerAssets/boat/detail.vue

@@ -31,6 +31,7 @@
         <component
           :is="activeComp"
           :rowId="rowId"
+          :code="code"
           :showTitle="false"
         ></component>
       </div>
@@ -46,6 +47,7 @@
   import inventory from '../components/details/inventory.vue';
   import pointInspection from '../components/details/point-inspection.vue';
   import internet from '../components/details/internet.vue';
+  import produceOrder from '../components/details/produceOrder/produce-order.vue';
   export default {
     components: {
       baseInfo,
@@ -54,7 +56,8 @@
       repair,
       inventory,
       malfunction,
-      internet
+      internet,
+      produceOrder
     },
     data() {
       return {
@@ -67,14 +70,17 @@
           { key: 'repair', name: '维修记录' },
           { key: 'malfunction', name: '故障记录' },
           { key: 'inventory', name: '盘点记录' },
-          { key: 'internet', name: '物联数据' }
+          { key: 'internet', name: '物联数据' },
+          { key: 'produceOrder', name: '生产记录' }
           // // { key: "InternetRecord", name: "物联记录" },
         ],
-        rowId: null
+        rowId: null,
+        code: null
       };
     },
     created() {
       this.rowId = this.$route.query.id;
+      this.code = this.$route.query.code;
       // const Array = [
       //   {key:'参数1',value:'值1'},
       //   {key:'参数2',value:'值2'},

+ 2 - 2
src/views/ledgerAssets/components/details/inventory.vue

@@ -2,9 +2,9 @@
   <div class="wrapper">
     <!-- 盘点记录 -->
     <div class="basic-details" id="check">
-      <div class="basic-details-title">
+      <!-- <div class="basic-details-title">
         <span class="border-span"> 盘点记录</span>
-      </div>
+      </div> -->
       <el-table
         :data="tableData"
         border

+ 389 - 0
src/views/ledgerAssets/components/details/produceOrder/produce-order.vue

@@ -0,0 +1,389 @@
+<template>
+  <div>
+    <el-card shadow="never" v-loading="loading">
+      <el-tabs v-model="activeName" type="card" @tab-click="changeActive">
+        <el-tab-pane label="未完成工单" name="first"></el-tab-pane>
+        <el-tab-pane label="已完成工单" name="second"></el-tab-pane>
+      </el-tabs>
+      <!-- 数据表格 -->
+      <ele-pro-table
+        ref="table"
+        :key="activeName"
+        :columns="newColumns"
+        :datasource="datasource"
+        row-key="id"
+        :cache-key="`${activeName}produceOrderTable`"
+        :selection.sync="selection"
+        @sort-change="onSortChange"
+        autoAmendPage
+        :parse-data="parseData"
+      >
+        <template v-slot:formingNum="{ row }">
+          <span> {{ row.formingNum }} {{ row.unit }} </span>
+        </template>
+
+        <template v-slot:formingWeight="{ row }">
+          <span> {{ row.formingNum }} {{ row.weightUnit }} </span>
+        </template>
+
+        <template v-slot:status="{ row }">
+          <span :class="{ 'ele-text-danger': row.status == 3 }">
+            {{ statusFormatter(row.status) }}
+          </span>
+        </template>
+      </ele-pro-table>
+    </el-card>
+  </div>
+</template>
+
+<script>
+  import { getPage, fieldModel } from '@/api/produceOrder/index.js';
+  export default {
+    props: ['code'],
+    components: {},
+    data() {
+      return {
+        activeName: 'first',
+
+        // 加载状态
+        loading: false,
+        pageType: 'add',
+        dialogTitle: '',
+        isBindPlan: false,
+        statusOpt: {
+          first: [
+            { label: '所有状态', value: '5,4' },
+            { label: '待生产', value: '4' },
+            { label: '生产中', value: '5' }
+            // { label: '已延期', value: '7' }
+          ],
+          second: [{ label: '已完成', value: '6' }]
+        },
+        planType: [
+          { label: '所有计划类型', value: null },
+          { label: '内销计划', value: '1' },
+          { label: '外销计划', value: '2' },
+          { label: '预制计划', value: '3' }
+        ],
+        selection: [],
+        newColumns: []
+      };
+    },
+    computed: {
+      // 表格列配置
+      columns() {
+        const opt = {
+          first: [
+            // {
+            //   prop: 'deliveryTime',
+            //   label: '预测交货日期',
+            //   align: 'center',
+            //   showOverflowTooltip: true,
+            //   minWidth: 110
+            // }
+          ],
+          second: [
+            {
+              prop: 'completeTime',
+              label: '完成时间',
+              align: 'center'
+            },
+            {
+              prop: 'cycle',
+              label: '生产周期',
+              align: 'center'
+            }
+          ]
+        };
+
+        return [
+          {
+            width: 45,
+            type: 'selection',
+            columnKey: 'selection',
+            align: 'center',
+            fixed: 'left'
+          },
+
+          {
+            prop: 'batchNo',
+            label: '批次号',
+            align: 'center',
+            minWidth: 130
+          },
+
+          {
+            prop: 'code',
+            label: '生产工单号',
+            align: 'center',
+            minWidth: 110
+          },
+          // {
+          //   prop: 'originalCode',
+          //   label: '原始工单号',
+          //   align: 'center',
+          //   minWidth: 110
+          // },
+
+          // {
+          //   slot: 'QRcode',
+          //   label: '二维码',
+          //   align: 'center',
+          //   minWidth: 110
+          // },
+
+          {
+            prop: 'productionPlanCode',
+            label: '计划编号',
+            align: 'center',
+            minWidth: 110
+          },
+          {
+            prop: 'planType',
+            label: '计划类型',
+            align: 'center',
+            formatter: (row) => {
+              const obj = this.planType.find((i) => i.value == row.planType);
+              return obj && obj.label;
+            }
+          },
+          {
+            prop: 'produceRoutingName',
+            label: '工艺路线',
+            align: 'center'
+          },
+          {
+            prop: 'productCode',
+            label: '编码',
+            align: 'center'
+          },
+          {
+            prop: 'productName',
+            label: '名称',
+            align: 'center'
+          },
+          {
+            prop: 'brandNo',
+            label: '牌号',
+            align: 'center'
+          },
+          {
+            prop: 'model',
+            label: '型号',
+            align: 'center'
+          },
+
+          {
+            prop: 'priority',
+            label: '优先级',
+            align: 'center',
+            minWidth: 120,
+            slot: 'priority',
+            sortable: 'custom'
+          },
+
+          {
+            prop: 'formingNum',
+            label: '要求生产数量',
+            align: 'center',
+            slot: 'formingNum',
+            showOverflowTooltip: true,
+            minWidth: 110
+          },
+          {
+            prop: 'formingWeight',
+            label: '要求生产重量',
+            slot: 'formingWeight',
+            align: 'center',
+            showOverflowTooltip: true,
+            minWidth: 110
+          },
+          {
+            prop: 'formedNum',
+            label: '已生产数量',
+            align: 'center',
+            showOverflowTooltip: true,
+            minWidth: 110
+          },
+          {
+            prop: 'formedWeight',
+            label: '已生产重量',
+            align: 'center',
+            showOverflowTooltip: true,
+            minWidth: 110
+          },
+          {
+            prop: 'planStartTime',
+            label: '计划开始时间',
+            align: 'center',
+            showOverflowTooltip: true,
+            minWidth: 110
+          },
+          {
+            prop: 'planCompleteTime',
+            label: '计划结束时间',
+            align: 'center',
+            showOverflowTooltip: true,
+            minWidth: 110
+          },
+          {
+            prop: 'startTime',
+            label: '实际开始时间',
+            align: 'center',
+            showOverflowTooltip: true,
+            minWidth: 110
+          },
+
+          ...opt[this.activeName],
+          {
+            prop: 'createTime',
+            label: '创建时间',
+            align: 'center',
+            showOverflowTooltip: true,
+            minWidth: 110
+          },
+          {
+            slot: 'status',
+            label: '状态',
+            align: 'center',
+            formatter: (row) => {
+              const obj = this.statusOpt[this.activeName].find(
+                (i) => i.value == row.status
+              );
+              return obj && obj.label;
+            }
+          },
+
+          {
+            prop: 'teamName',
+            label: '班组',
+            align: 'center',
+            showOverflowTooltip: true
+          }
+        ];
+      },
+
+      clientEnvironmentId() {
+        return this.$store.state.user.info.clientEnvironmentId;
+      }
+    },
+    created() {
+      this.getFieldModel();
+    },
+    methods: {
+      statusFormatter(status) {
+        const obj = this.statusOpt[this.activeName].find(
+          (i) => i.value == status
+        );
+
+        return obj && obj.label;
+      },
+      /* 表格数据源 */
+      async datasource({ page, limit, where, order }) {
+        let res = await getPage({
+          ...where,
+          ...order,
+          pageNum: page,
+          size: limit,
+          status: this.statusOpt[this.activeName][0].value,
+          deviceCode: this.code,
+          statusList: (
+            where.status || this.statusOpt[this.activeName][0].value
+          ).split(','),
+          workOrderType: 1,
+          ...this.sort
+        });
+
+        return res;
+      },
+      changeActive(tab) {
+        this.activeName = tab.name;
+        if (this.activeName === 'second') {
+          let aaa = {
+            status: this.statusOpt[this.activeName][0].value,
+            statusList: this.statusOpt[this.activeName][0].value.split(',')
+          };
+          this.$refs.table.reload(aaa);
+        } else {
+          this.reload();
+        }
+      },
+
+      reload(where = {}) {
+        this.$nextTick(() => {
+          where.statusList = (
+            where.status || this.statusOpt[this.activeName][0].value
+          ).split(',');
+          this.$refs.table.reload({ page: 1, where });
+        });
+      },
+      onSortChange(e) {
+        let sort = {
+          orderBy: e.order,
+          sortName: e.prop
+        };
+        this.sort = sort;
+        this.reload();
+      },
+      flattenArray(arr) {
+        var result = []; // 存放结果的数组
+        for (let i = 0; i < arr.length; i++) {
+          if (Array.isArray(arr[i].subWorkOrder)) {
+            let _arr = [];
+            _arr = _arr.concat(arr[i].subWorkOrder);
+            delete arr[i].subWorkOrder;
+            result.push(arr[i]);
+            result.push(..._arr);
+          } else {
+            result.push(arr[i]);
+          }
+        }
+
+        return result;
+      },
+
+      /* 数据转为树形结构 */
+      parseData(data) {
+        return {
+          ...data,
+          list: this.$util.toTreeData({
+            data: data.list,
+            count: data.total,
+            idField: 'code',
+            parentIdField: 'originalCode'
+          })
+        };
+      },
+
+      /* 数据转为树形结构 */
+      createSuccess() {
+        this.reload();
+      },
+      getFieldModel() {
+        fieldModel({ fieldModel: 't_main_category' }).then((res) => {
+          let newRes = res.map((m) => {
+            return {
+              prop: 'extField.' + m.prop,
+              label: m.label,
+              align: 'center',
+              showOverflowTooltip: true
+            };
+          });
+
+          this.newColumns = [...this.columns, ...newRes];
+
+          this.$forceUpdate();
+        });
+      },
+
+      handleTabChange() {
+        this.$refs.searchRef.reset();
+      }
+    }
+  };
+</script>
+<style lang="scss" scoped>
+  ::v-deep .el-card__body {
+    padding: 0px !important;
+  }
+</style>

+ 5 - 1
src/views/ledgerAssets/equipment/components/detailedList.vue

@@ -353,7 +353,11 @@
         });
       },
       handlePrinting() {
-        this.$refs.printRef.open(this.checkRadioData);
+        if (this.checkRadioData.length > 0) {
+          this.$refs.printRef.open(this.checkRadioData);
+        } else {
+          this.$message.warning('请选择数据!');
+        }
       },
       // 全选
       changeSelectAll(arr) {

+ 5 - 1
src/views/ledgerAssets/equipment/detail.vue

@@ -50,6 +50,7 @@
   import inventory from '../components/details/inventory.vue';
   import pointInspection from '../components/details/point-inspection.vue';
   import internet from '../components/details/internet.vue';
+  import produceOrder from '../components/details/produceOrder/produce-order.vue';
   export default {
     components: {
       baseInfo,
@@ -58,6 +59,7 @@
       maintain,
       repair,
       inventory,
+      produceOrder,
       // InternetRecord,
       malfunction,
       internet
@@ -76,7 +78,9 @@
           { key: 'repair', name: '维修记录' },
           { key: 'malfunction', name: '故障记录' },
           { key: 'inventory', name: '盘点记录' },
-          { key: 'internet', name: '物联数据' }
+          { key: 'internet', name: '物联数据' },
+          { key: 'produceOrder', name: '生产记录' }
+          // { key: 'healthRecord', name: '运行状况记录' }
           // // { key: "InternetRecord", name: "物联记录" },
         ]
       };

+ 5 - 8
src/views/ledgerAssets/equipment/detailsPop.vue

@@ -15,9 +15,9 @@
             v-model="currentNodeData.bomType"
             @change="bomChange"
           >
-            <el-radio-button :label="4">EBOM </el-radio-button>
+            <!-- <el-radio-button :label="4">EBOM </el-radio-button> -->
             <el-radio-button :label="1">PBOM </el-radio-button>
-            <el-radio-button
+            <!-- <el-radio-button
               :label="2"
               v-if="
                 searchObj.isProduct ||
@@ -32,7 +32,7 @@
                 [1, 9].includes(searchObj.rootPathIdParent)
               "
               >ABOM
-            </el-radio-button>
+            </el-radio-button> -->
           </el-radio-group>
         </div>
         <div>
@@ -154,11 +154,7 @@
               :description="
                 currentNodeData.bomType == 1
                   ? 'PBOM 暂无数据,请先新建'
-                  : currentNodeData.bomType == 2
-                  ? 'MBOM 暂无数据,请先新建'
-                  : currentNodeData.bomType == 3
-                  ? 'ABOM 暂无数据,请先新建'
-                  : 'EBOM 暂无数据,请先新建'
+                  : '暂无数据'
               "
             ></el-empty>
           </template>
@@ -247,6 +243,7 @@
 
     methods: {
       open(row) {
+        console.log(row, 'rowrowrowrowrowrowrowrowrow');
         this.searchObj = row;
 
         if (Object.prototype.hasOwnProperty.call(row, 'isWt') && row.isWt) {

+ 10 - 6
src/views/ledgerAssets/meter/components/equipment-list.vue

@@ -95,7 +95,11 @@
   import printSr from '@/views/ledgerAssets/components/printSr';
   import printTg from '@/views/ledgerAssets/components/printTg';
   import { getByCode } from '@/api/system/dictionary-data';
-  import { businessStatus, networkStatus,sourceStatus } from '@/utils/dict/warehouse';
+  import {
+    businessStatus,
+    networkStatus,
+    sourceStatus
+  } from '@/utils/dict/warehouse';
   import EquipmentSearch from './equipment-search.vue';
   import DialogMoveto from './DialogMoveTo.vue';
   import {
@@ -233,9 +237,8 @@
             label: '生命周期',
             showOverflowTooltip: true,
             minWidth: 110,
-            formatter:(_row)=>{
-              return sourceStatus[_row.lifeCycle]
-
+            formatter: (_row) => {
+              return sourceStatus[_row.lifeCycle];
             }
           },
           {
@@ -332,11 +335,12 @@
         }
       },
       // 跳转到详情页
-      details({ id }) {
+      details({ id, code }) {
         this.$router.push({
           path: '/ledgerAssets/meter/detail',
           query: {
-            id
+            id,
+            code
           }
         });
       },

+ 5 - 2
src/views/ledgerAssets/meter/detail.vue

@@ -50,6 +50,7 @@
   import inventory from '../components/details/inventory.vue';
   import pointInspection from '../components/details/point-inspection.vue';
   import internet from '../components/details/internet.vue';
+  import produceOrder from '../components/details/produceOrder/produce-order.vue';
   export default {
     components: {
       baseInfo,
@@ -60,7 +61,8 @@
       inventory,
       // InternetRecord,
       malfunction,
-      internet
+      internet,
+      produceOrder
     },
     data() {
       return {
@@ -76,7 +78,8 @@
           { key: 'repair', name: '维修记录' },
           { key: 'malfunction', name: '故障记录' },
           { key: 'inventory', name: '盘点记录' },
-          { key: 'internet', name: '物联数据' }
+          { key: 'internet', name: '物联数据' },
+          { key: 'produceOrder', name: '生产记录' }
           // // { key: "InternetRecord", name: "物联记录" },
         ]
       };

+ 31 - 9
src/views/ledgerAssets/mould/components/mould-list.vue

@@ -83,11 +83,13 @@
         >
           编辑
         </el-link>
+        <el-link type="primary" @click="handelBOM(row)">BOM</el-link>
       </template>
     </ele-pro-table>
     <print ref="printRef"></print>
     <printSr ref="printSrRef"></printSr>
     <printTg ref="printTgRef"></printTg>
+    <BomDetailsPop ref="bomDrawer"></BomDetailsPop>
   </div>
 </template>
 
@@ -96,7 +98,11 @@
   import printSr from '@/views/ledgerAssets/components/printSr';
   import printTg from '@/views/ledgerAssets/components/printTg';
   import { getByCode } from '@/api/system/dictionary-data';
-  import { businessStatus, networkStatus,sourceStatus } from '@/utils/dict/warehouse';
+  import {
+    businessStatus,
+    networkStatus,
+    sourceStatus
+  } from '@/utils/dict/warehouse';
   import MouldSearch from './mould-search.vue';
   import { getAssetList, downloadAsset } from '@/api/ledgerAssets';
   import dictMixins from '@/mixins/dictMixins';
@@ -108,8 +114,11 @@
   } from '@/config/setting';
   import { download } from '@/utils/file';
   import { getToken, setToken } from '@/utils/token-util';
+
+  import BomDetailsPop from '@/views/ledgerAssets/equipment/detailsPop.vue';
+
   export default {
-    components: { MouldSearch, print, printSr, printTg },
+    components: { MouldSearch, print, printSr, printTg, BomDetailsPop },
     mixins: [dictMixins],
     props: {
       // 类别id
@@ -208,11 +217,9 @@
             label: '生命周期',
             showOverflowTooltip: true,
             minWidth: 110,
-            formatter:(_row)=>{
-              return sourceStatus[_row.lifeCycle]
-
+            formatter: (_row) => {
+              return sourceStatus[_row.lifeCycle];
             }
-            
           },
           {
             prop: 'level',
@@ -280,7 +287,7 @@
             columnKey: 'action',
             slot: 'action',
             label: '操作',
-            minWidth: 100,
+            minWidth: 120,
             fixed: 'right'
           }
         ],
@@ -358,11 +365,12 @@
       },
 
       // 跳转到详情页
-      details({ id }) {
+      details({ id, code }) {
         this.$router.push({
           path: '/ledgerAssets/mould/detail',
           query: {
-            id
+            id,
+            code
           }
         });
       },
@@ -397,6 +405,20 @@
           download(res.data, '模具台账导出数据');
         });
         // downloadAsset(params, '模具台账导出数据');
+      },
+      handelBOM(row) {
+        console.log(row, '111111111111111');
+        let rowData = {
+          categoryId: row.category.id,
+          categoryName: row.categoryName,
+          code: row.code,
+          versions: row.versions,
+          rootPathIdParent: row.category.categoryLevelPathIdParent,
+          isProduct: true,
+          bomType: '1',
+          isTemp: row.isTemp
+        };
+        this.$refs.bomDrawer.open(rowData);
       }
     },
     watch: {

+ 9 - 3
src/views/ledgerAssets/mould/detail.vue

@@ -32,6 +32,7 @@
         <component
           :is="activeComp"
           :rowId="rowId"
+          :code="code"
           :showTitle="false"
         ></component>
       </div>
@@ -47,6 +48,7 @@
   import inventory from '../components/details/inventory.vue';
   import pointInspection from '../components/details/point-inspection.vue';
   import internet from '../components/details/internet.vue';
+  import produceOrder from '../components/details/produceOrder/produce-order.vue';
   export default {
     components: {
       baseInfo,
@@ -55,7 +57,8 @@
       repair,
       inventory,
       malfunction,
-      internet
+      internet,
+      produceOrder
     },
     data() {
       return {
@@ -68,15 +71,18 @@
           { key: 'repair', name: '维修记录' },
           { key: 'malfunction', name: '故障记录' },
           { key: 'inventory', name: '盘点记录' },
-          { key: 'internet', name: '物联数据' }
+          { key: 'internet', name: '物联数据' },
+          { key: 'produceOrder', name: '生产记录' }
           // // { key: "InternetRecord", name: "物联记录" },
         ],
-        rowId: null
+        rowId: null,
+        code: null
       };
     },
 
     created() {
       this.rowId = this.$route.query.id;
+      this.code = this.$route.query.code;
     }
   };
 </script>

+ 3 - 4
src/views/ledgerAssets/mould/edit.vue

@@ -170,7 +170,7 @@
           code: '',
           name: '',
           productTime: '',
-          workstation:''
+          workstation: ''
         },
         rules: {
           name: [
@@ -292,9 +292,8 @@
         this.form = data;
         this.form.category = res;
         this.basicInfo = data;
-        this.form.rootCategoryLevelId = this.basicInfo.categoryLevelPathId
-          .split(',')[0]
-          .replace('[', '');
+        this.form.rootCategoryLevelId =
+          this.basicInfo.categoryLevelPathIdParent;
         this.form.categoryId = this.basicInfo.id;
         this.form.name = this.basicInfo.name;
         this.form.code = data.code; //Date.now(); //res.data[0].onlyCode;

+ 10 - 6
src/views/ledgerAssets/office/components/data-list.vue

@@ -96,7 +96,11 @@
   import printSr from '@/views/ledgerAssets/components/printSr';
   import printTg from '@/views/ledgerAssets/components/printTg';
   import { getByCode } from '@/api/system/dictionary-data';
-  import { businessStatus, networkStatus,sourceStatus } from '@/utils/dict/warehouse';
+  import {
+    businessStatus,
+    networkStatus,
+    sourceStatus
+  } from '@/utils/dict/warehouse';
   import UserSearch from './user-search.vue';
   import { getAssetList, downloadAsset } from '@/api/ledgerAssets';
   import dictMixins from '@/mixins/dictMixins';
@@ -224,9 +228,8 @@
             label: '生命周期',
             showOverflowTooltip: true,
             minWidth: 110,
-            formatter:(_row)=>{
-              return sourceStatus[_row.lifeCycle]
-
+            formatter: (_row) => {
+              return sourceStatus[_row.lifeCycle];
             }
           },
           {
@@ -373,11 +376,12 @@
       },
 
       // 跳转到详情页
-      details({ id }) {
+      details({ id, code }) {
         this.$router.push({
           path: '/ledgerAssets/office/detail',
           query: {
-            id
+            id,
+            code
           }
         });
       },

+ 4 - 1
src/views/ledgerAssets/office/detail.vue

@@ -13,6 +13,7 @@
         <component
           :is="activeComp"
           :rowId="rowId"
+          :code="code"
           :showTitle="false"
         ></component>
       </div>
@@ -30,12 +31,14 @@
       return {
         activeComp: 'baseInfo',
         tabOptions: [{ key: 'baseInfo', name: '基本信息' }],
-        rowId: null
+        rowId: null,
+        code: null
       };
     },
 
     created() {
       this.rowId = this.$route.query.id;
+      this.code = this.$route.query.code;
     }
   };
 </script>

+ 3 - 2
src/views/ledgerAssets/sparepart/components/sparepart-list.vue

@@ -403,11 +403,12 @@
       },
 
       // 跳转到详情页
-      details({ id }) {
+      details({ id, code }) {
         this.$router.push({
           path: '/ledgerAssets/sparepart/detail',
           query: {
-            id
+            id,
+            code
           }
         });
       },

+ 9 - 3
src/views/ledgerAssets/sparepart/detail.vue

@@ -32,6 +32,7 @@
         <component
           :is="activeComp"
           :rowId="rowId"
+          :code="code"
           :showTitle="false"
         ></component>
       </div>
@@ -47,6 +48,7 @@
   import inventory from '../components/details/inventory.vue';
   import pointInspection from '../components/details/point-inspection.vue';
   import internet from '../components/details/internet.vue';
+  import produceOrder from '../components/details/produceOrder/produce-order.vue';
   export default {
     components: {
       baseInfo,
@@ -55,7 +57,8 @@
       repair,
       inventory,
       malfunction,
-      internet
+      internet,
+      produceOrder
     },
     data() {
       return {
@@ -68,15 +71,18 @@
           { key: 'repair', name: '维修记录' },
           { key: 'malfunction', name: '故障记录' },
           { key: 'inventory', name: '盘点记录' },
-          { key: 'internet', name: '物联数据' }
+          { key: 'internet', name: '物联数据' },
+          { key: 'produceOrder', name: '生产记录' }
           // // { key: "InternetRecord", name: "物联记录" },
         ],
-        rowId: null
+        rowId: null,
+        code: null
       };
     },
 
     created() {
       this.rowId = this.$route.query.id;
+      this.code = this.$route.query.code;
     }
   };
 </script>

+ 11 - 7
src/views/ledgerAssets/turnoverCar/components/turnovercar-list.vue

@@ -5,7 +5,7 @@
       @search="reload"
       :networkCounts="networkCounts"
     >
-    </turnovercar-search>
+    </turnovercar-Search>
     <!-- 数据表格 -->
     <ele-pro-table
       ref="table"
@@ -84,7 +84,11 @@
   import printSr from '@/views/ledgerAssets/components/printSr';
   import printTg from '@/views/ledgerAssets/components/printTg';
   import { getByCode } from '@/api/system/dictionary-data';
-  import { businessStatus, networkStatus,sourceStatus } from '@/utils/dict/warehouse';
+  import {
+    businessStatus,
+    networkStatus,
+    sourceStatus
+  } from '@/utils/dict/warehouse';
   import TurnovercarSearch from './turnovercar-search.vue';
   import { getAssetList, downloadAsset } from '@/api/ledgerAssets';
   import dictMixins from '@/mixins/dictMixins';
@@ -199,9 +203,8 @@
             label: '生命周期',
             showOverflowTooltip: true,
             minWidth: 110,
-            formatter:(_row)=>{
-              return sourceStatus[_row.lifeCycle]
-
+            formatter: (_row) => {
+              return sourceStatus[_row.lifeCycle];
             }
           },
           {
@@ -348,11 +351,12 @@
       },
 
       // 跳转到详情页
-      details({ id }) {
+      details({ id, code }) {
         this.$router.push({
           path: '/ledgerAssets/turnoverCar/detail',
           query: {
-            id
+            id,
+            code
           }
         });
       },

+ 9 - 3
src/views/ledgerAssets/turnoverCar/detail.vue

@@ -32,6 +32,7 @@
         <component
           :is="activeComp"
           :rowId="rowId"
+          :code="code"
           :showTitle="false"
         ></component>
       </div>
@@ -47,6 +48,7 @@
   import inventory from '../components/details/inventory.vue';
   import pointInspection from '../components/details/point-inspection.vue';
   import internet from '../components/details/internet.vue';
+  import produceOrder from '../components/details/produceOrder/produce-order.vue';
   export default {
     components: {
       baseInfo,
@@ -55,7 +57,8 @@
       repair,
       inventory,
       malfunction,
-      internet
+      internet,
+      produceOrder
     },
     data() {
       return {
@@ -68,15 +71,18 @@
           { key: 'repair', name: '维修记录' },
           { key: 'malfunction', name: '故障记录' },
           { key: 'inventory', name: '盘点记录' },
-          { key: 'internet', name: '物联数据' }
+          { key: 'internet', name: '物联数据' },
+          { key: 'produceOrder', name: '生产记录' }
           // // { key: "InternetRecord", name: "物联记录" },
         ],
-        rowId: null
+        rowId: null,
+        code: null
       };
     },
 
     created() {
       this.rowId = this.$route.query.id;
+      this.code = this.$route.query.code;
     }
   };
 </script>

+ 5 - 5
src/views/ledgerAssets/turnoverDisks/components/equipment-list.vue

@@ -218,9 +218,8 @@
             label: '生命周期',
             showOverflowTooltip: true,
             minWidth: 110,
-            formatter:(_row)=>{
-              return sourceStatus[_row.lifeCycle]
-
+            formatter: (_row) => {
+              return sourceStatus[_row.lifeCycle];
             }
           },
           {
@@ -401,11 +400,12 @@
       },
 
       // 跳转到详情页
-      handleView({ id }) {
+      handleView({ id, code }) {
         this.$router.push({
           path: '/ledgerAssets/turnoverDisks/detail',
           query: {
-            id
+            id,
+            code
           }
         });
       },

+ 5 - 2
src/views/ledgerAssets/turnoverDisks/detail.vue

@@ -50,6 +50,7 @@
   import inventory from '../components/details/inventory.vue';
   import pointInspection from '../components/details/point-inspection.vue';
   import internet from '../components/details/internet.vue';
+  import produceOrder from '../components/details/produceOrder/produce-order.vue';
   export default {
     components: {
       baseInfo,
@@ -60,7 +61,8 @@
       inventory,
       // InternetRecord,
       malfunction,
-      internet
+      internet,
+      produceOrder
     },
     data() {
       return {
@@ -76,7 +78,8 @@
           { key: 'repair', name: '维修记录' },
           { key: 'malfunction', name: '故障记录' },
           { key: 'inventory', name: '盘点记录' },
-          { key: 'internet', name: '物联数据' }
+          { key: 'internet', name: '物联数据' },
+          { key: 'produceOrder', name: '生产记录' }
           // // { key: "InternetRecord", name: "物联记录" },
         ]
       };

+ 25 - 3
src/views/maintenance/components/programRulesDialog.vue

@@ -693,15 +693,19 @@
           ? '保养'
           : this.dialogTitle.includes('量具送检')
           ? '量具送检'
+          : this.dialogTitle.includes('运行记录')
+          ? '运行记录'
           : '盘点';
         const typeOptions = {
           巡点检: 1,
           保养: 2,
           维修: 3,
           计划性维修: 4,
-          量具送检: 5
+          量具送检: 5,
+          运行记录: 6
         };
-        this.addForm.type = typeOptions[this.formLabel];
+        this.$set(this.addForm, 'type', typeOptions[this.formLabel]);
+
         // const planRuleTypeObj = {
         //   巡点检: 'PATROL',
         //   保养: 'MAINTAIN',
@@ -721,7 +725,7 @@
         this.ruleObj.code = item.code;
       },
       save() {
-        console.log(this.addForm);
+        console.log(this.addForm, 888);
         console.log(this.ruleIdList);
         if (this.ruleIdList && this.ruleIdList.length > 0) {
           this.$refs.addFormRef.validate(async (valid) => {
@@ -925,6 +929,10 @@
           const code = await getCode('quantity_code');
           this.$set(this.addForm, 'code', code);
         }
+        if (tips.includes('运行记录')) {
+          const code = await getCode('runRecord_code');
+          this.$set(this.addForm, 'code', code);
+        }
       },
       //选择部门(搜索)
       searchDeptNodeClick(info, data) {
@@ -1006,6 +1014,20 @@
             this.ruleNameList = res.list || [];
           }
         }
+        if (
+          this.dialogTitle === '新增运行记录配置' ||
+          this.dialogTitle === '编辑运行记录配置'
+        ) {
+          const res = await getRule({
+            status: 1,
+            type: 6,
+            pageNum: 1,
+            size: -1
+          });
+          if (res.list) {
+            this.ruleNameList = res.list || [];
+          }
+        }
       },
       downloadFile(file) {
         getFile({ objectName: file.storePath }, file.name);

+ 70 - 0
src/views/maintenance/runRecord/index.vue

@@ -0,0 +1,70 @@
+<template>
+  <div class="patrol">
+    <div class="ele-body">
+      <el-card shadow="never">
+        <div class="switch">
+          <div class="switch_left">
+            <ul>
+              <li
+                v-for="item in tabOptions"
+                :key="item.key"
+                :class="{ active: activeComp == item.key }"
+                @click="activeComp = item.key"
+              >
+                {{ item.name }}
+              </li>
+            </ul>
+          </div>
+        </div>
+        <div class="main">
+          <div v-if="activeComp == 'plan'">
+            <plan />
+          </div>
+          <div v-else>
+            <workOrder />
+          </div>
+        </div>
+      </el-card>
+    </div>
+  </div>
+</template>
+<script>
+  import plan from './plan';
+  import workOrder from './workOrder';
+  export default {
+    components: { plan, workOrder },
+    data() {
+      return {
+        activeComp: 'plan',
+        tabOptions: [
+          { key: 'plan', name: '计划' },
+          { key: 'workOrder', name: '工单' }
+        ]
+      };
+    },
+    mounted() {
+      switch (this.$route.query.title) {
+        case '计划':
+          this.activeComp = 'plan';
+          break;
+        case '工单':
+          this.activeComp = 'workOrder';
+          break;
+        default:
+          break;
+      }
+    }
+  };
+</script>
+<style lang="scss" scoped>
+  ::v-deep .el-card__body {
+    padding-top: 0;
+    padding-left: 0;
+  }
+  .main {
+    padding-left: 17px;
+    .plan {
+      padding-top: 15px;
+    }
+  }
+</style>

+ 187 - 0
src/views/maintenance/runRecord/plan/components/plan-search.vue

@@ -0,0 +1,187 @@
+<!-- 搜索表单 -->
+<template>
+  <el-form
+    label-width="100px"
+    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.planCode" placeholder="请输入" />
+        </el-form-item>
+        <el-form-item label="计划性质:">
+          <el-select
+            clearable
+            filterable
+            v-model="where.cycleType"
+            class="w100"
+          >
+            <el-option label="手动" :value="0"></el-option>
+            <el-option label="自动" :value="1"></el-option>
+          </el-select>
+        </el-form-item>
+      </el-col>
+      <el-col v-bind="styleResponsive ? { lg: 6, md: 12 } : { span: 6 }">
+        <el-form-item label="计划名称:">
+          <el-input clearable v-model="where.planName" placeholder="请输入" />
+        </el-form-item>
+        <el-form-item label="设备分类:">
+          <equipmentSelect v-model="where.categoryLevelId" />
+        </el-form-item>
+      </el-col>
+      <el-col v-bind="styleResponsive ? { lg: 6, md: 12 } : { span: 6 }">
+        <el-form-item label="计划规则:">
+          <el-input clearable v-model="where.ruleName" placeholder="请输入" />
+        </el-form-item>
+        <el-form-item label="生成时间:">
+          <el-date-picker
+            v-model="where.time"
+            type="daterange"
+            align="right"
+            unlink-panels
+            range-separator="至"
+            start-placeholder="开始日期"
+            end-placeholder="结束日期"
+            :picker-options="pickerOptions"
+            value-format="yyyy-MM-dd HH:mm:ss"
+            :default-time="['00:00:00', '23:59:59']"
+          >
+          </el-date-picker>
+        </el-form-item>
+      </el-col>
+      <el-col v-bind="styleResponsive ? { lg: 6, md: 12 } : { span: 6 }">
+        <el-form-item label="状态:">
+          <el-select
+            clearable
+            filterable
+            v-model="where.planStatus"
+            class="w100"
+          >
+            <el-option label="待派单" :value="0"></el-option>
+            <el-option label="已派单" :value="1"></el-option>
+            <el-option label="执行中" :value="2"></el-option>
+            <el-option label="已完成" :value="3"></el-option>
+            <el-option label="已撤回" :value="4"></el-option>
+            <el-option label="已驳回" :value="4"></el-option>
+          </el-select>
+        </el-form-item>
+        <!-- <el-form-item label="组织机构:">
+          <auth-selection v-model="where.deptIds" style="width: 100%"></auth-selection>
+        </el-form-item> -->
+
+      </el-col>
+    </el-row>
+    <el-row :gutter="15">
+      <el-col class="ele-form-actions">
+        <el-button
+          type="primary"
+          icon="el-icon-search"
+          class="ele-btn-icon"
+          @click="search"
+          size="small"
+        >
+          查询
+        </el-button>
+        <el-button
+          @click="reset"
+          icon="el-icon-refresh-left"
+          size="small"
+          type="primary"
+        >重置</el-button
+        >
+      </el-col>
+    </el-row>
+  </el-form>
+</template>
+
+<script>
+  import equipmentSelect from '@/components/CommomSelect/equipment-select.vue';
+  export default {
+    components: { equipmentSelect },
+    data() {
+      // 默认表单数据
+      const defaultWhere = {
+        planName: '',
+        planCode: '',
+        fixCode: '',
+        time: [],
+        ruleName: '',
+        categoryLevelId: ''
+      };
+      return {
+        // 表单数据
+        where: { ...defaultWhere },
+        treeData: [],
+        pickerOptions: {
+          shortcuts: [
+            {
+              text: '最近一周',
+              onClick(picker) {
+                const end = new Date();
+                const start = new Date();
+                start.setTime(start.getTime() - 3600 * 1000 * 24 * 7);
+                picker.$emit('pick', [start, end]);
+              }
+            },
+            {
+              text: '最近一个月',
+              onClick(picker) {
+                const end = new Date();
+                const start = new Date();
+                start.setTime(start.getTime() - 3600 * 1000 * 24 * 30);
+                picker.$emit('pick', [start, end]);
+              }
+            },
+            {
+              text: '最近三个月',
+              onClick(picker) {
+                const end = new Date();
+                const start = new Date();
+                start.setTime(start.getTime() - 3600 * 1000 * 24 * 90);
+                picker.$emit('pick', [start, end]);
+              }
+            }
+          ]
+        }
+      };
+    },
+    computed: {
+      // 是否开启响应式布局
+      styleResponsive() {
+        return this.$store.state.theme.styleResponsive;
+      }
+    },
+    created() {},
+    methods: {
+      /* 搜索 */
+      search() {
+        const parmas = this.where;
+        if (parmas.time?.length) {
+          parmas.startTime = parmas.time[0];
+          parmas.endTime = parmas.time[1];
+        }
+        delete parmas.time;
+        this.$emit('search', parmas);
+      },
+      /*  重置 */
+      reset() {
+        this.where = { ...this.defaultWhere };
+        this.search();
+      }
+    }
+  };
+</script>
+<style lang="scss" scoped>
+  .ele-form-actions {
+    display: flex;
+    align-items: center;
+    justify-content: flex-end;
+  }
+  ::v-deep {
+    .el-range-editor--medium.el-input__inner {
+      width: 100%;
+    }
+  }
+</style>

+ 737 - 0
src/views/maintenance/runRecord/plan/details.vue

@@ -0,0 +1,737 @@
+<template>
+  <div class="page" v-loading="pageLoading">
+    <el-form label-width="130px">
+      <div class="content-detail">
+        <div class="basic-details">
+          <HeaderTitle title="基本信息" size="16px">
+            <el-button
+              type="primary"
+              @click="
+                $router.push({
+                  path: '/maintenance/patrol',
+                  query: { title: '计划' }
+                })
+              "
+              >返回</el-button
+            >
+          </HeaderTitle>
+          <el-row>
+            <el-col :span="12">
+              <el-col :span="12">
+                <el-form-item label="计划单号">
+                  <span> {{ infoData.code }} </span>
+                </el-form-item>
+              </el-col>
+              <el-col :span="12">
+                <el-form-item label="来源计划配置单号">
+                  <span> {{ infoData.planConfigCode }} </span>
+                </el-form-item>
+              </el-col>
+              <el-col :span="12">
+                <el-form-item label="名称">
+                  <span> {{ infoData.name }} </span>
+                </el-form-item>
+              </el-col>
+              <el-col :span="12">
+                <el-form-item label="部门">
+                  <span v-if="infoData.executor && infoData.executor.length">
+                    {{ infoData.executor[0].deptName }}
+                  </span>
+                </el-form-item>
+              </el-col>
+              <el-col :span="12">
+                <el-form-item label="人员">
+                  <span v-if="infoData.executor && infoData.executor.length">
+                    {{ infoData.executor.map((i) => i.name).join(',') }}
+                  </span>
+                </el-form-item>
+              </el-col>
+              <el-col :span="12">
+                <el-form-item label="计划完成时长">
+                  <span v-if="infoData.duration >= 0"
+                    >{{ infoData.duration }}分钟</span
+                  >
+                </el-form-item>
+              </el-col>
+              <el-col :span="12">
+                <el-form-item label="设备分类">
+                  <span> {{ infoData.categoryLevelName }} </span>
+                </el-form-item>
+              </el-col>
+              <el-col :span="12">
+                <el-form-item label="规则名称">
+                  <span>
+                    {{ infoData.ruleInfo && infoData.ruleInfo.name }}
+                  </span>
+                </el-form-item>
+              </el-col>
+              <el-col :span="12">
+                <el-form-item label="创建部门">
+                  <span> {{ infoData.createUserGroupName }} </span>
+                </el-form-item>
+              </el-col>
+              <el-col :span="12">
+                <el-form-item label="创建人">
+                  <span> {{ infoData.createUserName }} </span>
+                </el-form-item>
+              </el-col>
+              <el-col :span="12">
+                <el-form-item label="创建时间">
+                  <span> {{ infoData.createTime }} </span>
+                </el-form-item>
+              </el-col>
+              <el-col :span="24">
+                <el-form-item label="备注">
+                  <span> {{ infoData.remark }} </span>
+                </el-form-item>
+              </el-col>
+            </el-col>
+            <el-col :span="12">
+              <!-- <img :src="infoData.imageUrl" alt="" /> -->
+            </el-col>
+          </el-row>
+        </div>
+        <!-- 备品备件 -->
+        <div v-if="sparePartsList.length > 0" class="maintain_spareParts_info">
+          <HeaderTitle title="备品备件" size="16px"></HeaderTitle>
+          <div
+            class="maintain_spareParts_info_content"
+            v-for="(item, index) in sparePartsList"
+          >
+            <div class="title">
+              <span>工单号:{{ item.workOrderId }}</span>
+            </div>
+            <el-table :data="item.infoList" border>
+              <el-table-column label="序号" width="50">
+                <template slot-scope="scope">
+                  <span>{{ scope.$index + 1 }}</span>
+                </template>
+              </el-table-column>
+              <el-table-column
+                label="备件物品编码"
+                prop="code"
+              ></el-table-column>
+              <el-table-column label="备件名称" prop="name"></el-table-column>
+              <el-table-column
+                label="所属分类"
+                prop="typeName"
+              ></el-table-column>
+              <el-table-column label="型号" prop="model"></el-table-column>
+              <el-table-column label="使用数量" prop="num"></el-table-column>
+            </el-table>
+          </div>
+        </div>
+        <div class="maintain_equipment_info">
+          <HeaderTitle title="设备" size="16px"></HeaderTitle>
+          <div class="maintain_equipment_info_content">
+            <div
+              class="equipment_item"
+              v-for="item in infoData.planDeviceList"
+              :key="item.id"
+            >
+              <div class="equipment_info" v-if="item.substance">
+                <div class="item_info">
+                  <span class="item_label">设备编码</span>
+                  <span class="item_value">{{ item.substance.code }}</span>
+                </div>
+                <div class="item_info">
+                  <span class="item_label">设备名称</span>
+                  <span class="item_value">{{ item.substance.name }}</span>
+                </div>
+                <div class="item_info">
+                  <span class="item_label">设备型号</span>
+                  <span class="item_value">{{ item.substance.model }}</span>
+                </div>
+                <div class="item_info">
+                  <span class="item_label">设备位置</span>
+                  <span class="item_value">{{
+                    item.substance.positionNames
+                  }}</span>
+                </div>
+              </div>
+              <p>操作事项</p>
+              <div class="ruleMatters_box">
+                <el-table :data="item.workItems" border>
+                  <el-table-column label="序号" width="50">
+                    <template slot-scope="scope">
+                      <span>{{ scope.$index + 1 }}</span>
+                    </template>
+                  </el-table-column>
+                  <el-table-column
+                    label="零部件编码"
+                    prop="categoryCode"
+                    width="100"
+                  >
+                    <template slot-scope="scope">
+                      <div>
+                        <span>{{ scope.row.categoryCode }}</span>
+                      </div>
+                    </template>
+                  </el-table-column>
+                  <el-table-column
+                    label="零部件名称"
+                    prop="categoryName"
+                    width="100"
+                  >
+                    <template slot-scope="scope">
+                      <div>
+                        <span>{{ scope.row.categoryName }}</span>
+                      </div>
+                    </template>
+                  </el-table-column>
+                  <el-table-column label="事项" prop="name" width="100">
+                    <template slot-scope="scope">
+                      <div>
+                        <span>{{ scope.row.name }}</span>
+                      </div>
+                    </template>
+                  </el-table-column>
+                  <el-table-column label="内容" prop="content" width="300">
+                    <template slot-scope="scope">
+                      <div>
+                        <span>{{ scope.row.content }}</span>
+                      </div>
+                    </template>
+                  </el-table-column>
+                  <el-table-column label="操作指导" prop="operationGuide">
+                    <template slot-scope="scope">
+                      <div class="operationGuide_box">
+                        <div class="left_content">
+                          <template v-if="scope.row.operationGuide">
+                            <div
+                              v-for="(item, index) in scope.row.operationGuide
+                                .toolList"
+                              :key="item.id"
+                              >{{ index + 1 }}.{{ item.name }}</div
+                            >
+                          </template>
+                        </div>
+                        <div class="line"></div>
+                        <div class="right_content">
+                          <template v-if="scope.row.operationGuide">
+                            <div
+                              v-for="(item, index) in scope.row.operationGuide
+                                .procedureList"
+                              :key="item.id"
+                              >{{ index + 1 }}.{{ item.content }}</div
+                            >
+                          </template>
+                        </div>
+                      </div>
+                    </template>
+                  </el-table-column>
+                  <el-table-column label="标准" prop="norm" width="100">
+                    <template slot-scope="scope">
+                      <div>
+                        <span>{{ scope.row.norm }}</span>
+                      </div>
+                    </template>
+                  </el-table-column>
+                </el-table>
+              </div>
+              <!-- <div class="matter_info">
+                <el-table :data="item.workItems || []" border>
+                  <el-table-column label="序号" align="center" width="80">
+                    <template slot-scope="scope">
+                      <span>{{ scope.$index + 1 }}</span>
+                    </template>
+                  </el-table-column>
+                  <el-table-column label="事项" prop="name" />
+                  <el-table-column label="内容" prop="content" />
+                  <el-table-column label="标准" prop="norm" />
+                </el-table>
+              </div> -->
+            </div>
+          </div>
+        </div>
+
+        <div class="btnbox" v-if="$route.query.isshow">
+          <el-button class="confirm-btn" type="danger" plain @click="reject"
+            >驳回</el-button
+          >
+          <el-button class="confirm-btn" type="success" plain @click="pass"
+            >通过</el-button
+          >
+          <!-- <el-button class="cancel-btn">关闭</el-button> -->
+        </div>
+        <div class="textbox" v-if="showtext" ref="rejectContent">
+          <el-input
+            type="textarea"
+            placeholder="请输入驳回原因"
+            v-model="cause"
+            maxlength="30"
+            rows="5"
+            show-word-limit
+          >
+          </el-input>
+          <div class="textbtnbox">
+            <el-button size="small" round @click="cancelreject">取消</el-button>
+            <el-button size="small" round @click="surereject">提交</el-button>
+          </div>
+        </div>
+      </div>
+    </el-form>
+  </div>
+</template>
+
+<script>
+  // import { getDetail, sendAudit } from '@/api/stockManagement/stocking'
+  // import { useDictLabel, patrolMatterStatus } from '@/utils/dict/index'
+  import { getById, getSpareParts } from '@/api/maintenance/patrol_maintenance';
+  import dictMixins from '@/mixins/dictMixins';
+  export default {
+    mixins: [dictMixins],
+    data() {
+      return {
+        num: 1,
+        dialogVisible: false,
+        baseInfo: {},
+        pageLoading: false,
+        typeValue: null,
+        contract_type: [],
+        status: [
+          {
+            value: true,
+            label: '失效'
+          },
+          {
+            value: false,
+            label: '生效'
+          }
+        ],
+        ruleItem: [],
+        cause: '',
+        showtext: false,
+        infoData: {},
+        sparePartsList: []
+      };
+    },
+    async created() {
+      this.getInfo();
+      this.getSparePartsList();
+    },
+    methods: {
+      // getStatus: useDictLabel(patrolMatterStatus),
+      delete() {},
+      // 点击切换事件
+      tab(index) {
+        this.num = index;
+      },
+      // 表格数据
+      async getInfo() {
+        this.pageLoading = true;
+        const res = await getById(this.$route.query.id).catch(() => {
+          this.pageLoading = false;
+        });
+        if (res?.data) {
+          this.infoData = res.data;
+        }
+        this.pageLoading = false;
+      },
+      // 通过工单查询备品备件
+      getSparePartsList() {
+        getSpareParts(this.$route.query.id).then((data) => {
+          console.log(data);
+          this.sparePartsList = data.map((item) => {
+            item.infoList = item.content.infoList.map((innerItem) => {
+              return {
+                sparePartsId: innerItem.sparePartsId,
+                ...JSON.parse(innerItem.sparePartsList)
+              };
+            });
+            return {
+              ...item
+            };
+          });
+          console.log(this.sparePartsList);
+        });
+      },
+      //通过按钮事件
+      pass() {
+        let params = {
+          id: this.$route.query.id,
+          checked: true,
+          myHandleId: this.$route.query.dbid,
+          cause: '',
+          type: 2,
+          handleType: 0
+        };
+        sendAudit(params).then((res) => {
+          if (res.success) {
+            this.$message.success('审批通过!');
+            this.$router.back();
+          }
+        });
+      },
+      //驳回按钮事件
+      reject() {
+        this.showtext = true;
+        let bodyscrollHeight = document.body.scrollHeight;
+        this.$nextTick(() => {
+          document.documentElement.scrollTop = bodyscrollHeight;
+        });
+      },
+      cancelreject() {
+        this.showtext = false;
+        this.cause = '';
+      },
+      surereject() {
+        if (!this.cause) {
+          this.$message.info('请填写驳回原因!');
+        } else {
+          let params = {
+            id: this.$route.query.id,
+            checked: false,
+            myHandleId: this.$route.query.dbid,
+            cause: this.cause,
+            type: 2,
+            handleType: 0
+          };
+          sendAudit(params).then((res) => {
+            if (res.success) {
+              this.$message.success('驳回成功!');
+              this.$router.back();
+            }
+          });
+        }
+      }
+    }
+  };
+</script>
+
+<style lang="scss" scoped>
+  // @import '@/assets/css/oaa.scss';
+  .page {
+    padding: 10px;
+  }
+  .page-title {
+    background: #fff;
+    font-size: 18px;
+    padding: 6px 20px;
+    font-weight: 500;
+    .page-title-div {
+      margin: 5px 0;
+      height: 30px;
+      line-height: 30px;
+      border-bottom: 1px solid #eaeefb;
+      .title-div-no {
+        margin-left: 10px;
+        font-weight: 400;
+        color: #909090;
+        font-size: 14px;
+      }
+    }
+  }
+  .page-data {
+    padding-top: 10px;
+  }
+  .content-detail {
+    background: #fff;
+    padding: 20px;
+  }
+  .flows {
+    .flow-left {
+      width: 156px;
+      height: 70px;
+      border: 1px dashed #ccc;
+      padding: 10px;
+    }
+    .row {
+      margin-top: 13px;
+    }
+  }
+  .basic-details-title {
+    margin-bottom: 12px;
+    margin-top: 20px;
+    border-bottom: 1px solid #1890ff;
+    padding-bottom: 8px;
+    display: flex;
+    justify-content: space-between;
+  }
+  .basic-details-title .border-span {
+    height: 18px;
+    font-size: 16px;
+    border-left: 4px solid #1890ff;
+    padding-left: 8px;
+
+    font-weight: 500;
+  }
+  .heade-right {
+    // float: right;
+    .heade-right-content {
+      margin-right: 12px;
+      font-size: 14px;
+      display: inline-block;
+      .content-key {
+        color: #3e3e3e;
+        margin-right: 12px;
+        font-weight: 500;
+      }
+      .content-value {
+        color: #000;
+      }
+    }
+  }
+  .list-title {
+    font-size: 14px;
+    color: #3e3e3e;
+    margin: 10px 0px;
+  }
+  .goods {
+    background: #a30014;
+    border: 1px solid #a30014;
+  }
+  .details-title {
+    display: inline-block;
+    color: #6e6e6e;
+    font-size: 14px;
+    font-weight: bold;
+    margin-right: 13px;
+    width: 70px;
+    text-align: right;
+  }
+  .details-con {
+    color: #3e3e3e;
+    font-size: 14px;
+  }
+  .detailed-tab {
+    margin-left: 10px;
+    margin-top: 10px;
+  }
+  ::v-deep .el-form-item--medium .el-form-item__label {
+    color: #6e6e6e;
+    font-size: 14px;
+    font-weight: bold;
+  }
+  .warehouse {
+    display: block;
+    border-bottom: 1px solid #eaeefb;
+    padding: 10px 0;
+  }
+  .box-card {
+    .store-box {
+      width: 80%;
+      .store-box-span {
+        display: inline-block;
+        font-size: 14px;
+        height: 50px;
+        width: 50px;
+        text-align: center;
+        line-height: 50px;
+        color: #fff;
+        margin: 2px;
+      }
+    }
+  }
+  .vacant {
+    background: #3196fb;
+  }
+  .inUse {
+    background: #157a2c;
+  }
+  .invalid {
+    background: #cccccc;
+  }
+  .full {
+    background: #cc3300;
+  }
+
+  .maintain_equipment_info {
+    .maintain_equipment_info_title {
+      border-bottom: 1px solid #1890ff;
+      padding-bottom: 3px;
+      margin-bottom: 20px;
+      > span {
+        display: inline-block;
+        line-height: 16px;
+        border-left: 6px solid #1890ff;
+        padding-left: 6px;
+      }
+    }
+    .maintain_equipment_info_content {
+      padding: 0 30px;
+      .equipment_item {
+        border: 1px solid #ccc;
+        font-size: 14px;
+        padding: 15px;
+        margin-bottom: 30px;
+        .equipment_info {
+          display: flex;
+          flex-wrap: wrap;
+          border: 1px solid #ddd;
+          .item_info {
+            width: 33.33%;
+            height: 24px;
+            line-height: 24px;
+            display: flex;
+            .item_label {
+              width: 90px;
+              text-align: center;
+              background-color: #f2f2f2;
+              font-weight: 700;
+            }
+            .item_value {
+              border-bottom: 1px solid #f2f2f2;
+              flex: 1;
+              padding-left: 5px;
+            }
+            &:last-child {
+              width: 100%;
+              .item_value {
+                border: 0;
+              }
+            }
+          }
+        }
+        > p {
+          margin-top: 20px;
+          color: #797979;
+        }
+        .matter_info {
+          ::v-deep .el-table {
+            th.el-table__cell {
+              background-color: #f2f2f2;
+              padding: 0;
+            }
+            td.el-table__cell {
+              padding: 0;
+            }
+          }
+        }
+        .ruleMatters_box {
+          flex: 3;
+          height: 100%;
+          display: flex;
+          flex-direction: column;
+          .divider {
+            flex: 0 0 50px;
+            .title {
+              height: 35px;
+            }
+          }
+          .el-table {
+            overflow: auto;
+            .operationGuide_box {
+              width: 100%;
+              display: flex;
+              position: relative;
+              .left_content {
+                flex: 0 0 300px;
+                padding: 10px;
+                margin-right: 10px;
+                overflow-y: auto;
+              }
+              .line {
+                position: absolute;
+                top: -10px;
+                left: 300px;
+                bottom: -10px;
+                height: 110%;
+                width: 1px;
+                background-color: #ededed;
+              }
+              .right_content {
+                flex: 1;
+                padding: 10px;
+                overflow-y: auto;
+              }
+            }
+          }
+        }
+      }
+    }
+  }
+
+  .maintain_spareParts_info {
+    margin-bottom: 20px;
+    .maintain_spareParts_info_content {
+      .title {
+        padding: 20px 0;
+        font-size: 16px;
+      }
+    }
+  }
+  .examine_info {
+    margin-bottom: 30px;
+    .examine_info_title {
+      border-bottom: 1px solid #1890ff;
+      padding-bottom: 3px;
+      margin-bottom: 20px;
+      > span {
+        display: inline-block;
+        line-height: 16px;
+        border-left: 6px solid #1890ff;
+        padding-left: 6px;
+      }
+    }
+    .item_row {
+      display: flex;
+      flex-wrap: wrap;
+      font-size: 14px;
+      padding: 0 15px;
+      box-sizing: border-box;
+      .item_info {
+        width: 33.33%;
+        height: 24px;
+        line-height: 24px;
+        display: flex;
+        &.border_right {
+          border-right: 1px solid #f2f2f2;
+        }
+        &.border_top {
+          border-top: 1px solid #f2f2f2;
+        }
+        &.reason {
+          width: 100%;
+        }
+        .item_label {
+          width: 90px;
+          text-align: center;
+          background-color: #f2f2f2;
+          font-weight: 700;
+        }
+        .item_value {
+          border-bottom: 1px solid #f2f2f2;
+          flex: 1;
+          padding-left: 5px;
+        }
+      }
+    }
+  }
+  .execute_info {
+    .execute_info_title {
+      border-bottom: 1px solid #1890ff;
+      padding-bottom: 3px;
+      margin-bottom: 20px;
+      > span {
+        display: inline-block;
+        line-height: 16px;
+        border-left: 6px solid #1890ff;
+        padding-left: 6px;
+      }
+    }
+    ::v-deep .el-table th.el-table__cell {
+      background-color: #f2f2f2;
+    }
+    ::v-deep .el-table .el-table__cell {
+      padding: 5px 0;
+    }
+  }
+  .btnbox {
+    display: flex;
+    justify-content: center;
+    margin-top: 10px;
+  }
+  ::v-deep .el-button {
+    padding: 10px 20px;
+    margin-right: 10px;
+  }
+  .textbox {
+    margin-top: 10px;
+  }
+  .textbtnbox {
+    margin-top: 10px;
+    display: flex;
+    justify-content: center;
+  }
+</style>

+ 271 - 0
src/views/maintenance/runRecord/plan/index.vue

@@ -0,0 +1,271 @@
+<template>
+  <div class="ele-body">
+    <el-card shadow="never" v-loading="loading">
+      <plan-search @search="reload"> </plan-search>
+      <!-- 数据表格 -->
+      <!-- :default-sort="{ prop: 'createTime', order: 'descending' }" -->
+      <ele-pro-table
+        ref="table"
+        :columns="columns"
+        :datasource="datasource"
+        cache-key="systemRoleTable"
+      >
+        <!-- 表头工具栏 -->
+        <template v-slot:toolbar>
+          <el-button
+            size="small"
+            type="primary"
+            icon="el-icon-plus"
+            class="ele-btn-icon"
+            @click="openAdd('新增运行记录配置')"
+          >
+            新建临时计划
+          </el-button>
+        </template>
+        <!-- 	     <template v-slot:enable="{ row }">
+	       <el-switch
+	         v-model="row.enable"
+	         active-color="#13ce66"
+	         inactive-color="#ff4949"
+	         :active-value="1"
+	         :inactive-value="0"
+	         @change="changeEnable(row)"
+	       >
+	       </el-switch>
+	     </template> -->
+        <template v-slot:planCode="{ row }">
+          <el-link type="primary" :underline="false" @click="goDetail(row)">
+            {{ row.planCode }}
+          </el-link>
+        </template>
+        <!-- 操作列 -->
+        <template v-slot:action="{ row }">
+          <el-link
+            type="primary"
+            :underline="false"
+            v-if="row.cycleType == 0 || row.planStatus == 4"
+            icon="el-icon-edit"
+            @click="openAdd('编辑运行记录配置', row)"
+          >
+            编辑
+          </el-link>
+          <el-link
+            v-if="row.cycleType == 0 || row.planStatus == 4"
+            type="primary"
+            :underline="false"
+            icon="el-icon-edit"
+            @click="openAdd('派单', row)"
+          >
+            派单
+          </el-link>
+          <el-link
+            v-if="row.planStatus != 2 && row.planStatus != 3"
+            type="primary"
+            :underline="false"
+            icon="el-icon-edit"
+            @click="handleWithdraw(row)"
+          >
+            撤回
+          </el-link>
+        </template>
+      </ele-pro-table>
+    </el-card>
+
+    <!-- 新建或编辑弹窗 -->
+    <!-- <AddPatrolPlanDialog ref="addPatrolPlanDialogRef" @refreshList="reload" /> -->
+    <programRulesDialog
+      ref="programRulesDialog"
+      :visible.sync="addProgramRulesDialog"
+      :dialogTitle="dialogTitle"
+      :isBindPlan="isBindPlan"
+      @done="reload"
+    />
+    <dispatchDialog ref="dispatchDialogRef" @refreshList="reload" />
+  </div>
+</template>
+
+<script>
+  import ProgramRulesDialog from '../../components/programRulesDialog.vue';
+  import AddPatrolPlanDialog from '@/components/addPatrolPlanDialog/index.vue';
+  import DispatchDialog from '@/components/addPatrolPlanDialog/DispatchDialog';
+  import PlanSearch from './components/plan-search.vue';
+  import { getPage, revocation } from '@/api/maintenance/patrol_maintenance';
+  export default {
+    components: {
+      PlanSearch,
+      DispatchDialog,
+      AddPatrolPlanDialog,
+      ProgramRulesDialog
+    },
+    data() {
+      return {
+        addProgramRulesDialog: false,
+        isBindPlan: false,
+        dialogTitle: '',
+        // 表格列配置
+        columns: [
+          {
+            columnKey: 'index',
+            label: '序号',
+            type: 'index',
+            width: 55,
+            align: 'center',
+            showOverflowTooltip: true,
+            fixed: 'left'
+          },
+          {
+            columnKey: 'planCode',
+            slot: 'planCode',
+            prop: 'planCode',
+            label: '计划单号',
+            align: 'center',
+            showOverflowTooltip: true,
+            minWidth: 200
+          },
+          {
+            prop: 'planName',
+            label: '计划名称',
+            align: 'center',
+            showOverflowTooltip: true,
+            minWidth: 110
+          },
+          {
+            prop: 'ruleName',
+            label: '计划规则',
+            align: 'center',
+            showOverflowTooltip: true,
+            slot: 'enable',
+            minWidth: 200
+          },
+          {
+            prop: 'categoryLevelName',
+            label: '设备分类',
+            align: 'center',
+            showOverflowTooltip: true,
+            minWidth: 110
+          },
+          {
+            prop: 'cycleType',
+            label: '计划性质',
+            align: 'center',
+            showOverflowTooltip: true,
+            minWidth: 110,
+            formatter(item) {
+              return { 1: '自动', 0: '手动' }[item.cycleType];
+            }
+          },
+          {
+            prop: 'planStatus',
+            label: '状态',
+            align: 'center',
+            showOverflowTooltip: true,
+            minWidth: 110,
+            formatter(item) {
+              return {
+                0: '待派单',
+                1: '已派单',
+                2: '执行中',
+                3: '已完成',
+                4: '已撤回',
+                5: '已驳回'
+              }[item.planStatus];
+            }
+          },
+          {
+            prop: 'approvalUserName',
+            label: '审批人',
+            align: 'center',
+            showOverflowTooltip: true,
+            minWidth: 110
+          },
+          {
+            prop: 'createUserName',
+            label: '创建人',
+            align: 'center',
+            showOverflowTooltip: true,
+            minWidth: 110
+          },
+          {
+            prop: 'createTime',
+            label: '生成时间',
+            align: 'center',
+            // sortable: true,
+            showOverflowTooltip: true,
+            minWidth: 150,
+            formatter: (_row, _column, cellValue) => {
+              return this.$util.toDateString(cellValue);
+            }
+          },
+          {
+            columnKey: 'action',
+            label: '操作',
+            width: 230,
+            align: 'center',
+            resizable: false,
+            slot: 'action',
+            showOverflowTooltip: true
+          }
+        ],
+        // 加载状态
+        loading: false,
+        pageType: 'add',
+        isBindPlan: false
+      };
+    },
+    methods: {
+      /* 表格数据源 */
+      datasource({ page, limit, where, order }) {
+        return getPage({ pageNum: page, size: limit, ...where, planType: 6 });
+      },
+      async changeEnable(row) {
+        const res = await putRoles(row);
+        if (res.code == 0) {
+          this.$message({
+            type: 'success',
+            message: '修改成功',
+            customClass: 'ele-message-border'
+          });
+          this.reload();
+        }
+      },
+      /* 刷新表格 */
+      reload(where) {
+        this.addProgramRulesDialog = false;
+        this.$refs.table.reload({ page: 1, where });
+      },
+      handleWithdraw(row) {
+        // 撤回
+        this.$confirm(`确认撤回?`, '提示').then(async () => {
+          revocation(row.id)
+            .then(() => {
+              this.$message.success('撤回成功!');
+              this.reload();
+            })
+            .catch((err) => {
+              this.$message.success(err.message || '撤回失败!');
+            });
+        });
+      },
+
+      openAdd(dialogTitle, row) {
+        // this.$refs.addPatrolPlanDialogRef.open(dialogTitle, row);
+        this.isBindPlan = false;
+        this.addProgramRulesDialog = true;
+        this.dialogTitle = dialogTitle;
+        this.$nextTick(() => {
+          this.$refs.programRulesDialog.init(row, '运行记录');
+        });
+      },
+      goDetail({ id }) {
+        this.$router.push({
+          path: '/maintenance/patrol/plan/details',
+          query: {
+            id
+          }
+        });
+      }
+    }
+  };
+</script>
+
+<style lang="scss" scoped></style>

+ 177 - 0
src/views/maintenance/runRecord/workOrder/components/work-search.vue

@@ -0,0 +1,177 @@
+<!-- 搜索表单 -->
+<template>
+  <el-form
+    label-width="100px"
+    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.code" placeholder="请输入" />
+        </el-form-item>
+        <el-form-item label="巡点检人员:">
+          <el-input
+            clearable
+            v-model="where.executeUserName"
+            placeholder="请输入"
+          />
+        </el-form-item>
+      </el-col>
+      <el-col v-bind="styleResponsive ? { lg: 6, md: 12 } : { span: 6 }">
+        <el-form-item label="计划单号:">
+          <el-input clearable v-model="where.planCode" placeholder="请输入" />
+        </el-form-item>
+        <el-form-item label="状态:">
+          <el-select
+            style="width: 100%"
+            clearable
+            filterable
+            v-model="where.orderStatus"
+          >
+            <el-option label="待接收" :value="0"></el-option>
+            <el-option label="已接收" :value="1"></el-option>
+            <el-option label="执行中" :value="2"></el-option>
+            <el-option label="已完成" :value="3"></el-option>
+          </el-select>
+        </el-form-item>
+      </el-col>
+      <el-col v-bind="styleResponsive ? { lg: 6, md: 12 } : { span: 6 }">
+        <el-form-item label="巡点检名称:">
+          <el-input clearable v-model="where.planName" placeholder="请输入" />
+        </el-form-item>
+        <el-form-item label="规则名称:">
+          <!-- <el-input clearable v-model="where.ruleName" placeholder="请输入" /> -->
+          <el-select
+            v-model="where.ruleId"
+            size="small"
+            clearable
+            style="width: 100%"
+            filterable
+          >
+            <el-option
+              v-for="item in ruleNameList"
+              :key="item.id"
+              :value="item.id"
+              :label="item.name"
+            ></el-option>
+          </el-select>
+        </el-form-item>
+        <!-- <el-form-item label="设备分类:">
+          <equipmentSelect v-model="where.categoryLevelId" />
+        </el-form-item> -->
+      </el-col>
+      <el-col v-bind="styleResponsive ? { lg: 6, md: 12 } : { span: 6 }">
+        <el-form-item label="巡点检部门:">
+          <deptSelect v-model="where.groupId" @changeGroup="changeGroup" />
+        </el-form-item>
+        <!-- <el-form-item label="规则名称:">
+          <el-input clearable v-model="where.name" placeholder="请输入" />
+        </el-form-item> -->
+        <!-- <el-form-item label="组织机构:">
+          <auth-selection v-model="where.deptIds" style="width: 100%"></auth-selection>
+        </el-form-item> -->
+      </el-col>
+    </el-row>
+    <el-row :gutter="15">
+      <el-col class="ele-form-actions">
+        <el-button
+          type="primary"
+          icon="el-icon-search"
+          class="ele-btn-icon"
+          @click="search"
+          size="small"
+        >
+          查询
+        </el-button>
+        <el-button
+          @click="reset"
+          icon="el-icon-refresh-left"
+          size="small"
+          type="primary"
+          >重置</el-button
+        >
+      </el-col>
+    </el-row>
+  </el-form>
+</template>
+
+<script>
+  import { getRule } from '@/api/ruleManagement/plan';
+  import equipmentSelect from '@/components/CommomSelect/equipment-select.vue';
+  import deptSelect from '@/components/CommomSelect/dept-select.vue';
+  import personSelect from '@/components/CommomSelect/person-select.vue';
+  export default {
+    components: { equipmentSelect, deptSelect, personSelect },
+    data() {
+      // 默认表单数据
+      const defaultWhere = {
+        name: '',
+        executeUserName: '',
+        planCode: '',
+        code: '',
+        orderStatus: '',
+        groupId: '',
+        categoryLevelId: '',
+        planName: ''
+      };
+      return {
+        // 表单数据
+        where: { ...defaultWhere },
+        treeData: [],
+        ruleNameList: []
+      };
+    },
+    computed: {
+      // 是否开启响应式布局
+      styleResponsive() {
+        return this.$store.state.theme.styleResponsive;
+      }
+    },
+    created() {
+      this.getRuleNameList();
+    },
+    methods: {
+      /* 部门选择 */
+      changeGroup(id, data) {
+        if (id) {
+          this.where.groupId = id;
+          this.where.executeGroupName = data.name;
+        } else {
+          this.where.groupId = '';
+          this.where.executeGroupName = '';
+        }
+      },
+      /* 搜索 */
+      search() {
+        console.log(this.where);
+        this.$emit('search', this.where);
+      },
+      /*  重置 */
+      reset() {
+        this.where = { ...this.defaultWhere };
+        this.search();
+      },
+      // 获取规则名列表(设备保养)
+      async getRuleNameList() {
+        const res = await getRule({
+          status: 1,
+          type: 1,
+          pageNum: 1,
+          size: -1
+        });
+        if (res.list) {
+          this.ruleNameList = res.list || [];
+        }
+      }
+    }
+  };
+</script>
+<style lang="scss" scoped>
+  .ele-form-actions {
+    display: flex;
+    align-items: center;
+    justify-content: flex-end;
+  }
+</style>

+ 798 - 0
src/views/maintenance/runRecord/workOrder/details.vue

@@ -0,0 +1,798 @@
+<template>
+  <div class="page" v-loading="pageLoading">
+    <el-form label-width="130px">
+      <div class="content-detail" v-show="num == 1">
+        <div class="basic-details">
+          <HeaderTitle title="基本信息" size="16px">
+            <el-button
+              type="primary"
+              @click="
+                $router.push({
+                  path: '/maintenance/patrol',
+                  query: { title: '工单' }
+                })
+              "
+              >返回</el-button
+            >
+          </HeaderTitle>
+          <el-row>
+            <el-col :span="12">
+              <el-col :span="12">
+                <el-form-item label="计划单号">
+                  <span> {{ infoData.planCode }} </span>
+                </el-form-item>
+              </el-col>
+              <el-col :span="12">
+                <el-form-item label="来源计划配置单号">
+                  <span> {{ infoData.planConfigCode }} </span>
+                </el-form-item>
+              </el-col>
+              <el-col :span="12">
+                <el-form-item label="名称">
+                  <span> {{ infoData.planName }} </span>
+                </el-form-item>
+              </el-col>
+              <el-col :span="12">
+                <el-form-item label="部门">
+                  <span>
+                    {{ infoData.executeGroupName }}
+                  </span>
+                </el-form-item>
+              </el-col>
+              <el-col :span="12">
+                <el-form-item label="人员">
+                  <span>
+                    {{ infoData.executeUserName }}
+                  </span>
+                </el-form-item>
+              </el-col>
+              <el-col :span="12">
+                <el-form-item label="计划完成时长">
+                  <span v-if="infoData.duration >= 0"
+                    >{{ infoData.duration }}分钟</span
+                  >
+                </el-form-item>
+              </el-col>
+              <el-col :span="12">
+                <el-form-item label="周期">
+                  <span v-if="infoData.ruleInfo">
+                    {{ infoData.ruleInfo.cycleValue
+                    }}{{
+                      getDictValue('巡点检周期', infoData.ruleInfo.cycleType)
+                    }}
+                  </span>
+                </el-form-item>
+              </el-col>
+              <el-col :span="12">
+                <el-form-item label="设备分类">
+                  <span> {{ infoData.categoryLevelName }} </span>
+                </el-form-item>
+              </el-col>
+              <el-col :span="12">
+                <el-form-item label="规则名称">
+                  <span>
+                    {{ infoData.ruleName }}
+                  </span>
+                </el-form-item>
+              </el-col>
+              <el-col :span="12">
+                <el-form-item label="创建部门">
+                  <span> {{ infoData.createGroupName }} </span>
+                </el-form-item>
+              </el-col>
+              <el-col :span="12">
+                <el-form-item label="创建人">
+                  <span> {{ infoData.createUserName }} </span>
+                </el-form-item>
+              </el-col>
+              <el-col :span="12">
+                <el-form-item label="创建时间">
+                  <span> {{ infoData.createTime }} </span>
+                </el-form-item>
+              </el-col>
+              <el-col :span="24">
+                <el-form-item label="备注">
+                  <span> {{ infoData.remark }} </span>
+                </el-form-item>
+              </el-col>
+            </el-col>
+            <el-col :span="12">
+              <img :src="data.imageUrl" alt="" />
+            </el-col>
+          </el-row>
+        </div>
+
+        <!-- 巡点检、执行信息 -->
+        <!-- <div class="execute_info">
+          <div class="execute_info_title">
+            <span>执行信息</span>
+            <span
+              >执行人:{{ data.executeUserName }}
+              <i style="margin: 0 18px"></i> 执行时间:{{
+                data.acceptTime
+              }}</span
+            >
+          </div>
+          <HeaderTitle title="执行信息" size="16px"></HeaderTitle>
+          <el-row class="execute_row">
+            <el-col :span="8" class="column">
+              <span class="label">确认结果:</span>
+              <span class="value">{{
+                infoData.status ? infoData.status.descp : ''
+              }}</span>
+            </el-col>
+            <el-col :span="8" class="column">
+              <span class="label">实际开始时间:</span>
+              <span class="value">{{ infoData.acceptTime }}</span>
+            </el-col>
+            <el-col :span="8" class="column">
+              <span class="label">实际结束时间:</span>
+              <span class="value">{{ infoData.finishTime }}</span>
+            </el-col>
+            <el-col :span="24" class="column">
+              <span class="label">超期原因:</span>
+              <span class="value">{{ infoData.timeoutCause }}</span>
+            </el-col>
+          </el-row>
+        </div> -->
+
+        <!-- 巡点检、保养设备 -->
+        <div class="maintain_equipment_info">
+          <HeaderTitle title="巡点检设备" size="16px"></HeaderTitle>
+          <div class="maintain_equipment_info_content">
+            <div
+              class="equipment_item"
+              v-for="item in infoData.deviceList"
+              :key="item.id"
+            >
+              <div class="equipment_info" v-if="item.substance">
+                <div class="item_info">
+                  <span class="item_label">设备编码</span>
+                  <span class="item_value">{{ item.substance.code }}</span>
+                </div>
+                <div class="item_info">
+                  <span class="item_label">设备名称</span>
+                  <span class="item_value">{{ item.substance.name }}</span>
+                </div>
+                <div class="item_info">
+                  <span class="item_label">设备型号</span>
+                  <span class="item_value">{{ item.substance.model }}</span>
+                </div>
+                <div class="item_info">
+                  <span class="item_label">设备位置</span>
+                  <span class="item_value">{{
+                    item.substance.positionNames
+                  }}</span>
+                </div>
+              </div>
+              <p>操作事项</p>
+              <div class="ruleMatters_box">
+                <el-table :data="item.workItems" border>
+                  <el-table-column label="序号" width="50">
+                    <template slot-scope="scope">
+                      <span>{{ scope.$index + 1 }}</span>
+                    </template>
+                  </el-table-column>
+                  <el-table-column
+                    label="零部件编码"
+                    prop="categoryCode"
+                    width="100"
+                  >
+                    <template slot-scope="scope">
+                      <div>
+                        <span>{{ scope.row.categoryCode }}</span>
+                      </div>
+                    </template>
+                  </el-table-column>
+                  <el-table-column
+                    label="零部件名称"
+                    prop="categoryName"
+                    width="100"
+                  >
+                    <template slot-scope="scope">
+                      <div>
+                        <span>{{ scope.row.categoryName }}</span>
+                      </div>
+                    </template>
+                  </el-table-column>
+                  <el-table-column label="事项" prop="name" width="100">
+                    <template slot-scope="scope">
+                      <div>
+                        <span>{{ scope.row.name }}</span>
+                      </div>
+                    </template>
+                  </el-table-column>
+                  <el-table-column label="内容" prop="content" width="300">
+                    <template slot-scope="scope">
+                      <div>
+                        <span>{{ scope.row.content }}</span>
+                      </div>
+                    </template>
+                  </el-table-column>
+                  <el-table-column label="操作指导" prop="operationGuide">
+                    <template slot-scope="scope">
+                      <div class="operationGuide_box">
+                        <div class="left_content">
+                          <template v-if="scope.row.operationGuide">
+                            <div
+                              v-for="(item, index) in scope.row.operationGuide
+                                .toolList"
+                              :key="item.id"
+                              >{{ index + 1 }}.{{ item.name }}</div
+                            >
+                          </template>
+                        </div>
+                        <div class="line"></div>
+                        <div class="right_content">
+                          <template v-if="scope.row.operationGuide">
+                            <div
+                              v-for="(item, index) in scope.row.operationGuide
+                                .procedureList"
+                              :key="item.id"
+                              >{{ index + 1 }}.{{ item.content }}</div
+                            >
+                          </template>
+                        </div>
+                      </div>
+                    </template>
+                  </el-table-column>
+                  <el-table-column label="标准" prop="norm" width="100">
+                    <template slot-scope="scope">
+                      <div>
+                        <span>{{ scope.row.norm }}</span>
+                      </div>
+                    </template>
+                  </el-table-column>
+                  <el-table-column label="状态" prop="status" width="100">
+                    <template slot-scope="scope">
+                      <div>
+                        <span>{{ options[scope.row.status] }}</span>
+                      </div>
+                    </template>
+                  </el-table-column>
+                  <el-table-column label="结果" prop="result" width="200">
+                  </el-table-column>
+                </el-table>
+              </div>
+              <!-- <div class="matter_info">
+                <el-table :data="item.workItems || []" border>
+                  <el-table-column label="序号" align="center" width="80">
+                    <template slot-scope="scope">
+                      <span>{{ scope.$index + 1 }}</span>
+                    </template>
+                  </el-table-column>
+                  <el-table-column label="事项" prop="item" />
+                  <el-table-column label="内容" prop="content" />
+                  <el-table-column label="标准" prop="standard" />
+                </el-table>
+              </div> -->
+            </div>
+            <!-- <div class="btnbox" v-if="$route.query.isshow">
+              <el-button class="confirm-btn" type="danger" plain @click="reject"
+                >驳回</el-button
+              >
+              <el-button class="confirm-btn" type="success" plain @click="pass"
+                >通过</el-button
+              >
+              <el-button class="cancel-btn">关闭</el-button>
+            </div> -->
+            <!-- <div class="textbox" v-if="showtext">
+              <el-input
+                type="textarea"
+                placeholder="请输入驳回原因"
+                v-model="cause"
+                maxlength="30"
+                rows="5"
+                show-word-limit
+              >
+              </el-input>
+              <div class="textbtnbox">
+                <el-button size="small" round @click="cancelreject"
+                  >取消</el-button
+                >
+                <el-button size="small" round @click="surereject"
+                  >提交</el-button
+                >
+              </div>
+            </div> -->
+          </div>
+        </div>
+        <HeaderTitle title="备品备件申请单" size="16px"></HeaderTitle>
+        <editd :id="infoData.id" />
+
+        <!-- 巡点检、缺陷设备报修记录 -->
+        <!-- <div class="repair_notes">
+          <HeaderTitle title="缺陷设备报修记录" size="16px"></HeaderTitle>
+          <div class="repair_notes_equipment_item">
+            <el-row class="equipment_item_tilte">
+              <el-col :span="8">
+                <span class="label">设备名称:</span>
+                <span>{{ repairNotes.equiName }}</span>
+              </el-col>
+              <el-col :span="8">
+                <span class="label">规格型号:</span>
+                <span>{{ repairNotes.equiModel }}</span>
+              </el-col>
+              <el-col :span="8">
+                <span class="label">设备编码:</span>
+                <span>{{ repairNotes.equiCode }}</span>
+              </el-col>
+            </el-row>
+            <div class="main_info">
+              <div>
+                <span>报修记录编号:</span>
+                <span>{{ repairNotes.repairsCode }}</span>
+              </div>
+              <div>
+                <span>故障描述:</span>
+                <span>{{ repairNotes.repairsDescription }}</span>
+              </div>
+              <div>
+                <span>处理进度:</span>
+                <span>{{ statusObj[repairNotes.status] }}</span>
+              </div>
+            </div>
+          </div>
+        </div> -->
+      </div>
+    </el-form>
+  </div>
+</template>
+
+<script>
+  import dictMixins from '@/mixins/dictMixins';
+  import { getWordOrderDetail } from '@/api/maintenance/patrol_maintenance';
+  import editd from '@/views/sparePartsApply/components/editd';
+
+  export default {
+    components: {
+      editd
+    },
+    mixins: [dictMixins],
+    data() {
+      return {
+        options: {
+          0: '正常',
+          '-1': '缺陷'
+        },
+        num: 1,
+        infoData: {},
+        dialogVisible: false,
+        data: {},
+        repairNotes: {},
+        pageLoading: false,
+        typeValue: null,
+        contract_type: [],
+        status: [
+          {
+            value: true,
+            label: '失效'
+          },
+          {
+            value: false,
+            label: '生效'
+          }
+        ],
+        ruleItem: [],
+        cause: '',
+        showtext: false,
+        from: null
+      };
+    },
+    created() {
+      this.requestDict('巡点检周期');
+      this.getInfo();
+    },
+    methods: {
+      // getStatus: useDictLabel(patrolMatterStatus),
+      delete() {},
+      // 点击切换事件
+      tab(index) {
+        this.num = index;
+      },
+      goBack() {
+        window.sessionStorage.setItem('patrolTabType', 'work');
+        if (this.form) {
+          this.$router.push({
+            path: '/workspace/workOrder',
+            query: { activeName: 'polling' }
+          });
+        } else {
+          this.$router.go(-1);
+        }
+      },
+      // 表格数据
+      getInfo() {
+        this.pageLoading = true;
+        getWordOrderDetail(this.$route.query.id)
+          .then((data) => {
+            this.infoData = data;
+            // if (res.success) {
+            //   this.data = res.data;
+            //   this.data.planEquiList = this.data.planEquiList.filter(
+            //     (item) => item.itemList && item.itemList.length > 0
+            //   );
+            //   // 获取 缺陷设备报修记录
+            //   const repairId = res.data.planEquiList[0].repairId;
+            //   if (repairId) {
+            //     this.getRepairNotes(repairId);
+            //   }
+            // }
+            this.pageLoading = false;
+          })
+          .catch(() => {
+            this.pageLoading = false;
+          });
+      },
+      // 获取 缺陷设备报修记录
+      async getRepairNotes(repairId) {
+        const res = await repair.getInfo(repairId);
+        if (res?.success) {
+          console.log('缺陷设备报修记录:', res.data);
+          this.repairNotes = res.data;
+        }
+      },
+      //通过按钮事件
+      pass() {
+        let params = {
+          planId: this.$route.query.id,
+          checked: 2,
+          myHandleId: this.$route.query.dbid,
+          cause: this.cause,
+          type: 2, //1维修;2保养,巡点检
+          handleType: 0 //办理类型(0 审批 1 验收)
+        };
+        sendAudit(params).then((res) => {
+          if (res.success) {
+            this.$message.success('审批通过!');
+            this.$router.back();
+          }
+        });
+      },
+      //驳回按钮事件
+      reject() {
+        this.showtext = true;
+      },
+      cancelreject() {
+        this.showtext = false;
+        this.cause = '';
+      },
+      surereject() {
+        if (!this.cause) {
+          this.$message.info('请填写驳回原因!');
+        } else {
+          let params = {
+            id: this.$route.query.id,
+            checked: 0,
+            myHandleId: this.$route.query.dbid,
+            cause: this.cause,
+            type: 2, //1维修;2保养,巡点检
+            handleType: 0 //办理类型(0 审批 1 验收)
+          };
+          sendAudit(params).then((res) => {
+            if (res.success) {
+              this.$message.error('审批驳回!');
+              this.$router.back();
+            }
+          });
+        }
+      }
+    }
+  };
+</script>
+
+<style lang="scss" scoped>
+  // @import '@/assets/css/oaa.scss';
+  .page {
+    padding: 10px;
+  }
+  .page-title {
+    background: #fff;
+    font-size: 18px;
+    padding: 6px 20px;
+    font-weight: 500;
+    .page-title-div {
+      margin: 5px 0;
+      height: 30px;
+      line-height: 30px;
+      border-bottom: 1px solid #eaeefb;
+      .title-div-no {
+        margin-left: 10px;
+        font-weight: 400;
+        color: #909090;
+        font-size: 14px;
+      }
+    }
+  }
+  .page-data {
+    padding-top: 10px;
+  }
+  .content-detail {
+    background: #fff;
+    padding: 20px;
+  }
+  .flows {
+    .flow-left {
+      width: 156px;
+      height: 70px;
+      border: 1px dashed #ccc;
+      padding: 10px;
+    }
+    .row {
+      margin-top: 13px;
+    }
+  }
+  .basic-details-title {
+    margin-bottom: 12px;
+    margin-top: 20px;
+    border-bottom: 1px solid #1890ff;
+    padding-bottom: 8px;
+    display: flex;
+    justify-content: space-between;
+  }
+  .basic-details-title .border-span {
+    height: 18px;
+    font-size: 16px;
+    border-left: 4px solid #1890ff;
+    padding-left: 8px;
+
+    font-weight: 500;
+  }
+  .heade-right {
+    // float: right;
+    .heade-right-content {
+      margin-right: 12px;
+      font-size: 14px;
+      display: inline-block;
+      .content-key {
+        color: #3e3e3e;
+        margin-right: 12px;
+        font-weight: 500;
+      }
+      .content-value {
+        color: #000;
+      }
+    }
+  }
+  .list-title {
+    font-size: 14px;
+    color: #3e3e3e;
+    margin: 10px 0px;
+  }
+  .goods {
+    background: #a30014;
+    border: 1px solid #a30014;
+  }
+  .details-title {
+    display: inline-block;
+    color: #6e6e6e;
+    font-size: 14px;
+    font-weight: bold;
+    margin-right: 13px;
+    width: 70px;
+    text-align: right;
+  }
+  .details-con {
+    color: #3e3e3e;
+    font-size: 14px;
+  }
+  .detailed-tab {
+    margin-left: 10px;
+    margin-top: 10px;
+  }
+  ::v-deep .el-form-item--medium .el-form-item__label {
+    color: #6e6e6e;
+    font-size: 14px;
+    font-weight: bold;
+  }
+  .warehouse {
+    display: block;
+    border-bottom: 1px solid #eaeefb;
+    padding: 10px 0;
+  }
+  .box-card {
+    .store-box {
+      width: 80%;
+      .store-box-span {
+        display: inline-block;
+        font-size: 14px;
+        height: 50px;
+        width: 50px;
+        text-align: center;
+        line-height: 50px;
+        color: #fff;
+        margin: 2px;
+      }
+    }
+  }
+  .vacant {
+    background: #3196fb;
+  }
+  .inUse {
+    background: #157a2c;
+  }
+  .invalid {
+    background: #cccccc;
+  }
+  .full {
+    background: #cc3300;
+  }
+
+  .maintain_equipment_info {
+    .maintain_equipment_info_title {
+      border-bottom: 1px solid #1890ff;
+      padding-bottom: 3px;
+      margin-bottom: 20px;
+      > span {
+        display: inline-block;
+        line-height: 16px;
+        border-left: 6px solid #1890ff;
+        padding-left: 6px;
+      }
+    }
+    .maintain_equipment_info_content {
+      padding: 0 30px;
+      .equipment_item {
+        border: 1px solid #ccc;
+        font-size: 14px;
+        padding: 15px;
+        margin-bottom: 30px;
+        .equipment_info {
+          display: flex;
+          flex-wrap: wrap;
+          border: 1px solid #ddd;
+          .item_info {
+            width: 33.33%;
+            height: 24px;
+            line-height: 24px;
+            display: flex;
+            .item_label {
+              width: 90px;
+              text-align: center;
+              background-color: #f2f2f2;
+              font-weight: 700;
+            }
+            .item_value {
+              border-bottom: 1px solid #f2f2f2;
+              flex: 1;
+              padding-left: 5px;
+            }
+            &:last-child {
+              width: 100%;
+              .item_value {
+                border: 0;
+              }
+            }
+          }
+        }
+        > p {
+          margin-top: 20px;
+          color: #797979;
+        }
+        .matter_info {
+          ::v-deep .el-table {
+            th.el-table__cell {
+              background-color: #f2f2f2;
+              padding: 0;
+            }
+            td.el-table__cell {
+              padding: 0;
+            }
+          }
+        }
+        .ruleMatters_box {
+          flex: 3;
+          height: 100%;
+          display: flex;
+          flex-direction: column;
+          .divider {
+            flex: 0 0 50px;
+            .title {
+              height: 35px;
+            }
+          }
+          .el-table {
+            overflow: auto;
+            .operationGuide_box {
+              width: 100%;
+              display: flex;
+              position: relative;
+              .left_content {
+                flex: 0 0 300px;
+                padding: 10px;
+                margin-right: 10px;
+                overflow-y: auto;
+              }
+              .line {
+                position: absolute;
+                top: -10px;
+                left: 300px;
+                bottom: -10px;
+                height: 110%;
+                width: 1px;
+                background-color: #ededed;
+              }
+              .right_content {
+                flex: 1;
+                padding: 10px;
+                overflow-y: auto;
+              }
+            }
+          }
+        }
+      }
+    }
+  }
+  .execute_info {
+    margin: 30px 0;
+    .execute_info_title {
+      border-bottom: 1px solid #1890ff;
+      padding-bottom: 3px;
+      margin-bottom: 20px;
+      display: flex;
+      justify-content: space-between;
+      > span:first-child {
+        line-height: 16px;
+        border-left: 6px solid #1890ff;
+        padding-left: 6px;
+      }
+    }
+    .execute_row {
+      padding: 0 30px;
+      .column {
+        display: flex;
+        font-size: 14px;
+        margin-bottom: 20px;
+        .label {
+          // width: 110px;
+          text-align: center;
+          font-weight: 700;
+        }
+      }
+    }
+  }
+  .repair_notes {
+    .repair_notes_title {
+      border-bottom: 1px solid #1890ff;
+      padding-bottom: 3px;
+      margin-bottom: 20px;
+      > span {
+        display: inline-block;
+        line-height: 16px;
+        border-left: 6px solid #1890ff;
+        padding-left: 6px;
+      }
+    }
+    .repair_notes_equipment_item {
+      padding: 0 20px;
+      .equipment_item_tilte {
+        background-color: #f7f7f7;
+        height: 36px;
+        line-height: 36px;
+        .label {
+          font-weight: 700;
+        }
+      }
+      .main_info {
+        font-size: 14px;
+        margin-top: 15px;
+        > div {
+          margin-bottom: 10px;
+        }
+      }
+    }
+  }
+  .btnbox {
+    display: flex;
+    justify-content: center;
+  }
+  ::v-deep .el-button {
+    padding: 10px 20px;
+    margin-right: 10px;
+  }
+  .textbtnbox {
+    margin-top: 10px;
+    display: flex;
+    justify-content: center;
+  }
+</style>

+ 286 - 0
src/views/maintenance/runRecord/workOrder/index.vue

@@ -0,0 +1,286 @@
+<template>
+  <div class="ele-body">
+    <el-card shadow="never" v-loading="loading">
+      <work-search @search="reload"> </work-search>
+      <!-- 数据表格 -->
+      <!-- :default-sort="{ prop: 'createTime', order: 'descending' }" -->
+      <ele-pro-table
+        ref="table"
+        :columns="columns"
+        :datasource="datasource"
+        cache-key="patrolOrderTable"
+      >
+        <template v-slot:code="{ row }">
+          <el-link type="primary" @click="goDetail(row)">
+            {{ row.code }}
+          </el-link>
+        </template>
+        <!-- 操作列 -->
+        <template v-slot:action="{ row }">
+          <el-link
+            v-if="row.orderStatus === 3"
+            type="primary"
+            :underline="false"
+            @click="handleExport(row)"
+          >
+            预览打印
+          </el-link>
+          <el-link
+            v-if="row.orderStatus !== 3 && row.orderStatus !== 4"
+            type="primary"
+            :underline="false"
+            icon="el-icon-truck"
+            @click="addSpareItems(row)"
+          >
+            申请备品备件
+          </el-link>
+          <el-link
+            v-if="row.orderStatus !== 3 && row.orderStatus !== 4"
+            type="primary"
+            :underline="false"
+            icon="el-icon-edit"
+            @click="toSigningUpWork(row)"
+          >
+            报工
+          </el-link>
+          <el-link
+            v-if="
+              row.orderStatus !== 3 && row.orderStatus !== 4 && row.isGroup != 1
+            "
+            type="primary"
+            :underline="false"
+            icon="el-icon-edit"
+            @click="toRedeploy(row)"
+          >
+            转派
+          </el-link>
+        </template>
+      </ele-pro-table>
+    </el-card>
+    <!-- 转派弹窗 -->
+    <redeployOther ref="redeployOtherRef" @refresh="reload" />
+    <!-- 报工弹框 -->
+    <signingUpWork ref="signingUpWorkRef" @refresh="reload" />
+    <edit @refresh="reload" ref="edit" />
+  </div>
+</template>
+
+<script>
+  import edit from '@/views/sparePartsApply/components/edit';
+  import WorkSearch from './components/work-search.vue';
+  import redeployOther from '@/views/maintenance/components/redeployOther.vue';
+  import signingUpWork from '@/views/maintenance/components/signingUpWork.vue';
+  import {
+    getWorkOrderPage,
+    getWordOrderDetail
+  } from '@/api/maintenance/patrol_maintenance';
+
+  import dictMixins from '@/mixins/dictMixins';
+
+  import { getToken } from '@/utils/token-util';
+  export default {
+    components: {
+      WorkSearch,
+      redeployOther,
+      signingUpWork,
+      edit
+    },
+    mixins: [dictMixins],
+    data() {
+      return {
+        // 表格列配置
+        columns: [
+          {
+            columnKey: 'index',
+            label: '序号',
+            type: 'index',
+            width: 55,
+            align: 'center',
+            showOverflowTooltip: true,
+            fixed: 'left'
+          },
+          {
+            columnKey: 'code',
+            slot: 'code',
+            prop: 'code',
+            label: '工单单号',
+            align: 'center',
+            showOverflowTooltip: true,
+            minWidth: 140
+          },
+          {
+            prop: 'planCode',
+            label: '计划单号',
+            align: 'center',
+            showOverflowTooltip: true,
+            minWidth: 140
+          },
+          {
+            prop: 'planName',
+            label: '巡点检名称',
+            align: 'center',
+            showOverflowTooltip: true,
+            minWidth: 120
+          },
+          {
+            prop: 'executeGroupName',
+            label: '巡点检部门',
+            align: 'center',
+            showOverflowTooltip: true,
+            minWidth: 120
+          },
+          {
+            prop: 'executeUserName',
+            label: '巡点检人员',
+            align: 'center',
+            showOverflowTooltip: true
+          },
+          {
+            prop: 'ruleName',
+            label: '规则名称',
+            align: 'center',
+            showOverflowTooltip: true
+          },
+          {
+            prop: 'createTime',
+            label: '工单生成时间',
+            align: 'center',
+            // sortable: true,
+            showOverflowTooltip: true,
+            width: 170
+          },
+          {
+            prop: 'acceptTime',
+            label: '开工时间',
+            align: 'center',
+            showOverflowTooltip: true
+          },
+          {
+            prop: 'finishTime',
+            label: '报工时间',
+            align: 'center',
+            showOverflowTooltip: true
+          },
+          {
+            columnKey: 'orderHour',
+            label: '实际工时(分钟)',
+            align: 'center',
+            resizable: false,
+            showOverflowTooltip: true,
+            minWidth: 120,
+            formatter: (row) => {
+              if (row.finishTime && row.acceptTime) {
+                return parseInt(
+                  (new Date(row.finishTime).getTime() -
+                    new Date(row.acceptTime).getTime()) /
+                    60000
+                );
+              }
+            }
+          },
+          {
+            prop: 'orderStatus',
+            label: '状态',
+            align: 'center',
+            showOverflowTooltip: true,
+            formatter: (row) => {
+              return {
+                0: '待接收',
+                1: '已接收',
+                2: '执行中',
+                3: '已完成'
+              }[row.orderStatus];
+            }
+          },
+          {
+            prop: 'acceptanceStatus',
+            label: '执行结果',
+            align: 'center',
+            showOverflowTooltip: true,
+            formatter(row) {
+              return { 0: '缺陷', 1: '正常' }[row.isAbnormal];
+            }
+          },
+          {
+            columnKey: 'action',
+            label: '操作',
+            width: 240,
+            align: 'center',
+            resizable: false,
+            slot: 'action',
+            showOverflowTooltip: true
+          }
+        ],
+        // 加载状态
+        loading: false,
+        pageType: 'add',
+        dialogTitle: '',
+        isBindPlan: false
+      };
+    },
+    created() {
+      this.requestDict('巡点检工单状态');
+    },
+    computed: {},
+    methods: {
+      /* 表格数据源 */
+      datasource({ page, limit, where, order }) {
+        return getWorkOrderPage({
+          pageNum: page,
+          size: limit,
+          ...where,
+          type: 6
+        });
+      },
+      async changeEnable(row) {
+        const res = await putRoles(row);
+        if (res.code == 0) {
+          this.$message({
+            type: 'success',
+            message: '修改成功',
+            customClass: 'ele-message-border'
+          });
+          this.reload();
+        }
+      },
+      /* 刷新表格 */
+      reload(where) {
+        this.$refs.table.reload({ page: 1, where });
+      },
+
+      // 添加备品备件
+      async addSpareItems(row) {
+        let data = await getWordOrderDetail(row.id);
+        data.deviceList = data.deviceList.map((item) => {
+          return item.substance;
+        });
+
+        this.$refs.edit.open(data, 'add');
+      },
+      goDetail({ id }) {
+        this.$router.push({
+          path: '/maintenance/patrol/workOrder/details',
+          query: {
+            id
+          }
+        });
+      },
+      // 转派
+      toRedeploy(row) {
+        this.$refs.redeployOtherRef.open(row);
+      },
+      // 报工
+      toSigningUpWork(row) {
+        this.$refs.signingUpWorkRef.open(row);
+      },
+      handleExport(row) {
+        const url = `http://192.168.120.128:8085/jmreport/view/1060046036862939136?token=${getToken()}&id=${
+          row.id
+        }`;
+        window.open(url, '_blank');
+      }
+    }
+  };
+</script>
+
+<style lang="scss" scoped></style>