Procházet zdrojové kódy

Merge remote-tracking branch 'origin/master' into demo_

hfxc226 před 2 roky
rodič
revize
ddcb921475
75 změnil soubory, kde provedl 4436 přidání a 794 odebrání
  1. 2 1
      .gitignore
  2. 18 0
      src/api/check/checkjob.js
  3. 127 0
      src/api/customize/report.js
  4. 100 0
      src/api/report/application-form.js
  5. 37 0
      src/api/report/template.js
  6. 31 0
      src/api/sqarepartmanage/sparepartinfo.js
  7. 12 0
      src/api/upms/code.js
  8. 9 0
      src/api/upms/file.js
  9. 52 52
      src/components/Table/index.js
  10. 4 4
      src/components/Upload/UploadSpareFile.vue
  11. 3 0
      src/components/custom/Badge.vue
  12. 1 1
      src/components/custom/ImgCode.vue
  13. 23 9
      src/router/generator-platform-routers.js
  14. 38 1
      src/utils/dict.js
  15. 10 0
      src/views/check/checkjob/CheckJob.vue
  16. 113 0
      src/views/check/checkjob/modules/ImportFormUpdate.vue
  17. 61 5
      src/views/check/checkstandard/CheckStandard.vue
  18. 18 0
      src/views/check/checkstandard/modules/DetailSbCheck.vue
  19. 297 0
      src/views/customize/report/CustomizeReport.vue
  20. 214 0
      src/views/customize/report/modules/BaseForm.vue
  21. 297 0
      src/views/customize/report/modules/CustomizeReportSelectModal.vue
  22. 83 0
      src/views/customize/report/modules/Detail.vue
  23. 194 0
      src/views/customize/report/modules/ParameterModal.vue
  24. 68 26
      src/views/dashboard/CheckJobReport.vue
  25. 1 0
      src/views/dashboard/CheckJobReportWeek.vue
  26. 280 0
      src/views/dashboard/RepairReportSbInfo.vue
  27. 281 0
      src/views/dashboard/RepairReportSbInfoFee.vue
  28. 214 0
      src/views/dashboard/template/ChartReport.vue
  29. 0 1
      src/views/operate/article/Article.vue
  30. 36 3
      src/views/operate/article/modules/BaseForm.vue
  31. 304 305
      src/views/purchase/supplier-goods-list/modules/SupplierGoodsListSelectModal.vue
  32. 17 5
      src/views/repair/application-form/RepairApplicationForm.vue
  33. 2 2
      src/views/repair/application-form/RepairCheckForm.vue
  34. 2 11
      src/views/repair/application-form/RepairForm.vue
  35. 3 3
      src/views/repair/application-form/modules/BaseForm.vue
  36. 6 6
      src/views/repair/application-form/modules/Detail.vue
  37. 4 4
      src/views/repair/application-form/modules/DetailCheck.vue
  38. 15 17
      src/views/repair/application-form/modules/DetailRepair.vue
  39. 1 1
      src/views/repair/application-form/modules/EditForm.vue
  40. 89 2
      src/views/repair/fee/RepairFee.vue
  41. 27 28
      src/views/report/instorecount/InStoreCount.vue
  42. 1 1
      src/views/report/instoredetail/InStoreDetail.vue
  43. 71 10
      src/views/sb/info/SbInfo.vue
  44. 6 4
      src/views/sb/info/modules/BaseForm.vue
  45. 21 3
      src/views/sb/info/modules/Detail.vue
  46. 1 1
      src/views/sb/info/modules/PrintInSbInfoBatch.vue
  47. 59 14
      src/views/sb/measure/MeasureSbInfo.vue
  48. 1 1
      src/views/sb/measure/MeasureSbInfoWarn.vue
  49. 14 2
      src/views/sb/measure/modules/BaseForm.vue
  50. 1 0
      src/views/sb/measure/modules/Detail.vue
  51. 23 1
      src/views/sb/measurelog/modules/BaseForm.vue
  52. 4 1
      src/views/sb/measurelog/modules/DetailSbCheck.vue
  53. 75 7
      src/views/sqarepartmanage/sparepartinfo/SparePartInfo.vue
  54. 25 25
      src/views/sqarepartmanage/sparepartinfo/SparePartInfoSbModel.vue
  55. 295 0
      src/views/sqarepartmanage/sparepartinfo/SpareStoreTotal.vue
  56. 19 0
      src/views/sqarepartmanage/sparepartinfo/SpareStoreTotalCheckStock.vue
  57. 19 0
      src/views/sqarepartmanage/sparepartinfo/SpareStoreTotalMinStock.vue
  58. 58 16
      src/views/sqarepartmanage/sparepartinfo/modules/BaseForm.vue
  59. 8 10
      src/views/sqarepartmanage/sparepartinfo/modules/Detail.vue
  60. 322 0
      src/views/sqarepartmanage/sparepartinfo/modules/PrintInSpareBatch.vue
  61. 19 0
      src/views/sqarepartmanage/sparepartinfo/modules/SparePartInfoSelectModal.vue
  62. 9 9
      src/views/store/instoredetail/InStoreDetail.vue
  63. 32 18
      src/views/store/instoreform/modules/BaseForm.vue
  64. 4 2
      src/views/store/outstoredetail/OutStoreDetail.vue
  65. 34 14
      src/views/store/outstoreform/modules/BaseForm.vue
  66. 3 3
      src/views/store/outstoreform/modules/Detail.vue
  67. 0 17
      src/views/store/sparestore/CompanySpareStore.vue
  68. 0 17
      src/views/store/sparestore/CompanySpareStoreTotal.vue
  69. 0 17
      src/views/store/sparestore/ProjectSpareStore.vue
  70. 0 17
      src/views/store/sparestore/ProjectSpareStoreTotal.vue
  71. 12 8
      src/views/store/sparestore/SpareStore.vue
  72. 94 64
      src/views/store/sparestore/SpareStoreTotal.vue
  73. 19 0
      src/views/store/sparestore/SpareStoreTotalMinStock.vue
  74. 29 15
      src/views/store/sparestore/modules/BaseForm.vue
  75. 64 10
      src/views/store/sparestore/modules/SpareStoreSelectModal.vue

+ 2 - 1
.gitignore

@@ -7,4 +7,5 @@
 *.fatbin
 
 /node_modules/
-/.idea/
+/.idea/
+/dist/

+ 18 - 0
src/api/check/checkjob.js

@@ -237,3 +237,21 @@ export function finishJobBatch (parameter) {
     data: parameter
   })
 }
+
+/**
+ * add batch func
+ * parameter: { }
+ * @param parameter
+ * @returns {*}
+ */
+export function importCheckJobForUpdate (parameter) {
+  return axios({
+    url: '/check/jobs/import/update',
+    method: 'POST',
+    headers: {
+      'Accept': 'application/json',
+      'Content-Type': 'application/json;charset=UTF-8'
+    },
+    data: parameter
+  })
+}

+ 127 - 0
src/api/customize/report.js

@@ -0,0 +1,127 @@
+import { axios } from '@/utils/request'
+import { stringify } from 'qs'
+
+/**
+ * page func
+ * parameter: { }
+ * @param parameter
+ * @returns {*}
+ */
+export function getCustomizeReportPage (parameter) {
+  return axios({
+    url: '/customize/reports/page?' + stringify(parameter),
+    method: 'get',
+    headers: {
+      'Content-Type': 'application/json;charset=UTF-8'
+    }
+  })
+}
+
+/**
+ * add func
+ * parameter: { }
+ * @param parameter
+ * @returns {*}
+ */
+export function addCustomizeReport (parameter) {
+  return axios({
+    url: '/customize/reports',
+    method: 'POST',
+    headers: {
+      'Accept': 'application/json',
+      'Content-Type': 'application/json;charset=UTF-8'
+    },
+    data: parameter
+  })
+}
+
+/**
+ * update func
+ * parameter: { }
+ * @param parameter
+ * @returns {*}
+ */
+export function updateCustomizeReport (parameter) {
+  return axios({
+    url: '/customize/reports/' + parameter.id,
+    method: 'PUT',
+    data: parameter
+  })
+}
+
+/**
+ * fetch single func
+ * parameter: { }
+ * @param parameter
+ * @returns {*}
+ */
+export function fetchCustomizeReport (parameter) {
+  return axios({
+    url: '/customize/reports/' + parameter.id,
+    method: 'get',
+    headers: {
+      'Content-Type': 'application/json;charset=UTF-8'
+    }
+  })
+}
+
+/**
+ * query list func
+ * parameter: { }
+ * @param parameter
+ * @returns {*}
+ */
+export function queryCustomizeReport (parameter) {
+  return axios({
+    url: '/customize/reports?' + stringify(parameter),
+    method: 'get',
+    headers: {
+      'Content-Type': 'application/json;charset=UTF-8'
+    }
+  })
+}
+
+/**
+ * delete batch func
+ * parameter: { }
+ * @param parameter
+ * @returns {*}
+ */
+export function deleteCustomizeReports (parameter) {
+  return axios({
+    url: '/customize/reports',
+    method: 'DELETE',
+    data: parameter
+  })
+}
+
+/**
+ * delete single func
+ * parameter: { }
+ * @param parameter
+ * @returns {*}
+ */
+export function deleteCustomizeReport (parameter) {
+  return axios({
+    url: '/customize/reports/' + parameter.id,
+    method: 'DELETE',
+    data: parameter
+  })
+}
+
+/**
+ * export file
+ * parameter: { }
+ * @param parameter :
+ * @returns {*}
+ */
+export function exportCustomizeReport (parameter) {
+  return axios({
+    url: '/customize/reports/export?' + stringify(parameter),
+    method: 'get',
+    headers: {
+      'Content-Type': 'application/json;charset=UTF-8'
+    },
+    responseType: 'blob'
+  })
+}

+ 100 - 0
src/api/report/application-form.js

@@ -51,6 +51,106 @@ export function exportMonthReportBig24Month (parameter) {
   })
 }
 
+/**
+ * page func
+ * parameter: { }
+ * @param parameter
+ * @returns {*}
+ */
+export function getSbInfoReport (parameter) {
+  return axios({
+    url: '/report/repair/sbInfo?' + stringify(parameter),
+    method: 'get',
+    headers: {
+      'Content-Type': 'application/json;charset=UTF-8'
+    }
+  })
+}
+
+/**
+ * export file
+ * parameter: { }
+ * @param parameter :
+  * @returns {*}
+ */
+export function exportSbInfoReport (parameter) {
+  return axios({
+    url: '/report/repair/sbInfo/export?' + stringify(parameter),
+    method: 'get',
+    headers: {
+      'Content-Type': 'application/json;charset=UTF-8'
+    },
+    responseType: 'blob'
+  })
+}
+
+/**
+ * export file
+ * parameter: { }
+ * @param parameter :
+  * @returns {*}
+ */
+export function exportSbInfoReportYear (parameter) {
+  return axios({
+    url: '/report/repair/sbInfo/export/year?' + stringify(parameter),
+    method: 'get',
+    headers: {
+      'Content-Type': 'application/json;charset=UTF-8'
+    },
+    responseType: 'blob'
+  })
+}
+
+/**
+ * page func
+ * parameter: { }
+ * @param parameter
+ * @returns {*}
+ */
+export function getSbInfoReportFee (parameter) {
+  return axios({
+    url: '/report/repair/sbInfo/fee?' + stringify(parameter),
+    method: 'get',
+    headers: {
+      'Content-Type': 'application/json;charset=UTF-8'
+    }
+  })
+}
+
+/**
+ * export file
+ * parameter: { }
+ * @param parameter :
+  * @returns {*}
+ */
+export function exportSbInfoReportFee (parameter) {
+  return axios({
+    url: '/report/repair/sbInfo/fee/export?' + stringify(parameter),
+    method: 'get',
+    headers: {
+      'Content-Type': 'application/json;charset=UTF-8'
+    },
+    responseType: 'blob'
+  })
+}
+
+/**
+ * export file
+ * parameter: { }
+ * @param parameter :
+  * @returns {*}
+ */
+export function exportSbInfoReportFeeYear (parameter) {
+  return axios({
+    url: '/report/repair/sbInfo/fee/export/year?' + stringify(parameter),
+    method: 'get',
+    headers: {
+      'Content-Type': 'application/json;charset=UTF-8'
+    },
+    responseType: 'blob'
+  })
+}
+
 /**
  * page func
  * parameter: { }

+ 37 - 0
src/api/report/template.js

@@ -0,0 +1,37 @@
+import { axios } from '@/utils/request'
+import { stringify } from 'qs'
+
+/**
+ * 导出报表
+ * page func
+ * parameter: { }
+ * @param parameter
+ * @returns {*}
+ */
+export function getChartReport (parameter) {
+  return axios({
+    url: parameter.sqlVal,
+    method: 'get',
+    headers: {
+      'Content-Type': 'application/json;charset=UTF-8'
+    }
+  })
+}
+
+/**
+ * 导出模板报表
+ * export file
+ * parameter: { }
+ * @param parameter :
+  * @returns {*}
+ */
+export function exportChartReport (parameter) {
+  return axios({
+    url: parameter.url + '/export?' + stringify(parameter),
+    method: 'get',
+    headers: {
+      'Content-Type': 'application/json;charset=UTF-8'
+    },
+    responseType: 'blob'
+  })
+}

+ 31 - 0
src/api/sqarepartmanage/sparepartinfo.js

@@ -17,6 +17,23 @@ export function getSparePartInfoPage (parameter) {
   })
 }
 
+/**
+ * fetch single func
+ * parameter: { }
+ * @param parameter
+ * @returns {*}
+ */
+export function fetchSparePartInfos (parameter) {
+  return axios({
+    url: '/sqarepartmanage/spare-part-info/code/batch',
+    method: 'POST',
+    headers: {
+      'Content-Type': 'application/json;charset=UTF-8'
+    },
+    data: parameter
+  })
+}
+
 /**
  * page func
  * parameter: { }
@@ -65,6 +82,20 @@ export function updateSparePartInfo (parameter) {
   })
 }
 
+/**
+ * update func
+ * parameter: { }
+ * @param parameter
+ * @returns {*}
+ */
+export function updateSparePartInfoWarnStatus (parameter) {
+  return axios({
+    url: '/sqarepartmanage/spare-part-info/status/' + parameter.id + '/' + parameter.type + '/' + parameter.warnStatus,
+    method: 'PUT',
+    data: parameter
+  })
+}
+
 /**
  * fetch single func
  * parameter: { }

+ 12 - 0
src/api/upms/code.js

@@ -23,3 +23,15 @@ export function generateSbCodeAll (parameter) {
     data: parameter
   })
 }
+
+export function generateSpareCodeAll (parameter) {
+  return axios({
+    url: `/upms/codes/spare/all`,
+    method: 'POST',
+    headers: {
+      'Accept': 'application/json',
+      'Content-Type': 'application/json;charset=UTF-8'
+    },
+    data: parameter
+  })
+}

+ 9 - 0
src/api/upms/file.js

@@ -42,6 +42,15 @@ export function uploadFile (parameter) {
   })
 }
 
+export function uploadFileSpare (parameter) {
+  return axios({
+    url: `/upms/files/upload/spare`,
+    method: 'POST',
+    headers: { 'Content-Type': 'application/x-www-form-urlencoded' },
+    data: parameter
+  })
+}
+
 export function downloadFile (url) {
   const storeToken = Vue.ls.get(ACCESS_TOKEN)
   request.post(process.env.VUE_APP_API_BASE_URL + url, null, {

+ 52 - 52
src/components/Table/index.js

@@ -195,19 +195,19 @@ export default {
     loadData (pagination, filters, sorter) {
       this.localLoading = true
       const parameter = Object.assign({
-          pageNum: (pagination && pagination.current) ||
+        pageNum: (pagination && pagination.current) ||
             this.showPagination && this.localPagination.current || this.pageNum,
-          pageSize: (pagination && pagination.pageSize) ||
+        pageSize: (pagination && pagination.pageSize) ||
             this.showPagination && this.localPagination.pageSize || this.pageSize
-        },
-        (sorter && sorter.field && {
-          sortField: sorter.field
-        }) || {},
-        (sorter && sorter.order && {
-          sortOrder: sorter.order
-        }) || {}, {
-          ...filters
-        }
+      },
+      (sorter && sorter.field && {
+        sortField: sorter.field
+      }) || {},
+      (sorter && sorter.order && {
+        sortOrder: sorter.order
+      }) || {}, {
+        ...filters
+      }
       )
       const result = this.data(parameter)
       // 对接自己的通用数据接口需要修改下方代码中的 r.pageNo, r.totalCount, r.data
@@ -292,10 +292,10 @@ export default {
       if (this.selectedRowKeys.length <= 0) return null
       return (
         <a style="margin-left: 24px" onClick={() => {
-        callback()
-        this.clearSelected()
-      }}>清空</a>
-    )
+          callback()
+          this.clearSelected()
+        }}>清空</a>
+      )
     },
     /** myColumns
      * 处理交给 table 使用者去处理 clear 事件时,内部选中统计同时调用
@@ -314,38 +314,38 @@ export default {
         treeData.push({ title: item.title,
           key: item.title })
       })
-      //const choose=this.$t('m.common.choose_show_column')
+      // const choose=this.$t('m.common.choose_show_column')
       return (
         <a style="margin-left: 24px" onClick={() => {
-      }}>
+        }}>
 
-    <a-popover placement="bottom">
-        <template slot="content">
-        <a-tree
-      checkable={true}
-      onCheck={(checkedKeys) => {
-        Object.keys(this.checkCustomMap).forEach((key) => {
-          const item = this.checkCustomMap[key]
-          item.checked = false
-        })
-        checkedKeys.forEach((item) => {
-          this.checkCustomMap[item].checked = true
-        })
-        // 重新渲染render ()函数
-        this.$forceUpdate()
-      }}
-      onSelect={(selectedKeys, info) => {
-      }}
-      checkedKeys={checkedKeys}
-      treeData={treeData} />
-      </template>
-      <template slot="title">
-        <span>选择显示列</span>
-        </template>
-        <a-icon type="appstore" />
-        </a-popover>
+          <a-popover placement="bottom">
+            <template slot="content">
+              <a-tree
+                checkable={true}
+                onCheck={(checkedKeys) => {
+                  Object.keys(this.checkCustomMap).forEach((key) => {
+                    const item = this.checkCustomMap[key]
+                    item.checked = false
+                  })
+                  checkedKeys.forEach((item) => {
+                    this.checkCustomMap[item].checked = true
+                  })
+                  // 重新渲染render ()函数
+                  this.$forceUpdate()
+                }}
+                onSelect={(selectedKeys, info) => {
+                }}
+                checkedKeys={checkedKeys}
+                treeData={treeData} />
+            </template>
+            <template slot="title">
+              <span>选择显示列</span>
+            </template>
+            <a-icon type="appstore" />
+          </a-popover>
         </a>
-    )
+      )
     },
     renderAlert () {
       // 绘制统计列数据
@@ -362,18 +362,18 @@ export default {
         this.renderClear(this.alert.clear)
       ) : null
       const renderColumns = this.renderColumns()
-      //const ss = this.$t('m.common.choose_total')
+      // const ss = this.$t('m.common.choose_total')
       // 绘制 alert 组件
       return (
         <a-alert showIcon={true} style="margin-bottom: 16px">
-        <template slot="message">
-        <span style="margin-right: 12px">已选择:<a style="font-weight: 600">{this.selectedRows.length}</a></span>
-      {needTotalItems}
-      {clearItem}
-      {renderColumns}
-    </template>
-      </a-alert>
-    )
+          <template slot="message">
+            <span style="margin-right: 12px">已选择:<a style="font-weight: 600">{this.selectedRows.length}</a></span>
+            {needTotalItems}
+            {clearItem}
+            {renderColumns}
+          </template>
+        </a-alert>
+      )
     }
   },
 

+ 4 - 4
src/components/Upload/UploadSpareFile.vue

@@ -1,7 +1,7 @@
 <template>
   <div class="clearfix">
     <a-upload
-      action="action"
+      :action="action"
       listType="picture-card"
       :fileList="fileList"
       @change="handleChange"
@@ -21,13 +21,13 @@
 </template>
 
 <script>
-import { uploadFile } from '@/api/upms/file'
+import { uploadFileSpare } from '@/api/upms/file'
 export default {
   name: 'UploadSpareImg',
   data () {
     return {
       previewVisible: false,
-      action: process.env.VUE_APP_API_BASE_URL + '/upms/files/upload',
+      action: '/upms/files/upload/spare',
       maxSize: 1,
       previewImage: '',
       fileList: []
@@ -54,7 +54,7 @@ export default {
       formData.append('file', data.file)
       data.onProgress()
       const that = this
-      uploadFile(formData).then(res => {
+      uploadFileSpare(formData).then(res => {
         data.onSuccess()
         that.fileList.push({
           uid: '-1',

+ 3 - 0
src/components/custom/Badge.vue

@@ -41,6 +41,9 @@ export default {
       if (this.status === 'warning') {
         myShowStyle = { ...myShowStyle, ...{ backgroundColor: '#faad14' } }
       }
+      if (this.status === 'gray') {
+        myShowStyle = { ...myShowStyle, ...{ backgroundColor: '#7F7D77FF' } }
+      }
       myShowStyle = { ...myShowStyle, ...this.numberStyle }
       return myShowStyle
     }

+ 1 - 1
src/components/custom/ImgCode.vue

@@ -39,7 +39,7 @@ export default {
       type: String,
       default: ''
     },
-    type: { // 1.表示设备
+    type: { // 1.表示设备,2:备件
       type: Number,
       default: 1
     },

+ 23 - 9
src/router/generator-platform-routers.js

@@ -103,8 +103,12 @@ const constantRouterComponents = {
   'SpareType': () => import('@/views/sqarepartmanage/sparetype/SpareType'),
   // 备件基础信息
   'SparePartInfo': () => import('@/views/sqarepartmanage/sparepartinfo/SparePartInfo'),
-  'SparePartInfoCheckWarn': () => import('@/views/sqarepartmanage/sparepartinfo/SparePartInfoCheckWarn'),
+  'SparePartInfoCheckWarn': () => import('@/views/sqarepartmanage/sparepartinfo/SpareStoreTotalCheckStock'),
   'SparePartInfoPrint': () => import('@/views/sqarepartmanage/sparepartinfo/SparePartInfoPrint'),
+  // 备件库存汇总
+  'SpareStoreTotal': () => import('@/views/sqarepartmanage/sparepartinfo/SpareStoreTotal'),
+  // 备件库存汇总预警
+  'SpareStoreTotalMinStock': () => import('@/views/sqarepartmanage/sparepartinfo/SpareStoreTotalMinStock'),
   // 备件使用信息
   'SparePartUsed': () => import('@/views/sqarepartmanage/sparepartused/SparePartUsed'),
   // 点检
@@ -138,8 +142,6 @@ const constantRouterComponents = {
   'Store': () => import('@/views/store/store/Store'),
   // 备件库存
   'SpareStore': () => import('@/views/store/sparestore/SpareStore'),
-  // 备件库存汇总
-  'SpareStoreTotal': () => import('@/views/store/sparestore/SpareStoreTotal'),
   // 备件二级库存
   'SpareStoreSecond': () => import('@/views/store/sparestoresecond/SpareStoreSecond'),
   // 入库登记单
@@ -273,10 +275,6 @@ const constantRouterComponents = {
   'CompanySbInfo': () => import('@/views/sb/info/CompanySbInfo'),
   'MySpareStore': () => import('@/views/store/sparestore/MySpareStore'),
   'MySpareStoreTotal': () => import('@/views/store/sparestore/MySpareStoreTotal'),
-  'ProjectSpareStoreTotal': () => import('@/views/store/sparestore/ProjectSpareStoreTotal'),
-  'CompanySpareStoreTotal': () => import('@/views/store/sparestore/CompanySpareStoreTotal'),
-  'ProjectSpareStore': () => import('@/views/store/sparestore/ProjectSpareStore'),
-  'CompanySpareStore': () => import('@/views/store/sparestore/CompanySpareStore'),
   'MyRunCheckJob': () => import('@/views/check/checkjob/MyRunCheckJob'),
   'MyPollingCheckJob': () => import('@/views/check/checkjob/MyPollingCheckJob'),
   'MyPollingCheckJobFinish': () => import('@/views/check/checkjob/MyPollingCheckJobFinish'),
@@ -327,8 +325,13 @@ const constantRouterComponents = {
   'CheckJobReportWeek': () => import('@/views/dashboard/CheckJobReportWeek'), // 保养任务周工作负荷统计报表
   'RepairReport': () => import('@/views/dashboard/RepairReport'), // >24小时停机次数按月统计
   'RepairReportSbAll': () => import('@/views/dashboard/RepairReportSbAll'), // 设备故障次数按月统计
+  'RepairReportSbInfo': () => import('@/views/dashboard/RepairReportSbInfo'), // 设备维修报表
+  'RepairReportSbInfoFee': () => import('@/views/dashboard/RepairReportSbInfoFee'), // 设备维修费用报表
   'RepairReportMttr': () => import('@/views/dashboard/RepairReportMttr'), // MTTR月统计报表
-  'RepairReportFee': () => import('@/views/dashboard/RepairReportFee') // 费用按月统计
+  'RepairReportFee': () => import('@/views/dashboard/RepairReportFee'), // 费用按月统计
+
+  // 自定义管理
+  'CustomizeReport': () => import('@/views/customize/report/CustomizeReport') // 自定义报表
 }
 
 // 前端未找到页面路由(固定不用改)
@@ -425,7 +428,18 @@ export const constantRouterMap = [
       }
     ]
   },
-
+  {
+    path: '/chartReport',
+    component: BlankLayout,
+    redirect: '/chart/report',
+    children: [
+      {
+        path: 'ChartReport',
+        name: 'ChartReport',
+        component: () => import('@/views/dashboard/template/ChartReport')
+      }
+    ]
+  },
   {
     path: '/404',
     component: () => import(/* webpackChunkName: "fail" */ '@/views/exception/404')

+ 38 - 1
src/utils/dict.js

@@ -69,6 +69,10 @@ DictCache.TYPE = {
   SB_QR_CODE_LABEL_CONTENT_WIDTH: 'SB_QR_CODE_LABEL_CONTENT_WIDTH', // 设备标签表格宽度
   SB_QR_CODE_LABEL_CONTENT_HEIGHT: 'SB_QR_CODE_LABEL_CONTENT_HEIGHT', // 设备标签表格高度
   SB_QR_CODE_LABEL_IMG_WIDTH: 'SB_QR_CODE_LABEL_IMG_WIDTH', // 设备标签二维码宽度
+  SPARE_QR_CODE_LABEL_WIDTH: 'SPARE_QR_CODE_LABEL_WIDTH', // 备件标签宽度
+  SPARE_QR_CODE_LABEL_CONTENT_WIDTH: 'SPARE_QR_CODE_LABEL_CONTENT_WIDTH', // 备件标签表格宽度
+  SPARE_QR_CODE_LABEL_CONTENT_HEIGHT: 'SPARE_QR_CODE_LABEL_CONTENT_HEIGHT', // 备件标签表格高度
+  SPARE_QR_CODE_LABEL_IMG_WIDTH: 'SPARE_QR_CODE_LABEL_IMG_WIDTH', // 备件标签二维码宽度
   FILE_DOWNLOAD_TEMPLATE: 'FILE_DOWNLOAD_TEMPLATE', // 模板文件
   DELFLAG: 'DELFLAG', // 删除标志
   SBTYPE_TYPE: 'SBTYPE_TYPE', // 设备类型
@@ -81,6 +85,7 @@ DictCache.TYPE = {
   SB_COLOR: 'SB_COLOR', // 设备颜色
   SB_MEASURE_RESULT: 'SB_MEASURE_RESULT', // 检定结论
   SB_INFO_STATUS: 'SB_INFO_STATUS', // 设备状态
+  SPARE_WARN_STATUS: 'SPARE_WARN_STATUS', // 备件库存不足预警状态
   SB_MEASURE_STATUS: 'SB_MEASURE_STATUS', // 检定设备状态
   SBTYPE_SOURCETYPE: 'SBTYPE_SOURCETYPE', // 设备来源方式
   SBINFO_UNIT: 'SBINFO_UNIT', // 计量单位
@@ -273,7 +278,10 @@ DictCache.TYPE = {
   PURCHASE_INVOICE_TYPE: 'PURCHASE_INVOICE_TYPE',
   PURCHASE_STORE_PLACE: 'PURCHASE_STORE_PLACE',
   GROUP_INFO: 'GROUP_INFO',
-  _AUDIT_MONEY: '_AUDIT_MONEY'
+  _AUDIT_MONEY: '_AUDIT_MONEY',
+  CUSTOMIZE_REPORT_ECHART_TYPE: 'CUSTOMIZE_REPORT_ECHART_TYPE',
+  CUSTOMIZE_REPORT_INTER_TYPE: 'CUSTOMIZE_REPORT_INTER_TYPE',
+  PARAMETER_TYPE: 'PARAMETER_TYPE'
 
 }
 DictCache.CODE = {
@@ -657,6 +665,13 @@ DictCache.VALUE = {
     YOUKU: 1, // 园区
     SHENGCHANXIAN: 2 // 生产线
   },
+  /**
+   * 仓库等级枚举类
+   */
+  STORE_LEVEL: {
+    ZONGCANG: 1, // 立体库
+    FENCANG: 2 // 库位
+  },
   /**
    * 入库类型
    */
@@ -1204,6 +1219,15 @@ DictCache.COLOR = {
     1: 'success', // 正在使用
     2: 'error' // 已过期
   },
+  /**
+   * 设备状态
+   */
+  SPARE_WARN_STATUS: {
+    1: 'error', // 在库
+    2: 'warning', // 使用中
+    3: 'gray', // 报废中
+    0: 'success' // 已报废
+  },
   /**
    * 设备状态
    */
@@ -1217,6 +1241,19 @@ DictCache.COLOR = {
     7: 'error', // 停用中
     8: 'error' // 维修中
   },
+  /**
+   * 计量设备状态
+   */
+  SB_MEASURE_STATUS: {
+    1: 'success', // 在用
+    2: 'warning', // 检定
+    3: 'gray', // 备用
+    4: 'error', // 维修
+    5: 'gray', // 停用
+    6: 'gray', // 丢失
+    7: 'gray', // 转出
+    8: 'gray' // 报废
+  },
   /**
    * 改进措施状态
    */

+ 10 - 0
src/views/check/checkjob/CheckJob.vue

@@ -114,6 +114,10 @@
       <div class="table-operator">
         <a-button v-if="$auth('check-polling-jobs-add')" type="primary" icon="plus" @click="$refs.baseModal.base()">新增</a-button>
         <a-button style="margin-left: 8px" v-if="($auth('check-spot-jobs-export') || $auth('check-polling-jobs-export'))" type="primary" icon="download" @click="doExport">导出</a-button>
+        <a-button style="margin-left:8px;" type="primary" @click="doImportForUpdate">
+          <a-icon type="upload"/>
+          修改导入
+        </a-button>
         <a-button style="margin-left: 8px" type="success" @click="handleSeven">本周</a-button>
         <a-button style="margin-left: 8px" type="success" @click="handleMonth">本月</a-button>
         <a-button style="margin-left: 8px" type="success" @click="handleTuiCalendar">日历图</a-button>
@@ -182,6 +186,7 @@
     </div>
     <base-form :check-type="checkType" ref="baseModal" @ok="handleOk"/>
     <detail :check-type="checkType" ref="detailModal" @ok="handleOk"/>
+    <import-form-update ref="importModalUpdate" @ok="handleOk"/>
   </a-card>
 </template>
 
@@ -192,6 +197,7 @@ import Detail from './modules/Detail'
 import { getCheckJobPage, deleteCheckJobs, fetchCheckJob, exportCheckJob, executeJob, executeJobBatch, finishJobBatch, queryTuiCalendarIgnores } from '@/api/check/checkjob'
 import { fetchSbTypeTree } from '@/api/sb/type'
 import DictCache from '@/utils/dict'
+import ImportFormUpdate from './modules/ImportFormUpdate'
 
 export default {
   name: 'CheckJobList',
@@ -199,6 +205,7 @@ export default {
     STable,
     Ellipsis,
     BaseForm,
+    ImportFormUpdate,
     Detail
   },
   props: {
@@ -626,6 +633,9 @@ export default {
       exportCheckJob(parameter).then(file => {
         this.BaseTool.UPLOAD.downLoadExportExcel(file)
       })
+    },
+    doImportForUpdate () {
+      this.$refs.importModalUpdate.base(null, null)
     }
   }
 }

+ 113 - 0
src/views/check/checkjob/modules/ImportFormUpdate.vue

@@ -0,0 +1,113 @@
+<template>
+  <a-modal
+    :title="modalTitle"
+    :width="640"
+    :visible="visible"
+    :confirmLoading="confirmLoading"
+    @cancel="handleCancel"
+  >
+    <a-form :form="form">
+      <a-form-item
+        label="上传文件"
+        :labelCol="BaseTool.Constant.labelCol"
+        :wrapperCol="BaseTool.Constant.wrapperCol"
+      >
+        <a-upload :fileList="fileList" @change="handleChange" :remove="handleRemove" :beforeUpload="beforeUpload">
+          <a-button> <a-icon type="upload" />选择上传文件</a-button>
+        </a-upload>
+      </a-form-item>
+    </a-form>
+    <template slot="footer">
+      <a-button :loading="confirmLoading" type="primary" @click="save()">确定</a-button>
+    </template>
+  </a-modal>
+</template>
+
+<script>
+import { importCheckJobForUpdate } from '@/api/check/checkjob'
+
+export default {
+  name: 'CheckJobImportForm',
+  data () {
+    return {
+      confirmLoading: false,
+      modalTitle: null,
+      form: this.$form.createForm(this),
+      visible: false,
+      useCompany: null,
+      useProject: null,
+      type: null,
+      fileList: []
+    }
+  },
+  methods: {
+    base (useCompany, useProject) {
+      this.visible = true
+      this.useCompany = useCompany
+      this.useProject = useProject
+      this.modalTitle = '设备修改导入'
+      this.type = 2
+    },
+    handleRemove (file) {
+      const index = this.fileList.indexOf(file)
+      const newFileList = this.fileList.slice()
+      newFileList.splice(index, 1)
+      this.fileList = newFileList
+    },
+    beforeUpload (file) {
+      const reg = /\.(xls|xlsx)(\?.*)?$/
+      return new Promise((resolve, reject) => {
+        if (reg.test(file.name)) {
+          this.fileList = [file]
+          return false
+        } else {
+          this.$message.error(`请上传正确的excel文件`)
+          reject(new Error('请上传正确的excel文件'))
+          return false
+        }
+      })
+    },
+    handleChange (info) {
+      if (info.file.status !== 'uploading') {
+        console.log(info.file, info.fileList)
+      }
+      if (info.file.status === 'done') {
+        this.$message.success(`${info.file.name} file uploaded successfully`)
+      } else if (info.file.status === 'error') {
+        this.$message.error(`${info.file.name} file upload failed.`)
+      }
+    },
+    save () {
+      const { form: { validateFieldsAndScroll } } = this
+      this.confirmLoading = true
+      validateFieldsAndScroll((errors, values) => {
+        if (errors) {
+          this.confirmLoading = false
+          return
+        }
+        const formData = new FormData()
+        formData.append('type', this.type)
+        formData.append('file', this.fileList[0])
+        importCheckJobForUpdate(formData)
+          .then((res) => {
+            this.$message.success(res.data)
+            this.handleCancel(values)
+            this.BaseTool.ListForm.clearOneList(this)
+            this.BaseTool.ListForm.pushOneListAddMore(this, res.data)
+          }).catch(() => {
+            this.confirmLoading = false
+          })
+      })
+    },
+    handleCancel (values) {
+      this.visible = false
+      this.confirmLoading = false
+      this.fileList = []
+      this.form.resetFields()
+      this.storeId = null
+      this.$emit('ok', values)
+    }
+
+  }
+}
+</script>

+ 61 - 5
src/views/check/checkstandard/CheckStandard.vue

@@ -19,6 +19,56 @@
                 <a-input v-model="queryParam.sbName" placeholder="请输入设备名称"/>
               </a-form-item>
             </a-col>
+            <a-col :md="6" :sm="24">
+              <a-form-item label="设备类型">
+                <a-tree-select
+                  style="width: 100%"
+                  :dropdownStyle="{ maxHeight: '400px', overflow: 'auto' }"
+                  :treeData="treeData"
+                  :treeNodeFilterProp="'title'"
+                  :showSearch="true"
+                  v-model="queryParam.typeId"
+                  placeholder="请选择"
+                >
+                </a-tree-select>
+              </a-form-item>
+            </a-col>
+            <a-col :md="6" :sm="24">
+              <a-form-item label="设备等级">
+                <a-select v-model="queryParam.sbLevel" placeholder="请选择">
+                  <a-select-option
+                    v-for="(label,value) in sbLevelMap"
+                    :key="value"
+                    :label="label"
+                    :value="parseInt(value)">{{ label }}
+                  </a-select-option>
+                </a-select>
+              </a-form-item>
+            </a-col>
+            <a-col :md="6" :sm="24">
+              <a-form-item label="维护等级">
+                <a-select v-model="queryParam.level" placeholder="请选择">
+                  <a-select-option
+                    v-for="(label,value) in levelMap"
+                    :key="value"
+                    :label="label"
+                    :value="parseInt(value)">{{ label }}
+                  </a-select-option>
+                </a-select>
+              </a-form-item>
+            </a-col>
+            <a-col :md="6" :sm="24">
+              <a-form-item label="计划周期">
+                <a-select v-model="queryParam.periodType" placeholder="请选择">
+                  <a-select-option
+                    v-for="(label,value) in periodTypeMap"
+                    :key="value"
+                    :label="label"
+                    :value="parseInt(value)">{{ label }}
+                  </a-select-option>
+                </a-select>
+              </a-form-item>
+            </a-col>
             <a-col :md="6 || 24" :sm="24">
               <span class="table-page-search-submitButtons">
                 <a-button type="primary" @click="$refs.table.refresh(true)">查询</a-button>
@@ -40,7 +90,7 @@
           <a-icon type="upload"/>
           新增导入
         </a-button>
-<!--        <a-button style="margin-left:8px;" type="primary" @click="doImportOldVersion">
+        <!--        <a-button style="margin-left:8px;" type="primary" @click="doImportOldVersion">
           <a-icon type="upload"/>
           老版本导入
         </a-button>-->
@@ -55,10 +105,10 @@
           icon="download"
           @click="doExport">导出
         </a-button>
-        <!--      <a-button :confirmLoading="confirmLoading" style="margin-left:8px;" type="primary" @click="doUpdateNo">
-        <a-icon type="upload"/>
-        初始化编码
-      </a-button>-->
+        <a-button :confirmLoading="confirmLoading" style="margin-left:8px;" type="primary" @click="doUpdateNo">
+          <a-icon type="upload"/>
+          初始化编码
+        </a-button>
         <a-dropdown v-action:edit v-if="selectedRowKeys.length > 0 && ($auth('check-spot-standards-del')||$auth('check-polling-standards-del'))">
           <a-menu slot="overlay">
             <a-popconfirm title="是否要删除所选数据?" @confirm="batchDelete()">
@@ -130,6 +180,7 @@ import {
   exportCheckStandard
 } from '@/api/check/checkstandard'
 import DetailStandardCheckJob from '@/views/check/checkjob/modules/DetailStandardCheckJob'
+import { fetchSbTypeTree } from '@/api/sb/type'
 
 export default {
   name: 'CheckStandardList',
@@ -257,6 +308,8 @@ export default {
       enableMap: {},
       periodTypeMap: {},
       levelMap: {},
+      sbLevelMap: {},
+      treeData: [],
       checkUserTypeMap: {},
       // 加载数据方法 必须为 Promise 对象
       loadData: parameter => {
@@ -296,6 +349,9 @@ export default {
     this.actionTypeMap = this.DictCache.getLabelByValueMapByType(this.DictCache.TYPE.CHECK_PLAN_ACTION_TYPE)
     this.levelMap = this.DictCache.getLabelByValueMapByType(this.DictCache.TYPE.CHECK_PLAN_LEVEL)
     this.checkUserTypeMap = this.DictCache.getLabelByValueMapByType(this.DictCache.TYPE.CHECK_USER_TYPE)
+    fetchSbTypeTree().then(res => {
+      this.treeData = res.data
+    })
     this.tableOption()
   },
   methods: {

+ 18 - 0
src/views/check/checkstandard/modules/DetailSbCheck.vue

@@ -32,6 +32,17 @@
         <a-icon type="delete"/>
         删除
       </a-button>
+      <a-form-item style="margin-left:8px;" label="维护等级">
+        <a-select v-model="queryParam.level" placeholder="请选择">
+          <a-select-option
+            v-for="(label,value) in levelMap"
+            :key="value"
+            :label="label"
+            @change="changeLevel"
+            :value="parseInt(value)">{{ label }}
+          </a-select-option>
+        </a-select>
+      </a-form-item>
       <!--      <a-button style="margin-left: 8px" type="primary" icon="download" @click="doExport">导出</a-button>-->
     </div>
     <a-table
@@ -101,6 +112,8 @@ export default {
     return {
       confirmLoading: false,
       mdl: {},
+      queryParam: {
+      },
       levelMap: {},
       model: {
         'id': null,
@@ -227,6 +240,11 @@ export default {
         this.data = res.data
       })
     },
+    changeLevel (value) {
+      queryCheckStandard({ sbId: this.model.id, level: value, type: this.checkType }).then(res => {
+        this.data = res.data
+      })
+    },
     handleOk () {
       queryCheckStandard({ sbId: this.model.id, type: this.checkType }).then(res => {
         this.data = res.data

+ 297 - 0
src/views/customize/report/CustomizeReport.vue

@@ -0,0 +1,297 @@
+<template>
+  <a-card :bordered="false">
+    <div class="table-page-search-wrapper" @keyup.enter="handleEnter">
+      <a-form layout="inline">
+        <a-row :gutter="48">
+          <a-col :md="8" :sm="24">
+            <a-form-item label="关键字">
+              <a-input v-model="queryParam.keyword" placeholder="请输入名称/类型名称" />
+            </a-form-item>
+          </a-col>
+          <a-col :md="8 || 24" :sm="24">
+            <span class="table-page-search-submitButtons">
+              <a-button type="primary" @click="$refs.table.refresh(true)">查询</a-button>
+              <a-button style="margin-left: 8px" @click="resetSearchForm">重置</a-button>
+            </span>
+          </a-col>
+        </a-row>
+      </a-form>
+    </div>
+
+    <div class="table-operator">
+      <a-button v-if="$auth('customize-reports-add')" type="primary" icon="plus" @click="$refs.baseModal.base()">新增
+      </a-button>
+      <a-button
+        style="margin-left: 8px"
+        v-if="$auth('customize-reports-export')"
+        type="primary"
+        icon="download"
+        @click="doExport">导出
+      </a-button>
+      <a-dropdown v-action:edit v-if="selectedRowKeys.length > 0 && $auth('customize-reports-del')">
+        <a-menu slot="overlay">
+          <a-popconfirm title="是否要删除所选数据?" @confirm="batchDelete()">
+            <a-menu-item key="1">
+              <a-icon type="delete" />
+              <a>删除</a></a-menu-item>
+          </a-popconfirm>
+        </a-menu>
+        <a-button style="margin-left: 8px">
+          批量操作
+          <a-icon type="down" />
+        </a-button>
+      </a-dropdown>
+    </div>
+
+    <s-table
+      ref="table"
+      size="default"
+      rowKey="id"
+      :columns="columns"
+      :data="loadData"
+      :alert="options.alert"
+      :rowSelection="options.rowSelection"
+      showPagination="auto"
+    >
+      <span slot="action" slot-scope="record">
+        <template>
+          <a @click="handleView(record)">查看</a>
+          <operation-button
+            v-if="$auth('customize-reports-edit')"
+            @click="handleEdit(record)"
+          >修改</operation-button>
+          <operation-button
+            @click="handlePreview(record)"
+          >预览</operation-button>
+          <operation-button
+            v-if="$auth('customize-reports-del')"
+            :type="2"
+            title="是否要删除该条数据?"
+            @confirm="batchDelete(record.id)">删除</operation-button>
+        </template>
+      </span>
+
+      <span slot="interType" slot-scope="text">
+        <badge
+          :text="interTypeMap[text]" />
+      </span>
+
+      <span slot="echartType" slot-scope="text">
+        <badge
+          :text="echartTypeMap[text]" />
+      </span>
+    </s-table>
+    <base-form ref="baseModal" @ok="handleOk" />
+    <detail ref="detailModal" />
+  </a-card>
+</template>
+
+<script>
+import { STable, Ellipsis } from '@/components'
+import BaseForm from './modules/BaseForm'
+import Detail from './modules/Detail'
+import {
+  getCustomizeReportPage,
+  deleteCustomizeReports,
+  fetchCustomizeReport,
+  exportCustomizeReport
+} from '@/api/customize/report'
+
+export default {
+  name: 'CustomizeReportList',
+  components: {
+    STable,
+    Ellipsis,
+    BaseForm,
+    Detail
+  },
+  data () {
+    return {
+      // 查询参数
+      queryParam: {},
+      // 表头
+      columns: [
+        {
+          title: '序号',
+          dataIndex: 'index',
+          customRender: (text, record, index) => {
+            return `${(this.$refs.table.localPagination.current - 1) * this.$refs.table.localPagination.pageSize + index + 1}`
+          }
+        },
+        {
+          title: '自定义报表名称',
+          dataIndex: 'name'
+        },
+        {
+          title: '图形类别',
+          dataIndex: 'echartType',
+          scopedSlots: { customRender: 'echartType' }
+        },
+        /*   {
+          title: '报表检索条件',
+          dataIndex: 'parameter'
+        }, */
+        {
+          title: '报表接口类型',
+          dataIndex: 'interType',
+          scopedSlots: { customRender: 'interType' }
+        },
+        {
+          title: '数据来源',
+          dataIndex: 'sqlVal'
+        },
+        /*   {
+          title: '表格展示字段',
+          dataIndex: 'columns'
+        }, */
+        /*     {
+          title: '创建人',
+          dataIndex: 'createdUserName'
+        }, */
+        {
+          title: '创建时间',
+          dataIndex: 'createdTime'
+        },
+        {
+          title: '操作',
+          key: 'action',
+          width: '200px',
+          align: 'center',
+          scopedSlots: { customRender: 'action' }
+        }
+      ],
+      // 下拉框map
+      echartTypeMap: [],
+      interTypeMap: [],
+      // 加载数据方法 必须为 Promise 对象
+      loadData: parameter => {
+        parameter = {
+          ...parameter,
+          ...this.queryParam,
+          dataScope: {
+            sortBy: 'desc',
+            sortName: 'update_time'
+          }
+        }
+        return getCustomizeReportPage(Object.assign(parameter, this.queryParam))
+          .then(res => {
+            return res.data
+          })
+      },
+      selectedRowKeys: [],
+      selectedRows: [],
+
+      options: {
+        alert: {
+          show: true,
+          clear: () => {
+            this.selectedRowKeys = []
+          }
+        },
+        rowSelection: {
+          selectedRowKeys: this.selectedRowKeys,
+          onChange: this.onSelectChange
+        }
+      },
+      optionAlertShow: false
+    }
+  },
+  created () {
+    // 下拉框map
+    this.echartTypeMap = this.DictCache.getLabelByValueMapByType(this.DictCache.TYPE.CUSTOMIZE_REPORT_ECHART_TYPE)
+    this.interTypeMap = this.DictCache.getLabelByValueMapByType(this.DictCache.TYPE.CUSTOMIZE_REPORT_INTER_TYPE)
+  },
+  methods: {
+    tableOption () {
+      if (!this.optionAlertShow) {
+        this.options = {
+          alert: {
+            show: true,
+            clear: () => {
+              this.selectedRowKeys = []
+            }
+          },
+          rowSelection: {
+            selectedRowKeys: this.selectedRowKeys,
+            onChange: this.onSelectChange,
+            getCheckboxProps: record => ({
+              props: {
+                disabled: false,
+                name: record.id
+              }
+            })
+          }
+        }
+        this.optionAlertShow = true
+      } else {
+        this.options = {
+          alert: false,
+          rowSelection: null
+        }
+        this.optionAlertShow = false
+      }
+    },
+    batchDelete (id) {
+      let ids = []
+      if (this.BaseTool.String.isBlank(id)) {
+        const length = this.selectedRows.length
+        if (length === 0) {
+          this.$message.info('请选择要删除的记录')
+          return
+        }
+        ids = this.selectedRows.map(item => item.id)
+      } else {
+        ids = [id]
+      }
+      deleteCustomizeReports(ids).then(res => {
+        this.$message.info('删除成功')
+        this.handleOk()
+        this.$refs.table.clearSelected()
+      })
+    },
+    handleEdit (record) {
+      fetchCustomizeReport({ id: record.id }).then(res => {
+        const modal = this.$refs.baseModal
+        modal.base(res.data)
+      })
+    },
+    handlePreview (record) {
+      console.log('JSON.stringify(record): ' + JSON.stringify(record))
+      const text = this.$router.resolve({
+        name: 'ChartReport',
+        query: record
+      })
+      // 打开一个新的页面
+      window.open(text.href, '_blank')
+    },
+    handleView (record) {
+      fetchCustomizeReport({ id: record.id }).then(res => {
+        const modal = this.$refs.detailModal
+        modal.base(res.data)
+      })
+    },
+    handleOk () {
+      this.$refs.table.refresh()
+    },
+    onSelectChange (selectedRowKeys, selectedRows) {
+      this.selectedRowKeys = selectedRowKeys
+      this.selectedRows = selectedRows
+    },
+    resetSearchForm () {
+      this.queryParam = {}
+      this.$refs.table.refresh(true)
+    },
+    doExport () {
+      const parameter = {
+        ...this.queryParam
+      }
+      exportCustomizeReport(parameter).then(file => {
+        this.BaseTool.Util.downLoadExportExcel(file)
+      })
+    },
+    handleEnter () {
+      this.$refs.table.refresh(true)
+    }
+  }
+}
+</script>

+ 214 - 0
src/views/customize/report/modules/BaseForm.vue

@@ -0,0 +1,214 @@
+<template>
+  <a-modal
+    :title='modalTitle'
+    :width='800'
+    :visible='visible'
+    :confirmLoading='confirmLoading'
+    class='ant-modal2'
+    @cancel='handleCancel'
+  >
+    <a-form :form='form'>
+
+      <a-form-item v-show='false'>
+        <a-input v-decorator="['id']" type='hidden' />
+      </a-form-item>
+      <a-form-item v-show='false'>
+        <a-input v-decorator="['status']" type='hidden' />
+      </a-form-item>
+
+      <row-list :col='2'>
+        <row-item>
+
+          <a-form-item
+            label='自定义报表名称'
+            :labelCol='BaseTool.Constant.labelCol'
+            :wrapperCol='BaseTool.Constant.wrapperCol'
+          >
+            <a-input
+              v-decorator="['name', {rules: [{required: true, message: '自定义报表名称不能为空'}]}]" />
+          </a-form-item>
+        </row-item>
+        <row-item>
+
+          <a-form-item
+            label='图形类别'
+            :labelCol='BaseTool.Constant.labelCol'
+            :wrapperCol='BaseTool.Constant.wrapperCol'
+          >
+            <a-select
+              v-decorator="['echartType', { initValue: 1, rules: [{required: true, message: '图形不能为空'}]}]"
+              placeholder="请选择">
+              <a-select-option
+                v-for="(label,value) in echartTypeMap"
+                :key="value"
+                :label="label"
+                :value="parseInt(value)">{{ label }}
+              </a-select-option>
+            </a-select>
+          </a-form-item>
+        </row-item>
+        <row-item>
+          <a-form-item
+            label='报表检索条件'
+            :labelCol='BaseTool.Constant.labelCol'
+            :wrapperCol='BaseTool.Constant.wrapperCol'
+          >
+            <a-textarea
+              disabled='disabled'
+              v-decorator="['parameter', {rules: [{required: true, message: '报表检索条件不能为空'}]}]" />
+            <a-button type="primary" style="width:30%" @click="handleParameterSelect">新增</a-button>
+          </a-form-item>
+        </row-item>
+        <row-item>
+
+          <a-form-item
+            label='报表接口类型'
+            :labelCol='BaseTool.Constant.labelCol'
+            :wrapperCol='BaseTool.Constant.wrapperCol'
+          >
+            <a-select
+              v-decorator="['interType', { initValue: 1, rules: [{required: true, message: '数据提供方式不能为空'}]}]"
+              placeholder="请选择">
+              <a-select-option
+                v-for="(label,value) in interTypeMap"
+                :key="value"
+                :label="label"
+                :value="parseInt(value)">{{ label }}
+              </a-select-option>
+            </a-select>
+          </a-form-item>
+        </row-item>
+        <row-item>
+
+          <a-form-item
+            label='接口数据来源配置'
+            :labelCol='BaseTool.Constant.labelCol'
+            :wrapperCol='BaseTool.Constant.wrapperCol'
+          >
+            <a-textarea
+              v-decorator="['sqlVal', {rules: [{required: true, message: '自定义报表名称不能为空'}]}]" />
+          </a-form-item>
+        </row-item>
+        <row-item>
+
+          <a-form-item
+            label='表格展示字段'
+            :labelCol='BaseTool.Constant.labelCol'
+            :wrapperCol='BaseTool.Constant.wrapperCol'
+          >
+            <a-textarea
+              placeholder='输入数据库字段的驼峰名称,逗号,隔开'
+              v-decorator="['columns', {rules: [{required: true, message: '表格展示字段不能为空'}]}]" />
+          </a-form-item>
+        </row-item>
+      </row-list>
+    </a-form>
+    <template slot='footer'>
+      <a-button :loading='confirmLoading' type='primary' @click='save()'>保存</a-button>
+    </template>
+    <parameter-modal ref="parameterModal" @selected="handleparameterSelectd" />
+  </a-modal>
+</template>
+
+<script>
+import pick from 'lodash.pick'
+import ParameterModal from '@/views/customize/report/modules/ParameterModal'
+import { addCustomizeReport, updateCustomizeReport } from '@/api/customize/report'
+
+export default {
+  name: 'BaseCustomizeReport',
+  components: {
+    ParameterModal
+  },
+  data () {
+    return {
+      confirmLoading: false,
+      modalTitle: null,
+      form: this.$form.createForm(this),
+      visible: false,
+      // 下拉框map
+      echartTypeMap: [],
+      interTypeMap: [],
+      parameter: []
+    }
+  },
+  props: {},
+  created () {
+    // 下拉框map
+    this.echartTypeMap = this.DictCache.getLabelByValueMapByType(this.DictCache.TYPE.CUSTOMIZE_REPORT_ECHART_TYPE)
+    this.interTypeMap = this.DictCache.getLabelByValueMapByType(this.DictCache.TYPE.CUSTOMIZE_REPORT_INTER_TYPE)
+  },
+  methods: {
+    base (record) {
+      this.visible = true
+      // 如果是空标识添加
+      if (this.BaseTool.Object.isBlank(record)) {
+        this.modalTitle = '添加'
+        return
+      }
+      this.modalTitle = '编辑'
+      const { form: { setFieldsValue } } = this
+      // 日期处理
+      this.$nextTick(() => {
+        setFieldsValue(Object.assign(pick(record, [
+          'id',
+          'name',
+          'echartType',
+          'parameter',
+          'interType',
+          'sqlVal',
+          'columns',
+          'status',
+          'remark'
+        ])))
+      })
+    },
+    handleParameterSelect () {
+      this.$refs.parameterModal.base()
+    },
+    handleparameterSelectd (rows) {
+      this.parameter.push(rows)
+      const parameterVal = JSON.stringify(this.parameter)
+      this.form.setFieldsValue({
+        'parameter': parameterVal
+      })
+    },
+    save () {
+      const { form: { validateFieldsAndScroll } } = this
+      this.confirmLoading = true
+      validateFieldsAndScroll((errors, values) => {
+        if (errors) {
+          this.confirmLoading = false
+          return
+        }
+        // 日期处理
+        if (this.BaseTool.String.isBlank(values.id)) {
+          values.status = 0
+          addCustomizeReport(values)
+            .then(() => {
+              this.handleCancel(values)
+            }).catch(() => {
+            this.confirmLoading = false
+          })
+        } else {
+          updateCustomizeReport(values)
+            .then(() => {
+              this.handleCancel(values)
+            }).catch(() => {
+            this.confirmLoading = false
+          })
+        }
+      })
+    },
+    handleCancel(values) {
+      this.visible = false
+      this.confirmLoading = false
+      this.form.resetFields()
+      if (this.BaseTool.Object.isNotBlank(values)) {
+        this.$emit('ok', values)
+      }
+    }
+
+  }
+}
+</script>

+ 297 - 0
src/views/customize/report/modules/CustomizeReportSelectModal.vue

@@ -0,0 +1,297 @@
+<template>
+    <a-modal
+            :title="modalTitle"
+            :width="1000"
+            :visible="visible"
+            :confirmLoading="confirmLoading"
+            class="ant-modal2"
+            @cancel="handleCancel"
+    >
+        <a-card :bordered="false">
+            <div class="table-page-search-wrapper">
+                <a-form layout="inline">
+                    <a-row :gutter="48">
+                        <a-col :md="8" :sm="24">
+                            <a-form-item label="关键字">
+                                <a-input v-model="queryParam.keyword" placeholder="请输入名称/类型名称"/>
+                            </a-form-item>
+                        </a-col>
+                        <a-col :md="8 || 24" :sm="24">
+                <span class="table-page-search-submitButtons">
+                  <a-button type="primary" @click="$refs.table.refresh(true)">查询</a-button>
+                  <a-button style="margin-left: 8px" @click="resetSearchForm">重置</a-button>
+                </span>
+                        </a-col>
+                    </a-row>
+                </a-form>
+            </div>
+
+            <div class="table-operator">
+            </div>
+
+            <s-table
+                    ref="table"
+                    size="default"
+                    rowKey="id"
+                    :columns="columns"
+                    :data="loadData"
+                    :alert="options.alert"
+                    :customRow="options.customRow"
+                    :rowSelection="options.rowSelection"
+                    showPagination="auto"
+            >
+                <span slot="action" slot-scope="record1">
+                  <template>
+                    <a @click="handleView(record1)">查看</a>
+                  </template>
+                </span>
+            </s-table>
+            <detail ref="detailModal"/>
+        </a-card>
+        <template slot="footer">
+            <a-button :loading="confirmLoading" type="primary" @click="handleCancel()">取消</a-button>
+            <a-button :loading="confirmLoading" type="primary" @click="handleSelect()">确定</a-button>
+        </template>
+    </a-modal>
+</template>
+
+<script>
+    import { STable, Ellipsis } from '@/components'
+    import Detail from './Detail'
+    import { getCustomizeReportPage, fetchCustomizeReport } from '@/api/customize/report'
+
+    export default {
+        name: 'CustomizeReportSelectModal',
+        components: {
+            STable,
+            Ellipsis,
+            Detail
+        },
+        props: {
+            type: {
+                type: String,
+                default: 'radio'
+            },
+            selectedRowKey: {
+                type: Array,
+                default: () => {
+                    return []
+                }
+            },
+            selectedRow: {
+                type: Array,
+                default: () => {
+                    return []
+                }
+            }
+        },
+        data () {
+            return {
+                confirmLoading: false,
+                mdl: {},
+                modalTitle: null,
+                visible: false,
+                record: null,
+                // 查询参数
+                queryParam: {
+                },
+                extraQueryParam: {
+                },
+                // 表头
+                columns: [
+                    {
+                        title: '序号',
+                        dataIndex: 'index',
+                        customRender: (text, record, index) => {
+                            return `${(this.$refs.table.localPagination.current - 1) * this.$refs.table.localPagination.pageSize + index + 1}`
+                        }
+                    },
+                                                                                                                                                {
+                                title: '自定义报表名称',
+                                dataIndex: 'name'
+                            },
+                                                                                                                                                        {
+                                title: '图形类别',
+                                dataIndex: 'echartType'
+                            },
+                                                                                                                                                        {
+                                title: '报表检索条件',
+                                dataIndex: 'parameter'
+                            },
+                                                                                                                                                        {
+                                title: '报表接口类型',
+                                dataIndex: 'interType'
+                            },
+                                                                                                                                                        {
+                                title: 'sql语句',
+                                dataIndex: 'sql'
+                            },
+                                                                                                                                                        {
+                                title: '表格展示字段',
+                                dataIndex: 'columns'
+                            },
+                                                                                                                                                        {
+                                title: '自定义报表状态',
+                                dataIndex: 'status'
+                            },
+                                                                                                                                                        {
+                                title: '备注',
+                                dataIndex: 'remark'
+                            },
+                                                                                                                                                                                                                                                {
+                                title: '',
+                                dataIndex: 'createdUserName'
+                            },
+                                                                                                                                                                                                    {
+                                title: '',
+                                dataIndex: 'createdTime'
+                            },
+                                                                                                                                        {
+                        title: '操作',
+                        key: 'action',
+                        width: '200px',
+                        align: 'center',
+                        scopedSlots: { customRender: 'action' }
+                    }
+                ],
+                // 下拉框map
+                                // 加载数据方法 必须为 Promise 对象
+                loadData: parameter => {
+                    parameter = {
+                        ...parameter,
+                        ...this.queryParam,
+                        ...this.extraQueryParam,
+                        dataScope: {
+                            sortBy: 'desc',
+                            sortName: 'update_time'
+                        }
+                    }
+                    return getCustomizeReportPage(Object.assign(parameter, this.queryParam))
+                            .then(res => {
+                                return res.data
+                            })
+                },
+                selectedRowKeys: [],
+                selectedRows: [],
+
+                options: {
+                    alert: { show: true, clear: () => { this.selectedRowKeys = [] } },
+                    rowSelection: {
+                        selectedRowKeys: this.selectedRowKeys,
+                        onChange: this.onSelectChange
+                    }
+                },
+                optionAlertShow: false,
+                isCreated: false
+            }
+        },
+        created () {
+            // 下拉框map
+                    },
+        methods: {
+            tableOption () {
+                if (!this.optionAlertShow) {
+                    this.options = {
+                        alert: { show: true, clear: () => { this.selectedRowKeys = [] } },
+                        rowSelection: {
+                            selectedRowKeys: this.selectedRowKeys,
+                            onChange: this.onSelectChange,
+                            type: this.type,
+                            getCheckboxProps: record => ({
+                                props: {
+                                    disabled: false,
+                                    name: record.id
+                                }
+                            })
+                        },
+                        customRow: (record) => {
+                            return {
+                                on: { // 事件
+                                    click: (event) => { // 点击行
+                                        // 选择对象
+                                        this.mySelect([record.id], [record])
+                                    },
+                                    dblclick: (event) => {
+                                        this.mySelect([record.id], [record])
+                                        this.handleSelect()
+                                    }
+                                }
+                            }
+                        }
+                    }
+                    this.optionAlertShow = true
+                } else {
+                    this.options = {
+                        alert: false,
+                        rowSelection: null
+                    }
+                    this.optionAlertShow = false
+                }
+            },
+            handleView (record) {
+                fetchCustomizeReport({ id: record.id }).then(res => {
+                    const modal = this.$refs.detailModal
+                    modal.base(res.data)
+                })
+            },
+            handleOk () {
+                this.$refs.table.refresh()
+            },
+            onSelectChange (selectedRowKeys, selectedRows) {
+                this.selectedRowKeys = selectedRowKeys
+                this.selectedRows = selectedRows
+            },
+            resetSearchForm () {
+                this.queryParam = {
+                }
+                this.$refs.table.refresh(true)
+            },
+            base (record, queryParam = {}) {
+                this.visible = true
+                this.modalTitle = '选择信息'
+                this.extraQueryParam = queryParam
+                this.record = record
+                if (this.isCreated) {
+                    this.$refs.table.clearSelected()
+                    this.options.rowSelection.type = this.type
+                    this.handleOk()
+                } else {
+                    this.tableOption()
+                    this.isCreated = true
+                }
+            },
+            handleCancel () {
+                this.visible = false
+                this.confirmLoading = false
+            },
+            handleSelect () {
+                if (this.selectedRowKeys.length === 0) {
+                    this.$message.warn('请至少选择一项信息')
+                } else {
+                    this.confirmLoading = true
+                    this.$emit('selected', this.record, this.selectedRowKeys, this.selectedRows)
+                    this.confirmLoading = false
+                    this.visible = false
+                }
+            },
+            mySelect(selectedRowKeys, selectedRows) {
+                if (this.type === 'radio') {
+                    this.$refs.table.updateSelect(selectedRowKeys, selectedRows)
+                            this.$refs.table.rowSelection.onChange(selectedRowKeys, selectedRows)
+                } else {
+                    let mySelectedRowKeys
+                    let mySelectedRows = this.selectedRows.filter(item => item.id !== selectedRowKeys[0])
+                    if (this.selectedRowKeys.includes(selectedRowKeys[0])) {
+                        mySelectedRowKeys = this.selectedRowKeys.filter(item => item !== selectedRowKeys[0])
+                    } else {
+                        mySelectedRowKeys = [...selectedRowKeys, ...this.selectedRowKeys]
+                        mySelectedRows = [...mySelectedRows, ...selectedRows]
+                    }
+                    this.$refs.table.updateSelect(mySelectedRowKeys, mySelectedRows)
+                            this.$refs.table.rowSelection.onChange(mySelectedRowKeys, mySelectedRows)
+                }
+
+            }
+        }
+    }
+</script>

+ 83 - 0
src/views/customize/report/modules/Detail.vue

@@ -0,0 +1,83 @@
+<template>
+  <a-modal
+    :title='modalTitle'
+    :width='850'
+    :visible='visible'
+    :confirmLoading='confirmLoading'
+    class='ant-modal2'
+    @cancel='handleCancel'
+  >
+    <detail-list title='' :col='2'>
+      <detail-list-item term='自定义报表名称'>{{ model.name }}</detail-list-item>
+      <detail-list-item term='图形类别'>{{ BaseTool.Object.getField(echartTypeMap,model.echartType) }}</detail-list-item>
+      <detail-list-item term='报表检索条件'>{{ model.parameter }}</detail-list-item>
+      <detail-list-item term='报表接口类型'>{{ BaseTool.Object.getField(interTypeMap,model.interType) }}</detail-list-item>
+      <detail-list-item term='数据来源'>{{ model.sqlVal }}</detail-list-item>
+      <detail-list-item term='表格展示字段'>{{ model.columns }}</detail-list-item>
+      <detail-list-item term='添加人'>{{ model.createdUserName }}</detail-list-item>
+      <detail-list-item term='添加时间'>{{ model.createdTime }}</detail-list-item>
+      <detail-list-item term='修改人'>{{ model.updateUserName }}</detail-list-item>
+      <detail-list-item term='修改时间'>{{ model.updateTime }}</detail-list-item>
+    </detail-list>
+
+    <template slot='footer'>
+      <a-button :loading='confirmLoading' type='primary' @click='handleCancel()'>返回</a-button>
+    </template>
+  </a-modal>
+</template>
+
+<script>
+import DetailList from '@/components/tools/DetailList'
+
+const DetailListItem = DetailList.Item
+
+export default {
+  name: 'CustomizeReportDetail',
+  components: {
+    DetailList,
+    DetailListItem
+  },
+  data () {
+    return {
+      confirmLoading: false,
+      mdl: {},
+      modalTitle: null,
+      visible: false,
+      echartTypeMap: [],
+      interTypeMap: [],
+      // 下拉框map
+      model: {
+        'name': null,
+        'echartType': null,
+        'parameter': null,
+        'interType': null,
+        'sqlVal': null,
+        'columns': null,
+        'status': null,
+        'remark': null,
+        'createdUserId': null,
+        'updateUserId': null,
+        'updateUserName': null,
+        'updateTime': null
+      }
+    }
+  },
+  created () {
+    // 下拉框map
+    this.echartTypeMap = this.DictCache.getLabelByValueMapByType(this.DictCache.TYPE.CUSTOMIZE_REPORT_ECHART_TYPE)
+    this.interTypeMap = this.DictCache.getLabelByValueMapByType(this.DictCache.TYPE.CUSTOMIZE_REPORT_INTER_TYPE)
+  },
+  methods: {
+    base(record) {
+      this.visible = true
+      this.modalTitle = '详情'
+      this.model = record
+    },
+    handleCancel() {
+      this.visible = false
+      this.confirmLoading = false
+    }
+
+  }
+}
+</script>

+ 194 - 0
src/views/customize/report/modules/ParameterModal.vue

@@ -0,0 +1,194 @@
+<template>
+  <a-modal
+    :title="modalTitle"
+    :width="1200"
+    :visible="visible"
+    :confirmLoading="confirmLoading"
+    class="ant-modal2"
+    @cancel="handleCancel"
+  >
+    <a-form :form='form'>
+      <row-list :col='2'>
+        <row-item>
+          <a-form-item
+            label='条件名称'
+            :labelCol='BaseTool.Constant.labelCol'
+            :wrapperCol='BaseTool.Constant.wrapperCol'
+          >
+            <a-input
+              v-decorator="['label', {rules: [{required: true, message: '字段名称不能为空'}]}]" />
+          </a-form-item>
+        </row-item>
+        <row-item>
+          <a-form-item
+            label='对应数据库字段名称'
+            :labelCol='BaseTool.Constant.labelCol'
+            :wrapperCol='BaseTool.Constant.wrapperCol'
+          >
+            <a-input
+              v-decorator="['key', {rules: [{required: true, message: '字段名称不能为空'}]}]" />
+          </a-form-item>
+        </row-item>
+        <row-item>
+
+          <a-form-item
+            label='字段类型'
+            :labelCol='BaseTool.Constant.labelCol'
+            :wrapperCol='BaseTool.Constant.wrapperCol'
+          >
+            <a-select
+              @change="selectVal()"
+              v-decorator="['type', { initValue: 1, rules: [{required: true, message: '字段类型为空'}]}]"
+              placeholder="请选择">
+              <a-select-option
+                v-for="(label,value) in parameterTypeMap"
+                :key="value"
+                :label="label"
+                :value="value">{{ label }}
+              </a-select-option>
+            </a-select>
+          </a-form-item>
+        </row-item>
+        <row-item>
+          <a-form-item
+            label='字段值'
+            :labelCol='BaseTool.Constant.labelCol'
+            :wrapperCol='BaseTool.Constant.wrapperCol'
+          >
+            <a-textarea placeholder='select类型的值,请以英文,号隔开'
+                        v-decorator="['value']" />
+          </a-form-item>
+        </row-item>
+      </row-list>
+    </a-form>
+    <template slot="footer">
+      <a-button :loading="confirmLoading" type="primary" @click="handleCancel()">取消</a-button>
+      <a-button :loading="confirmLoading" type="primary" @click="handleSelect()">确定</a-button>
+    </template>
+  </a-modal>
+</template>
+
+<script>
+import { STable, Ellipsis } from '@/components'
+import Detail from './Detail'
+
+export default {
+  name: 'ParameterModal',
+  components: {
+    STable,
+    Ellipsis,
+    Detail
+  },
+  props: {
+    type: {
+      type: String,
+      default: 'radio'
+    },
+    selectedRowKey: {
+      type: Array,
+      default: () => {
+        return []
+      }
+    },
+    selectedRow: {
+      type: Array,
+      default: () => {
+        return []
+      }
+    }
+  },
+  data () {
+    return {
+      confirmLoading: false,
+      mdl: {},
+      modalTitle: null,
+      visible: false,
+      record: null,
+      form: this.$form.createForm(this),
+      // 查询参数
+      queryParam: {
+      },
+      extraQueryParam: {
+      },
+      projectStartTimeStart: undefined,
+      projectStartTimeEnd: undefined,
+
+      // 下拉框map
+      selectedRowKeys: [],
+      selectedRows: [],
+      parameterTypeMap: [],
+      options: {
+        alert: { show: true, clear: () => { this.selectedRowKeys = [] } },
+        rowSelection: {
+          selectedRowKeys: this.selectedRowKeys,
+          onChange: this.onSelectChange
+        }
+      },
+      optionAlertShow: false,
+      isCreated: false
+    }
+  },
+  created () {
+    // 下拉框map
+    this.parameterTypeMap = this.DictCache.getLabelByValueMapByType(this.DictCache.TYPE.PARAMETER_TYPE)
+  },
+  methods: {
+    selectVal (val) {
+      this.form.setFieldsValue({
+        'value': ''
+      })
+    },
+    handleOk () {
+      this.$refs.table.refresh()
+    },
+    onSelectChange (selectedRowKeys, selectedRows) {
+      this.selectedRowKeys = selectedRowKeys
+      this.selectedRows = selectedRows
+    },
+    resetSearchForm () {
+      this.queryParam = {
+      }
+      this.$refs.table.refresh(true)
+    },
+    base (record) {
+      this.visible = true
+      this.modalTitle = '新增查询条件'
+      this.form.resetFields()
+    },
+    handleCancel () {
+      this.visible = false
+      this.confirmLoading = false
+    },
+    handleSelect () {
+      const { form: { validateFieldsAndScroll } } = this
+      this.confirmLoading = true
+      validateFieldsAndScroll((errors, values) => {
+        if (errors) {
+          return
+        }
+        console.log(values)
+        this.$emit('selected', values)
+        this.confirmLoading = false
+        this.visible = false
+      })
+    },
+    mySelect (selectedRowKeys, selectedRows) {
+      if (this.type === 'radio') {
+        this.$refs.table.updateSelect(selectedRowKeys, selectedRows)
+        this.$refs.table.rowSelection.onChange(selectedRowKeys, selectedRows)
+      } else {
+        let mySelectedRowKeys
+        let mySelectedRows = this.selectedRows.filter(item => item.id !== selectedRowKeys[0])
+        if (this.selectedRowKeys.includes(selectedRowKeys[0])) {
+          mySelectedRowKeys = this.selectedRowKeys.filter(item => item !== selectedRowKeys[0])
+        } else {
+          mySelectedRowKeys = [...selectedRowKeys, ...this.selectedRowKeys]
+          mySelectedRows = [...mySelectedRows, ...selectedRows]
+        }
+        this.$refs.table.updateSelect(mySelectedRowKeys, mySelectedRows)
+        this.$refs.table.rowSelection.onChange(mySelectedRowKeys, mySelectedRows)
+      }
+    }
+  }
+}
+</script>

+ 68 - 26
src/views/dashboard/CheckJobReport.vue

@@ -4,31 +4,65 @@
       <div class="salesCard">
         <a-tabs default-active-key="1" size="large" :tab-bar-style="{marginBottom: '24px', paddingLeft: '16px'}">
           <div class="extra-wrapper" slot="tabBarExtraContent">
-            <a-month-picker
-              style="margin-left: 8px"
-              :default-value="moment(defaultStartMonth, monthFormat)"
-              :format="monthFormat"
-              v-model="queryParam.startMonth"
-              placeholder="开始月份"
-              @change="onStartChange" />
-            <a-month-picker
-              style="margin-left: 8px"
-              :default-value="moment(defaultEndMonth, monthFormat)"
-              :format="monthFormat"
-              v-model="queryParam.endMonth"
-              placeholder="结束月份"
-              @change="onEndChange" />
-            <a-button style="margin-left: 8px" type="default" @click="getData()">查询</a-button>
-            <a-button style="margin-left: 8px" type="primary" icon="printer" @click="handlePrint()">打印</a-button>
-            <a-button style="margin-left: 8px" type="primary" @click="doExport()">导出</a-button>
-            <a-select style="margin-left: 8px" @change="changeLevel" v-model="queryParam.standardLevel" placeholder="请选择">
-              <a-select-option
-                v-for="(label,value) in levelMap"
-                :key="value"
-                :label="label"
-                :value="parseInt(value)">{{ label }}
-              </a-select-option>
-            </a-select>
+            <a-row>
+              <a-col :md="3" :sm="24">
+                <a-month-picker
+                  style="margin-left: 8px"
+                  :default-value="moment(defaultStartMonth, monthFormat)"
+                  :format="monthFormat"
+                  v-model="queryParam.startMonth"
+                  placeholder="开始月份"
+                  @change="onStartChange" /></a-col>
+              <a-col :md="3" :sm="24">
+                <a-month-picker
+                  style="margin-left: 8px"
+                  :default-value="moment(defaultEndMonth, monthFormat)"
+                  :format="monthFormat"
+                  v-model="queryParam.endMonth"
+                  placeholder="结束月份"
+                  @change="onEndChange" /></a-col>
+              <a-col :md="3" :sm="24">
+                <a-tree-select
+                  style="width: 100%;margin-left: 8px;"
+                  :dropdownStyle="{ maxHeight: '400px', overflow: 'auto' }"
+                  :treeData="treeData"
+                  :treeNodeFilterProp="'title'"
+                  :showSearch="true"
+                  v-model="queryParam.typeId"
+                  placeholder="设备类型"
+                >
+                </a-tree-select>
+              </a-col>
+              <a-col :md="2" :sm="24">
+                <a-select style="margin-left: 8px" v-model="queryParam.sbLevel" placeholder="设备等级">
+                  <a-select-option
+                    v-for="(label,value) in sbLevelMap"
+                    :key="value"
+                    :label="label"
+                    :value="parseInt(value)">{{ label }}
+                  </a-select-option>
+                </a-select>
+              </a-col>
+              <a-col :md="2" :sm="24">
+                <a-select style="margin-left: 8px" @change="changeLevel" v-model="queryParam.standardLevel" placeholder="保养等级">
+                  <a-select-option
+                    v-for="(label,value) in levelMap"
+                    :key="value"
+                    :label="label"
+                    :value="parseInt(value)">{{ label }}
+                  </a-select-option>
+                </a-select>
+              </a-col>
+              <a-col :md="2" :sm="24">
+                <a-button style="margin-left: 8px" type="default" @click="getData()">查询</a-button>
+              </a-col>
+              <a-col :md="2" :sm="24">
+                <a-button style="margin-left: 8px" type="primary" @click="handlePrint()">打印</a-button>
+              </a-col>
+              <a-col :md="2" :sm="24">
+                <a-button style="margin-left: 8px" type="primary" @click="doExport()">导出</a-button>
+              </a-col>
+            </a-row>
           </div>
           <a-tab-pane loading="true" tab="图形统计" key="1">
             <a-row>
@@ -76,6 +110,7 @@ import { Chart } from '@antv/g2'
 import PrintInCheckJobReport from '@/views/dashboard/modules/PrintInCheckJobReport'
 import DetailCheckJobReport from '@/views/dashboard/modules/DetailCheckJobReport'
 import moment from 'moment'
+import { fetchSbTypeTree } from '@/api/sb/type'
 
 export default {
   name: 'Analysis',
@@ -94,6 +129,8 @@ export default {
     return {
       loading: false,
       serverData: [],
+      sbLevelMap: {},
+      treeData: [],
       monthFormat: 'YYYY-MM',
       defaultStartMonth: this.BaseTool.Moment().format(this.BaseTool.Date.PICKER_NORM_YEAR) + '-01',
       defaultEndMonth: this.BaseTool.Moment().format(this.BaseTool.Date.PICKER_NORM_YEAR) + '-12',
@@ -101,7 +138,8 @@ export default {
         // year: 2021,
         startMonth: this.BaseTool.Moment().format(this.BaseTool.Date.PICKER_NORM_YEAR) + '-01-01',
         endMonth: this.BaseTool.Moment().format(this.BaseTool.Date.PICKER_NORM_YEAR) + '-12-01',
-        standardLevel: 2
+        standardLevel: 2,
+        sbLevel: 1
       },
       years: [],
       levelMap: {},
@@ -147,6 +185,10 @@ export default {
   },
   created () {
     this.levelMap = this.DictCache.getLabelByValueMapByType(this.DictCache.TYPE.CHECK_PLAN_LEVEL)
+    this.sbLevelMap = this.DictCache.getLabelByValueMapByType(this.DictCache.TYPE.SBINFO_LEVEL)
+    fetchSbTypeTree().then(res => {
+      this.treeData = res.data
+    })
   },
   mounted () {
     this.$nextTick(function () {

+ 1 - 0
src/views/dashboard/CheckJobReportWeek.vue

@@ -205,6 +205,7 @@ export default {
       this.chart.legend({
         position: 'bottom'
       })
+      // 折线数据
       this.chart.line().position('week*totalUseHours')
       this.chart.point().position('week*totalUseHours').size(4).shape('circle').style({
         stroke: '#fff',

+ 280 - 0
src/views/dashboard/RepairReportSbInfo.vue

@@ -0,0 +1,280 @@
+<template>
+  <div class="page-header-index-wide">
+    <a-card :title="title" :loading="loading" v-show="visible" :bordered="false" :body-style="{padding: '0'}">
+      <div class="salesCard">
+        <a-tabs default-active-key="1" size="large" :tab-bar-style="{marginBottom: '24px', paddingLeft: '16px'}">
+          <div class="extra-wrapper" slot="tabBarExtraContent">
+            <a-button style="margin-left: 8px" type="default" @click="getData()">查询</a-button>
+            <a-button style="margin-left: 8px" type="primary" icon="printer" @click="handlePrint()">打印</a-button>
+            <a-button style="margin-left: 8px" type="primary" @click="doExport()">导出</a-button>
+            <a-button style="margin-left: 8px" type="primary" @click="handleCancel()">返回</a-button>
+          </div>
+          <a-tab-pane loading="true" tab="图形统计" key="1">
+            <a-row>
+              <a-col :xl="24" :lg="24" :md="24" :sm="24" :xs="24">
+                <div style="padding: 10px">
+                  <div id="container" style="width: 100%;overflow-x:auto"></div>
+                </div>
+              </a-col>
+            </a-row>
+          </a-tab-pane>
+          <a-tab-pane loading="true" tab="表格统计" key="2">
+            <a-row>
+              <a-col :xl="24" :lg="24" :md="24" :sm="24" :xs="24">
+                <div style="padding: 10px">
+                  <a-table
+                    bordered
+                    :data-source="tableData"
+                    :columns="columns"
+                    tableLayout="auto"
+                    :scroll="{x: 1, y: BaseTool.Constant.scrollY }"
+                    rowKey="month">
+                    <span slot="action" slot-scope="record">
+                      <template>
+                        <a @click="handleView(record)">查看明细</a>
+                        <a-divider type="vertical" />
+                        <a @click="doExportDetail(record)">导出</a>
+                      </template>
+                    </span>
+                  </a-table>
+                </div>
+              </a-col>
+            </a-row>
+          </a-tab-pane>
+        </a-tabs>
+      </div>
+    </a-card>
+    <print-in-repair-report ref="basePrintModal" @ok="handleOk"/>
+    <detail-repair-report ref="detailModal" @ok="handleOk"/>
+  </div>
+</template>
+
+<script>
+import { getSbInfoReport, exportSbInfoReport, exportSbInfoReportYear } from '@/api/report/application-form'
+import { Chart } from '@antv/g2'
+import PrintInRepairReport from '@/views/dashboard/modules/PrintInRepairReport'
+import DetailRepairReport from '@/views/dashboard/modules/DetailRepairReport'
+import moment from 'moment'
+// const DataSet = require('@antv/data-set')
+export default {
+  name: 'RepairReportSbInfo',
+  components: {
+    PrintInRepairReport,
+    Chart,
+    DetailRepairReport
+  },
+  props: {
+    sbId: {
+      type: String,
+      default: null
+    },
+    title: {
+      type: String,
+      default: '设备维修分析'
+    }
+  },
+  data () {
+    return {
+      loading: false,
+      serverData: [],
+      monthFormat: 'YYYY-MM',
+      queryParam: {
+        // year: 2021,
+        sbId: this.sbId
+      },
+      visible: false,
+      chart: null, // 创建一个chart变量
+      chartsData: [],
+      tableData: [],
+      categoryMap: {},
+      fields: [],
+      // 表头
+      columns: [
+        {
+          title: '年份',
+          width: 180,
+          dataIndex: 'year'
+        },
+        {
+          title: '工单次数',
+          width: 120,
+          dataIndex: 'num'
+        },
+        {
+          title: '工单类型',
+          width: 120,
+          dataIndex: 'category',
+          customRender: (text, record, index) => {
+            return this.BaseTool.Object.getField(this.categoryMap, text)
+          }
+        },
+        {
+          title: '寿命',
+          width: 120,
+          dataIndex: 'workYear'
+        },
+        {
+          title: '操作',
+          key: 'action',
+          width: '200px',
+          align: 'center',
+          scopedSlots: { customRender: 'action' }
+        }
+      ]
+    }
+  },
+  created () {
+    this.categoryMap = this.DictCache.getLabelByValueMapByType(this.DictCache.TYPE.REPAIR_APPLICATION_FORM_CATEGORY)
+  },
+  mounted () {
+    /* this.$nextTick(function () {
+      this.getData()
+    }) */
+  },
+  methods: {
+    moment,
+    base () {
+      this.visible = true
+      this.getData()
+    },
+    onStartChange (date, dateString) {
+      this.queryParam.startMonth = this.BaseTool.Date.formatter(dateString + '-01', this.BaseTool.Date.PICKER_NORM_DATE_PATTERN)
+    },
+    onEndChange (date, dateString) {
+      this.queryParam.endMonth = this.BaseTool.Date.formatter(dateString + '-01', this.BaseTool.Date.PICKER_NORM_DATE_PATTERN)
+    },
+    getData () {
+      getSbInfoReport(this.queryParam)
+        .then(res => {
+          this.chartsData = res.data.data
+          this.tableData = res.data.dataTable
+
+          // 需要将数据分组:总数,完成数
+          /*  const groupData = []
+          this.tableData.forEach(function (data) {
+            groupData.push({ name: '总数', year: data.year + '', num: data.num })
+            groupData.push({ name: '计划数', year: data.year + '', num: data.planNum })
+            groupData.push({ name: '非计划数', year: data.year + '', num: data.notPlanNum })
+          }) */
+          this.tableData.forEach(function (data) {
+            data.year = data.year + ''
+          })
+          this.getCharts('container', this.tableData)// 调用统计图
+        })
+    },
+    getCharts (id, data) {
+      this.chart && this.chart.destroy()// 防止点击搜索按钮新增一个
+      this.chart = new Chart({
+        container: id,
+        autoFit: true,
+        height: 400
+      })
+      this.chart.data(data)
+      this.chart.scale('num', {
+        nice: true
+      })
+      this.chart.tooltip({
+        showMarkers: false,
+        shared: true
+      })
+      this.chart.interval().position('year*num').color('name').adjust([
+        {
+          type: 'dodge',
+          marginRatio: 0
+        }
+      ])
+      this.chart.interaction('active-region')
+      this.chart.legend({
+        position: 'bottom'
+      })
+      // 折线数据
+      this.chart.line().position('year*workYear')
+      this.chart.point().position('year*workYear').size(4).shape('circle').style({
+        stroke: '#fff',
+        lineWidth: 1
+      })
+      this.chart.render()
+    },
+    doExport () {
+      const parameter = {
+        ...this.queryParam
+      }
+      exportSbInfoReport(parameter).then(file => {
+        this.BaseTool.UPLOAD.downLoadExportExcel(file)
+      })
+    },
+    doExportDetail (record) {
+      const parameter = {
+        ...this.queryParam,
+        year: record.year,
+        category: record.category
+      }
+      exportSbInfoReportYear(parameter).then(file => {
+        this.BaseTool.UPLOAD.downLoadExportExcel(file)
+      })
+    },
+    handlePrint (record) {
+      const modal = this.$refs.basePrintModal
+      this.visible = false
+      modal.base({ startMonth: this.queryParam.startMonth, endMonth: this.queryParam.endMonth, title: this.title, data: this.chartsData })
+    },
+    handleView (record) {
+      const modal = this.$refs.detailModal
+      modal.base(record)
+    },
+    handleOk () {
+      this.visible = true
+    },
+    handleCancel () {
+      this.visible = false
+      this.confirmLoading = false
+      this.$emit('ok')
+    }
+  }
+}
+</script>
+
+<style lang="less" scoped>
+.extra-wrapper {
+  line-height: 55px;
+  padding-right: 24px;
+
+  .extra-item {
+    display: inline-block;
+    margin-right: 24px;
+
+    a {
+      margin-left: 24px;
+    }
+  }
+}
+
+.antd-pro-pages-dashboard-analysis-twoColLayout {
+  position: relative;
+  display: flex;
+  display: block;
+  flex-flow: row wrap;
+}
+
+.antd-pro-pages-dashboard-analysis-salesCard {
+  height: calc(100% - 24px);
+  /deep/ .ant-card-head {
+    position: relative;
+  }
+}
+
+.dashboard-analysis-iconGroup {
+  i {
+    margin-left: 16px;
+    color: rgba(0,0,0,.45);
+    cursor: pointer;
+    transition: color .32s;
+    color: black;
+  }
+}
+.analysis-salesTypeRadio {
+  position: absolute;
+  right: 54px;
+  bottom: 12px;
+}
+</style>

+ 281 - 0
src/views/dashboard/RepairReportSbInfoFee.vue

@@ -0,0 +1,281 @@
+<template>
+  <div class="page-header-index-wide">
+    <a-card :title="title" :loading="loading" v-show="visible" :bordered="false" :body-style="{padding: '0'}">
+      <div class="salesCard">
+        <a-tabs default-active-key="1" size="large" :tab-bar-style="{marginBottom: '24px', paddingLeft: '16px'}">
+          <div class="extra-wrapper" slot="tabBarExtraContent">
+            <a-button style="margin-left: 8px" type="default" @click="getData()">查询</a-button>
+            <a-button style="margin-left: 8px" type="primary" icon="printer" @click="handlePrint()">打印</a-button>
+            <a-button style="margin-left: 8px" type="primary" @click="doExport()">导出</a-button>
+            <a-button style="margin-left: 8px" type="primary" @click="handleCancel()">返回</a-button>
+          </div>
+          <a-tab-pane loading="true" tab="图形统计" key="1">
+            <a-row>
+              <a-col :xl="24" :lg="24" :md="24" :sm="24" :xs="24">
+                <div style="padding: 10px">
+                  <div id="container2" style="width: 100%;overflow-x:auto"></div>
+                </div>
+              </a-col>
+            </a-row>
+          </a-tab-pane>
+          <a-tab-pane loading="true" tab="表格统计" key="2">
+            <a-row>
+              <a-col :xl="24" :lg="24" :md="24" :sm="24" :xs="24">
+                <div style="padding: 10px">
+                  <a-table
+                    bordered
+                    :data-source="tableData"
+                    :columns="columns"
+                    tableLayout="auto"
+                    :scroll="{x: 1, y: BaseTool.Constant.scrollY }"
+                    rowKey="month">
+                    <span slot="action" slot-scope="record">
+                      <template>
+                        <a @click="handleView(record)">查看明细</a>
+                        <a-divider type="vertical" />
+                        <a @click="doExportDetail(record)">导出</a>
+                      </template>
+                    </span>
+                  </a-table>
+                </div>
+              </a-col>
+            </a-row>
+          </a-tab-pane>
+        </a-tabs>
+      </div>
+    </a-card>
+    <print-in-repair-report-fee ref="basePrintModal" @ok="handleOk"/>
+    <detail-repair-report-fee ref="detailModal" @ok="handleOk"/>
+  </div>
+</template>
+
+<script>
+import { getSbInfoReportFee, exportSbInfoReportFee, exportSbInfoReportFeeYear } from '@/api/report/application-form'
+import { Chart } from '@antv/g2'
+import PrintInRepairReportFee from '@/views/dashboard/modules/PrintInRepairReportFee'
+import DetailRepairReportFee from '@/views/dashboard/modules/DetailRepairReportFee'
+import moment from 'moment'
+// const DataSet = require('@antv/data-set')
+export default {
+  name: 'RepairReportSbInfoFee',
+  components: {
+    PrintInRepairReportFee,
+    Chart,
+    DetailRepairReportFee
+  },
+  props: {
+    sbId: {
+      type: String,
+      default: null
+    },
+    title: {
+      type: String,
+      default: '设备费用分析'
+    }
+  },
+  data () {
+    return {
+      loading: false,
+      serverData: [],
+      monthFormat: 'YYYY-MM',
+      queryParam: {
+        // year: 2021,
+        sbId: this.sbId
+      },
+      visible: false,
+      chart: null, // 创建一个chart变量
+      chartsData: [],
+      typeMap: {},
+      tableData: [],
+      fields: [],
+      // 表头
+      columns: [
+        {
+          title: '年份',
+          width: 180,
+          dataIndex: 'year'
+        },
+        {
+          title: '费用次数',
+          width: 120,
+          dataIndex: 'num'
+        },
+        {
+          title: '费用类型',
+          width: 120,
+          dataIndex: 'type',
+          customRender: (text, record, index) => {
+            return this.BaseTool.Object.getField(this.typeMap, text)
+          }
+        },
+        {
+          title: '寿命',
+          width: 120,
+          dataIndex: 'workYear'
+        },
+        {
+          title: '操作',
+          key: 'action',
+          width: '200px',
+          align: 'center',
+          scopedSlots: { customRender: 'action' }
+        }
+      ]
+    }
+  },
+  created () {
+    this.typeMap = this.DictCache.getLabelByValueMapByType(this.DictCache.TYPE.REPAIR_FEE_TYPE)
+  },
+  mounted () {
+    /* this.$nextTick(function () {
+      this.getData()
+    }) */
+  },
+  methods: {
+    moment,
+    base () {
+      this.visible = true
+      this.getData()
+    },
+    onStartChange (date, dateString) {
+      this.queryParam.startMonth = this.BaseTool.Date.formatter(dateString + '-01', this.BaseTool.Date.PICKER_NORM_DATE_PATTERN)
+    },
+    onEndChange (date, dateString) {
+      this.queryParam.endMonth = this.BaseTool.Date.formatter(dateString + '-01', this.BaseTool.Date.PICKER_NORM_DATE_PATTERN)
+    },
+    getData () {
+      getSbInfoReportFee(this.queryParam)
+        .then(res => {
+          this.chartsData = res.data.data
+          this.tableData = res.data.dataTable
+
+          // 需要将数据分组:总数,完成数
+          /*  const groupData = []
+          this.tableData.forEach(function (data) {
+            groupData.push({ name: '总数', year: data.year + '', num: data.num })
+            groupData.push({ name: '计划数', year: data.year + '', num: data.planNum })
+            groupData.push({ name: '非计划数', year: data.year + '', num: data.notPlanNum })
+          }) */
+          this.tableData.forEach(function (data) {
+            data.year = data.year + ''
+            console.log('data: ' + data)
+          })
+          this.getCharts('container2', this.tableData)// 调用统计图
+        })
+    },
+    getCharts (id, data) {
+      this.chart && this.chart.destroy()// 防止点击搜索按钮新增一个
+      this.chart = new Chart({
+        container: id,
+        autoFit: true,
+        height: 400
+      })
+      this.chart.data(data)
+      this.chart.scale('num', {
+        nice: true
+      })
+      this.chart.tooltip({
+        showMarkers: false,
+        shared: true
+      })
+      this.chart.interval().position('year*num').color('name').adjust([
+        {
+          type: 'dodge',
+          marginRatio: 0
+        }
+      ])
+      this.chart.interaction('active-region')
+      this.chart.legend({
+        position: 'bottom'
+      })
+      // 折线数据
+      this.chart.line().position('year*workYear')
+      this.chart.point().position('year*workYear').size(4).shape('circle').style({
+        stroke: '#fff',
+        lineWidth: 1
+      })
+      this.chart.render()
+    },
+    doExport () {
+      const parameter = {
+        ...this.queryParam
+      }
+      exportSbInfoReportFee(parameter).then(file => {
+        this.BaseTool.UPLOAD.downLoadExportExcel(file)
+      })
+    },
+    doExportDetail (record) {
+      const parameter = {
+        ...this.queryParam,
+        year: record.year,
+        type: record.type
+      }
+      exportSbInfoReportFeeYear(parameter).then(file => {
+        this.BaseTool.UPLOAD.downLoadExportExcel(file)
+      })
+    },
+    handlePrint (record) {
+      const modal = this.$refs.basePrintModal
+      this.visible = false
+      modal.base({ startMonth: this.queryParam.startMonth, endMonth: this.queryParam.endMonth, title: this.title, data: this.chartsData })
+    },
+    handleView (record) {
+      const modal = this.$refs.detailModal
+      modal.base(record)
+    },
+    handleOk () {
+      this.visible = true
+    },
+    handleCancel () {
+      this.visible = false
+      this.confirmLoading = false
+      this.$emit('ok')
+    }
+  }
+}
+</script>
+
+<style lang="less" scoped>
+.extra-wrapper {
+  line-height: 55px;
+  padding-right: 24px;
+
+  .extra-item {
+    display: inline-block;
+    margin-right: 24px;
+
+    a {
+      margin-left: 24px;
+    }
+  }
+}
+
+.antd-pro-pages-dashboard-analysis-twoColLayout {
+  position: relative;
+  display: flex;
+  display: block;
+  flex-flow: row wrap;
+}
+
+.antd-pro-pages-dashboard-analysis-salesCard {
+  height: calc(100% - 24px);
+  /deep/ .ant-card-head {
+    position: relative;
+  }
+}
+
+.dashboard-analysis-iconGroup {
+  i {
+    margin-left: 16px;
+    color: rgba(0,0,0,.45);
+    cursor: pointer;
+    transition: color .32s;
+    color: black;
+  }
+}
+.analysis-salesTypeRadio {
+  position: absolute;
+  right: 54px;
+  bottom: 12px;
+}
+</style>

+ 214 - 0
src/views/dashboard/template/ChartReport.vue

@@ -0,0 +1,214 @@
+<template>
+  <div class="page-header-index-wide">
+    <a-card :title="queryParam.name" :loading="loading" v-show="visible" :bordered="false" :body-style="{padding: '0'}">
+      <div class="salesCard">
+        <a-tabs default-active-key="1" size="large" :tab-bar-style="{marginBottom: '24px', paddingLeft: '16px'}">
+          <div class="extra-wrapper" slot="tabBarExtraContent">
+            <a-month-picker
+              style="margin-left: 8px"
+              :default-value="moment(defaultStartMonth, monthFormat)"
+              :format="monthFormat"
+              v-model="queryParam.startMonth"
+              placeholder="开始月份"
+              @change="onStartChange" />
+            <a-month-picker
+              style="margin-left: 8px"
+              :default-value="moment(defaultEndMonth, monthFormat)"
+              :format="monthFormat"
+              v-model="queryParam.endMonth"
+              placeholder="结束月份"
+              @change="onEndChange" />
+            <a-button style="margin-left: 8px" type="default" @click="getData()">查询</a-button>
+            <a-button style="margin-left: 8px" type="default" icon="printer" @click="handlePrint()">打印</a-button>
+            <a-button style="margin-left: 8px" type="primary" @click="doExport()">导出</a-button>
+          </div>
+          <a-tab-pane loading="true" tab="图形统计" key="1">
+            <a-row>
+              <a-col :xl="24" :lg="24" :md="24" :sm="24" :xs="24">
+                <div style="padding: 10px">
+                  <div id="container" style="width: 100%;overflow-x:auto"></div>
+                </div>
+              </a-col>
+            </a-row>
+          </a-tab-pane>
+          <a-tab-pane loading="true" tab="表格统计" key="2">
+            <a-row>
+              <a-col :xl="24" :lg="24" :md="24" :sm="24" :xs="24">
+                <div style="padding: 10px">
+                  <a-table
+                    bordered
+                    :data-source="chartsData"
+                    :columns="columns"
+                    tableLayout="auto"
+                    :scroll="{x: 1, y: BaseTool.Constant.scrollY }"
+                    rowKey="month">
+                    <span slot="action" slot-scope="record">
+                      <template>
+                        <a @click="handleView(record)">查看明细</a>
+                        <a-divider type="vertical" />
+                        <a @click="doExportDetail(record)">导出</a>
+                      </template>
+                    </span>
+                  </a-table>
+                </div>
+              </a-col>
+            </a-row>
+          </a-tab-pane>
+        </a-tabs>
+      </div>
+    </a-card>
+    <print-in-check-job-report ref="basePrintModal" @ok="handleOk"/>
+    <detail-check-job-report ref="detailModal" @ok="handleOk"/>
+  </div>
+</template>
+
+<script>
+import { getChartReport } from '@/api/report/template'
+import { Chart } from '@antv/g2'
+import PrintInCheckJobReport from '@/views/dashboard/modules/PrintInCheckJobReport'
+import DetailCheckJobReport from '@/views/dashboard/modules/DetailCheckJobReport'
+import moment from 'moment'
+
+export default {
+  name: 'ChartReport',
+  components: {
+    PrintInCheckJobReport,
+    Chart,
+    DetailCheckJobReport
+  },
+  props: {
+  },
+  data () {
+    return {
+      // 自定义报表对象
+      chartData: {
+        title: '统计报表'
+      },
+      loading: false,
+      serverData: [],
+      sbLevelMap: {},
+      treeData: [],
+      monthFormat: 'YYYY-MM',
+      defaultStartMonth: this.BaseTool.Moment().format(this.BaseTool.Date.PICKER_NORM_YEAR) + '-01',
+      defaultEndMonth: this.BaseTool.Moment().format(this.BaseTool.Date.PICKER_NORM_YEAR) + '-12',
+      queryParam: {
+      },
+      years: [],
+      levelMap: {},
+      visible: true,
+      chart: null, // 创建一个chart变量
+      chartsData: [],
+      // 表头
+      columns: [
+        {
+          title: '月份',
+          width: 180,
+          dataIndex: 'month'
+        },
+        {
+          title: '数量',
+          width: 120,
+          dataIndex: 'num'
+        },
+        {
+          title: '操作',
+          key: 'action',
+          width: '200px',
+          align: 'center',
+          scopedSlots: { customRender: 'action' }
+        }
+      ]
+    }
+  },
+  created () {
+    // 获取浏览器的请求参数:页面跳转过来的数据
+    this.queryParam = this.$route.query
+    console.log('this.queryParam: ' + this.queryParam)
+  },
+  mounted () {
+    this.$nextTick(function () {
+      this.getData()
+    })
+  },
+  methods: {
+    moment,
+    getData () {
+      getChartReport(this.queryParam)
+        .then(res => {
+          this.chartsData = res.data
+          this.getCharts('container', this.chartsData)// 调用统计图
+        })
+    },
+    getCharts (id, data) {
+      this.chart && this.chart.destroy()// 防止点击搜索按钮新增一个
+      this.chart = new Chart({
+        container: 'container',
+        autoFit: true,
+        height: 400
+      })
+      this.chart.data(data)
+      this.chart.scale('num', {
+        nice: true
+      })
+      this.chart.tooltip({
+        showMarkers: true,
+        shared: true
+      })
+      this.chart.interval().position('month*num')
+      this.chart.interaction('active-region')
+      this.chart.legend({
+        position: 'bottom'
+      })
+      this.chart.render()
+    },
+    handleOk () {
+      this.visible = true
+    }
+  }
+}
+</script>
+
+<style lang="less" scoped>
+.extra-wrapper {
+  line-height: 55px;
+  padding-right: 24px;
+
+  .extra-item {
+    display: inline-block;
+    margin-right: 24px;
+
+    a {
+      margin-left: 24px;
+    }
+  }
+}
+
+.antd-pro-pages-dashboard-analysis-twoColLayout {
+  position: relative;
+  display: flex;
+  display: block;
+  flex-flow: row wrap;
+}
+
+.antd-pro-pages-dashboard-analysis-salesCard {
+  height: calc(100% - 24px);
+  /deep/ .ant-card-head {
+    position: relative;
+  }
+}
+
+.dashboard-analysis-iconGroup {
+  i {
+    margin-left: 16px;
+    color: rgba(0,0,0,.45);
+    cursor: pointer;
+    transition: color .32s;
+    color: black;
+  }
+}
+.analysis-salesTypeRadio {
+  position: absolute;
+  right: 54px;
+  bottom: 12px;
+}
+</style>

+ 0 - 1
src/views/operate/article/Article.vue

@@ -104,7 +104,6 @@ export default {
       },
       typeMap: {},
       // 表头
-
       columns: [
         {
           title: '序号',

+ 36 - 3
src/views/operate/article/modules/BaseForm.vue

@@ -17,7 +17,7 @@
         :labelCol="labelCol"
         :wrapperCol="wrapperCol"
       >
-        <a-select v-decorator="['type', {rules: [{required: true, message: '类别不能为空'}]}]" placeholder="请选择">
+        <a-select @change="handleChangeType" v-decorator="['type', {rules: [{required: true, message: '类别不能为空'}]}]" placeholder="请选择">
           <a-select-option
             v-for="(value,key) in typeMap"
             :key="key"
@@ -33,6 +33,21 @@
         <a-input
           v-decorator="['title', {rules: [{required: true, message: '标题不能为空'}]}]" />
       </a-form-item>
+      <a-form-item
+        label="父文章"
+        :labelCol="labelCol"
+        :wrapperCol="wrapperCol"
+        v-show="type==3||type==4||type==5"
+      >
+        <a-select v-decorator="['parentId']" >
+          <a-select-option
+            v-for="({id,title}) in pData"
+            :key="id"
+            :label="title"
+            :value="id">{{ title }}
+          </a-select-option>
+        </a-select>
+      </a-form-item>
       <a-form-item
         label="简介"
         :labelCol="labelCol"
@@ -115,7 +130,7 @@
 
 <script>
 import pick from 'lodash.pick'
-import { addArticle, updateArticle } from '@/api/operate/article'
+import { addArticle, updateArticle, queryArticle } from '@/api/operate/article'
 import WangEditor from '@/components/Editor/WangEditor'
 import UploadImg from '@/components/Upload/UploadImg'
 import UploadArticleFile from '@/components/Upload/UploadArticleFile'
@@ -137,6 +152,7 @@ export default {
         sm: { span: 20 }
       },
       topFlag: 0,
+      pData: [],
       status: 1,
       confirmLoading: false,
       mdl: {},
@@ -145,7 +161,8 @@ export default {
       visible: false,
       content: '',
       picture: '',
-      resultContent: ''
+      resultContent: '',
+      type: null
     }
   },
   props: {
@@ -154,6 +171,11 @@ export default {
       default: () => ({})
     }
   },
+  created () {
+    queryArticle({ type: 2 }).then(res => {
+      this.pData = res.data
+    })
+  },
   methods: {
     base (record) {
       this.visible = true
@@ -165,10 +187,12 @@ export default {
         return
       }
       this.modalTitle = '编辑'
+      this.type = record.type
       const { form: { setFieldsValue } } = this
       this.$nextTick(() => {
         setFieldsValue(Object.assign(pick(record, [
           'id',
+          'parentId',
           'type',
           'title',
           'sort',
@@ -196,6 +220,9 @@ export default {
     catchData (content) {
       this.resultContent = content
     },
+    handleChangeType (value) {
+      this.type = value
+    },
     catchImage (fileList) {
       if (fileList.length !== 0) {
         this.picture = fileList[0].url
@@ -216,6 +243,12 @@ export default {
           status: this.status,
           content: this.resultContent ? this.resultContent : this.content
         }
+        if (this.type === 2) {
+          if (values.parentId == null) {
+            this.$message.error('请选择父文章')
+            return
+          }
+        }
         if (this.BaseTool.String.isBlank(values.id)) {
           addArticle(values)
             .then(() => {

+ 304 - 305
src/views/purchase/supplier-goods-list/modules/SupplierGoodsListSelectModal.vue

@@ -1,321 +1,320 @@
 <template>
-    <a-modal
-            :title="modalTitle"
-            :width="1000"
-            :visible="visible"
-            :confirmLoading="confirmLoading"
-            class="ant-modal2"
-            @cancel="handleCancel"
-    >
-        <a-card :bordered="false">
-            <div class="table-page-search-wrapper">
-                <a-form layout="inline">
-                    <a-row :gutter="48">
-                        <a-col :md="8" :sm="24">
-                            <a-form-item label="关键字">
-                                <a-input v-model="queryParam.keyword" placeholder="请输入名称/类型名称"/>
-                            </a-form-item>
-                        </a-col>
-                        <a-col :md="8 || 24" :sm="24">
-                <span class="table-page-search-submitButtons">
-                  <a-button type="primary" @click="$refs.table.refresh(true)">查询</a-button>
-                  <a-button style="margin-left: 8px" @click="resetSearchForm">重置</a-button>
-                </span>
-                        </a-col>
-                    </a-row>
-                </a-form>
-            </div>
+  <a-modal
+    :title="modalTitle"
+    :width="1000"
+    :visible="visible"
+    :confirmLoading="confirmLoading"
+    class="ant-modal2"
+    @cancel="handleCancel"
+  >
+    <a-card :bordered="false">
+      <div class="table-page-search-wrapper">
+        <a-form layout="inline">
+          <a-row :gutter="48">
+            <a-col :md="8" :sm="24">
+              <a-form-item label="关键字">
+                <a-input v-model="queryParam.keyword" placeholder="请输入名称/类型名称"/>
+              </a-form-item>
+            </a-col>
+            <a-col :md="8 || 24" :sm="24">
+              <span class="table-page-search-submitButtons">
+                <a-button type="primary" @click="$refs.table.refresh(true)">查询</a-button>
+                <a-button style="margin-left: 8px" @click="resetSearchForm">重置</a-button>
+              </span>
+            </a-col>
+          </a-row>
+        </a-form>
+      </div>
 
-            <div class="table-operator">
-            </div>
+      <div class="table-operator">
+      </div>
 
-            <s-table
-                    ref="table"
-                    size="default"
-                    rowKey="id"
-                    :columns="columns"
-                    :data="loadData"
-                    :alert="options.alert"
-                    :customRow="options.customRow"
-                    :rowSelection="options.rowSelection"
-                    showPagination="auto"
-            >
-                <span slot="action" slot-scope="record1">
-                  <template>
-                    <a @click="handleView(record1)">查看</a>
-                  </template>
-                </span>
-            </s-table>
-            <detail ref="detailModal"/>
-        </a-card>
-        <template slot="footer">
-            <a-button :loading="confirmLoading" type="primary" @click="handleCancel()">取消</a-button>
-            <a-button :loading="confirmLoading" type="primary" @click="handleSelect()">确定</a-button>
-        </template>
-    </a-modal>
+      <s-table
+        ref="table"
+        size="default"
+        rowKey="id"
+        :columns="columns"
+        :data="loadData"
+        :alert="options.alert"
+        :customRow="options.customRow"
+        :rowSelection="options.rowSelection"
+        showPagination="auto"
+      >
+        <span slot="action" slot-scope="record1">
+          <template>
+            <a @click="handleView(record1)">查看</a>
+          </template>
+        </span>
+      </s-table>
+      <detail ref="detailModal"/>
+    </a-card>
+    <template slot="footer">
+      <a-button :loading="confirmLoading" type="primary" @click="handleCancel()">取消</a-button>
+      <a-button :loading="confirmLoading" type="primary" @click="handleSelect()">确定</a-button>
+    </template>
+  </a-modal>
 </template>
 
 <script>
-    import { STable, Ellipsis } from '@/components'
-    import Detail from './Detail'
-    import { getSupplierGoodsListPage, fetchSupplierGoodsList } from '@/api/purchase/supplier-goods-list'
+import { STable, Ellipsis } from '@/components'
+import Detail from './Detail'
+import { getSupplierGoodsListPage, fetchSupplierGoodsList } from '@/api/purchase/supplier-goods-list'
 
-    export default {
-        name: 'SupplierGoodsListSelectModal',
-        components: {
-            STable,
-            Ellipsis,
-            Detail
+export default {
+  name: 'SupplierGoodsListSelectModal',
+  components: {
+    STable,
+    Ellipsis,
+    Detail
+  },
+  props: {
+    type: {
+      type: String,
+      default: 'radio'
+    },
+    selectedRowKey: {
+      type: Array,
+      default: () => {
+        return []
+      }
+    },
+    selectedRow: {
+      type: Array,
+      default: () => {
+        return []
+      }
+    }
+  },
+  data () {
+    return {
+      confirmLoading: false,
+      mdl: {},
+      modalTitle: null,
+      visible: false,
+      record: null,
+      // 查询参数
+      queryParam: {
+      },
+      extraQueryParam: {
+      },
+      // 表头
+      columns: [
+        {
+          title: '序号',
+          dataIndex: 'index',
+          customRender: (text, record, index) => {
+            return `${(this.$refs.table.localPagination.current - 1) * this.$refs.table.localPagination.pageSize + index + 1}`
+          }
         },
-        props: {
-            type: {
-                type: String,
-                default: 'radio'
-            },
-            selectedRowKey: {
-                type: Array,
-                default: () => {
-                    return []
-                }
-            },
-            selectedRow: {
-                type: Array,
-                default: () => {
-                    return []
-                }
-            }
+        {
+          title: '供应商主键',
+          dataIndex: 'supplierId'
         },
-        data () {
-            return {
-                confirmLoading: false,
-                mdl: {},
-                modalTitle: null,
-                visible: false,
-                record: null,
-                // 查询参数
-                queryParam: {
-                },
-                extraQueryParam: {
-                },
-                // 表头
-                columns: [
-                    {
-                        title: '序号',
-                        dataIndex: 'index',
-                        customRender: (text, record, index) => {
-                            return `${(this.$refs.table.localPagination.current - 1) * this.$refs.table.localPagination.pageSize + index + 1}`
-                        }
-                    },
-                                                                                                                                                {
-                                title: '供应商主键',
-                                dataIndex: 'supplierId'
-                            },
-                                                                                                                                                        {
-                                title: '供应商名称',
-                                dataIndex: 'supplierName'
-                            },
-                                                                                                                                                        {
-                                title: '编号',
-                                dataIndex: 'no'
-                            },
-                                                                                                                                                            {
-                                    title: '类别',
-                                    dataIndex: 'type',
-                                    customRender: (text, record, index) => {
-                                        return this.BaseTool.Object.getField(this.typeMap, text)
-                                    }                  ,
-                                },
-                                                                                                                                                        {
-                                title: '名称',
-                                dataIndex: 'name'
-                            },
-                                                                                                                                                        {
-                                title: '规格',
-                                dataIndex: 'specs'
-                            },
-                                                                                                                                                            {
-                                    title: '单位',
-                                    dataIndex: 'unit',
-                                    customRender: (text, record, index) => {
-                                        return this.BaseTool.Object.getField(this.unitMap, text)
-                                    }                  ,
-                                },
-                                                                                                                                                            {
-                                    title: '单价',
-                                    dataIndex: 'price',
-                                    customRender: (text, record, index) => {
-                                        return this.BaseTool.Amount.formatter(text)
-                                    }                                ,
-                                },
-                                                                                                                                                            {
-                                    title: '库存',
-                                    dataIndex: 'stock',
-                                    customRender: (text, record, index) => {
-                                        return this.BaseTool.Amount.formatter(text)
-                                    }                                ,
-                                },
-                                                                                                                                                        {
-                                title: '删除标志',
-                                dataIndex: 'delFlag'
-                            },
-                                                                                                                                                                                                    {
-                                title: '创建人名称',
-                                dataIndex: 'createdUserName'
-                            },
-                                                                                                                                                        {
-                                title: '创建时间',
-                                dataIndex: 'createdTime'
-                            },
-                                                                                                                                                                                                                                {
-                        title: '操作',
-                        key: 'action',
-                        width: '200px',
-                        align: 'center',
-                        scopedSlots: { customRender: 'action' }
-                    }
-                ],
-                // 下拉框map
-                                    typeMap: {},
-                                    unitMap: {},
-                                // 加载数据方法 必须为 Promise 对象
-                loadData: parameter => {
-                    parameter = {
-                        ...parameter,
-                        ...this.queryParam,
-                        ...this.extraQueryParam,
-                        dataScope: {
-                            sortBy: 'desc',
-                            sortName: 'update_time'
-                        }
-                    }
-                    return getSupplierGoodsListPage(Object.assign(parameter, this.queryParam))
-                            .then(res => {
-                                return res.data
-                            })
-                },
-                selectedRowKeys: [],
-                selectedRows: [],
+        {
+          title: '供应商名称',
+          dataIndex: 'supplierName'
+        },
+        {
+          title: '编号',
+          dataIndex: 'no'
+        },
+        {
+          title: '类别',
+          dataIndex: 'type',
+          customRender: (text, record, index) => {
+            return this.BaseTool.Object.getField(this.typeMap, text)
+          }
+        },
+        {
+          title: '名称',
+          dataIndex: 'name'
+        },
+        {
+          title: '规格',
+          dataIndex: 'specs'
+        },
+        {
+          title: '单位',
+          dataIndex: 'unit',
+          customRender: (text, record, index) => {
+            return this.BaseTool.Object.getField(this.unitMap, text)
+          }
+        },
+        {
+          title: '单价',
+          dataIndex: 'price',
+          customRender: (text, record, index) => {
+            return this.BaseTool.Amount.formatter(text)
+          }
+        },
+        {
+          title: '库存',
+          dataIndex: 'stock',
+          customRender: (text, record, index) => {
+            return this.BaseTool.Amount.formatter(text)
+          }
+        },
+        {
+          title: '删除标志',
+          dataIndex: 'delFlag'
+        },
+        {
+          title: '创建人名称',
+          dataIndex: 'createdUserName'
+        },
+        {
+          title: '创建时间',
+          dataIndex: 'createdTime'
+        },
+        {
+          title: '操作',
+          key: 'action',
+          width: '200px',
+          align: 'center',
+          scopedSlots: { customRender: 'action' }
+        }
+      ],
+      // 下拉框map
+      typeMap: {},
+      unitMap: {},
+      // 加载数据方法 必须为 Promise 对象
+      loadData: parameter => {
+        parameter = {
+          ...parameter,
+          ...this.queryParam,
+          ...this.extraQueryParam,
+          dataScope: {
+            sortBy: 'desc',
+            sortName: 'update_time'
+          }
+        }
+        return getSupplierGoodsListPage(Object.assign(parameter, this.queryParam))
+          .then(res => {
+            return res.data
+          })
+      },
+      selectedRowKeys: [],
+      selectedRows: [],
 
-                options: {
-                    alert: { show: true, clear: () => { this.selectedRowKeys = [] } },
-                    rowSelection: {
-                        selectedRowKeys: this.selectedRowKeys,
-                        onChange: this.onSelectChange
-                    }
+      options: {
+        alert: { show: true, clear: () => { this.selectedRowKeys = [] } },
+        rowSelection: {
+          selectedRowKeys: this.selectedRowKeys,
+          onChange: this.onSelectChange
+        }
+      },
+      optionAlertShow: false,
+      isCreated: false
+    }
+  },
+  created () {
+    // 下拉框map
+    this.typeMap = this.DictCache.getLabelByValueMapByType(this.DictCache.TYPE.SUPPLIER_GOODS_LIST_TYPE)
+    this.unitMap = this.DictCache.getLabelByValueMapByType(this.DictCache.TYPE.SUPPLIER_GOODS_LIST_UNIT)
+  },
+  methods: {
+    tableOption () {
+      if (!this.optionAlertShow) {
+        this.options = {
+          alert: { show: true, clear: () => { this.selectedRowKeys = [] } },
+          rowSelection: {
+            selectedRowKeys: this.selectedRowKeys,
+            onChange: this.onSelectChange,
+            type: this.type,
+            getCheckboxProps: record => ({
+              props: {
+                disabled: false,
+                name: record.id
+              }
+            })
+          },
+          customRow: (record) => {
+            return {
+              on: { // 事件
+                click: (event) => { // 点击行
+                  // 选择对象
+                  this.mySelect([record.id], [record])
                 },
-                optionAlertShow: false,
-                isCreated: false
-            }
-        },
-        created () {
-            // 下拉框map
-                            this.typeMap = this.DictCache.getLabelByValueMapByType(this.DictCache.TYPE.SUPPLIER_GOODS_LIST_TYPE)
-                            this.unitMap = this.DictCache.getLabelByValueMapByType(this.DictCache.TYPE.SUPPLIER_GOODS_LIST_UNIT)
-                    },
-        methods: {
-            tableOption () {
-                if (!this.optionAlertShow) {
-                    this.options = {
-                        alert: { show: true, clear: () => { this.selectedRowKeys = [] } },
-                        rowSelection: {
-                            selectedRowKeys: this.selectedRowKeys,
-                            onChange: this.onSelectChange,
-                            type: this.type,
-                            getCheckboxProps: record => ({
-                                props: {
-                                    disabled: false,
-                                    name: record.id
-                                }
-                            })
-                        },
-                        customRow: (record) => {
-                            return {
-                                on: { // 事件
-                                    click: (event) => { // 点击行
-                                        // 选择对象
-                                        this.mySelect([record.id], [record])
-                                    },
-                                    dblclick: (event) => {
-                                        this.mySelect([record.id], [record])
-                                        this.handleSelect()
-                                    }
-                                }
-                            }
-                        }
-                    }
-                    this.optionAlertShow = true
-                } else {
-                    this.options = {
-                        alert: false,
-                        rowSelection: null
-                    }
-                    this.optionAlertShow = false
-                }
-            },
-            handleView (record) {
-                fetchSupplierGoodsList({ id: record.id }).then(res => {
-                    const modal = this.$refs.detailModal
-                    modal.base(res.data)
-                })
-            },
-            handleOk () {
-                this.$refs.table.refresh()
-            },
-            onSelectChange (selectedRowKeys, selectedRows) {
-                this.selectedRowKeys = selectedRowKeys
-                this.selectedRows = selectedRows
-            },
-            resetSearchForm () {
-                this.queryParam = {
-                }
-                this.$refs.table.refresh(true)
-            },
-            base (record, queryParam = {}) {
-                this.visible = true
-                this.modalTitle = '选择信息'
-                this.extraQueryParam = queryParam
-                this.record = record
-                if (this.isCreated) {
-                    this.$refs.table.clearSelected()
-                    this.options.rowSelection.type = this.type
-                    this.handleOk()
-                } else {
-                    this.tableOption()
-                    this.isCreated = true
-                }
-            },
-            handleCancel () {
-                this.visible = false
-                this.confirmLoading = false
-            },
-            handleSelect () {
-                if (this.selectedRowKeys.length === 0) {
-                    this.$message.warn('请至少选择一项信息')
-                } else {
-                    this.confirmLoading = true
-                    this.$emit('selected', this.record, this.selectedRowKeys, this.selectedRows)
-                    this.confirmLoading = false
-                    this.visible = false
+                dblclick: (event) => {
+                  this.mySelect([record.id], [record])
+                  this.handleSelect()
                 }
-            },
-            mySelect(selectedRowKeys, selectedRows) {
-                if (this.type === 'radio') {
-                    this.$refs.table.updateSelect(selectedRowKeys, selectedRows)
-                            this.$refs.table.rowSelection.onChange(selectedRowKeys, selectedRows)
-                } else {
-                    let mySelectedRowKeys
-                    let mySelectedRows = this.selectedRows.filter(item => item.id !== selectedRowKeys[0])
-                    if (this.selectedRowKeys.includes(selectedRowKeys[0])) {
-                        mySelectedRowKeys = this.selectedRowKeys.filter(item => item !== selectedRowKeys[0])
-                    } else {
-                        mySelectedRowKeys = [...selectedRowKeys, ...this.selectedRowKeys]
-                        mySelectedRows = [...mySelectedRows, ...selectedRows]
-                    }
-                    this.$refs.table.updateSelect(mySelectedRowKeys, mySelectedRows)
-                            this.$refs.table.rowSelection.onChange(mySelectedRowKeys, mySelectedRows)
-                }
-
+              }
             }
+          }
+        }
+        this.optionAlertShow = true
+      } else {
+        this.options = {
+          alert: false,
+          rowSelection: null
+        }
+        this.optionAlertShow = false
+      }
+    },
+    handleView (record) {
+      fetchSupplierGoodsList({ id: record.id }).then(res => {
+        const modal = this.$refs.detailModal
+        modal.base(res.data)
+      })
+    },
+    handleOk () {
+      this.$refs.table.refresh()
+    },
+    onSelectChange (selectedRowKeys, selectedRows) {
+      this.selectedRowKeys = selectedRowKeys
+      this.selectedRows = selectedRows
+    },
+    resetSearchForm () {
+      this.queryParam = {
+      }
+      this.$refs.table.refresh(true)
+    },
+    base (record, queryParam = {}) {
+      this.visible = true
+      this.modalTitle = '选择信息'
+      this.extraQueryParam = queryParam
+      this.record = record
+      if (this.isCreated) {
+        this.$refs.table.clearSelected()
+        this.options.rowSelection.type = this.type
+        this.handleOk()
+      } else {
+        this.tableOption()
+        this.isCreated = true
+      }
+    },
+    handleCancel () {
+      this.visible = false
+      this.confirmLoading = false
+    },
+    handleSelect () {
+      if (this.selectedRowKeys.length === 0) {
+        this.$message.warn('请至少选择一项信息')
+      } else {
+        this.confirmLoading = true
+        this.$emit('selected', this.record, this.selectedRowKeys, this.selectedRows)
+        this.confirmLoading = false
+        this.visible = false
+      }
+    },
+    mySelect (selectedRowKeys, selectedRows) {
+      if (this.type === 'radio') {
+        this.$refs.table.updateSelect(selectedRowKeys, selectedRows)
+        this.$refs.table.rowSelection.onChange(selectedRowKeys, selectedRows)
+      } else {
+        let mySelectedRowKeys
+        let mySelectedRows = this.selectedRows.filter(item => item.id !== selectedRowKeys[0])
+        if (this.selectedRowKeys.includes(selectedRowKeys[0])) {
+          mySelectedRowKeys = this.selectedRowKeys.filter(item => item !== selectedRowKeys[0])
+        } else {
+          mySelectedRowKeys = [...selectedRowKeys, ...this.selectedRowKeys]
+          mySelectedRows = [...mySelectedRows, ...selectedRows]
         }
+        this.$refs.table.updateSelect(mySelectedRowKeys, mySelectedRows)
+        this.$refs.table.rowSelection.onChange(mySelectedRowKeys, mySelectedRows)
+      }
     }
+  }
+}
 </script>

+ 17 - 5
src/views/repair/application-form/RepairApplicationForm.vue

@@ -29,6 +29,18 @@
                 <a-input v-model="queryParam.content" placeholder="问题描述模糊查询"/>
               </a-form-item>
             </a-col>
+            <a-col :md="6" :sm="24">
+              <a-form-item label="状态">
+                <a-select v-model="queryParam.category" placeholder="请选择">
+                  <a-select-option
+                    v-for="(label,value) in categoryMap"
+                    :key="value"
+                    :label="label"
+                    :value="parseInt(value)">{{ label }}
+                  </a-select-option>
+                </a-select>
+              </a-form-item>
+            </a-col>
             <a-col :md="6" :sm="24">
               <a-form-item label="状态">
                 <a-select v-model="queryParam.status" placeholder="请选择">
@@ -213,7 +225,7 @@ export default {
           width: '100px',
           dataIndex: 'category',
           customRender: (text, record, index) => {
-            return this.BaseTool.Object.getField(this.planFlagMap, text)
+            return this.BaseTool.Object.getField(this.categoryMap, text)
           }
         },
         {
@@ -293,7 +305,7 @@ export default {
       levelMap: {},
       statusMap: {},
       needStopMap: {},
-      planFlagMap: {},
+      categoryMap: {},
       // 加载数据方法 必须为 Promise 对象
       loadData: parameter => {
         parameter = {
@@ -301,8 +313,8 @@ export default {
           ...this.queryParam,
           type: 1,
           dataScope: {
-            sortBy: 'desc, asc',
-            sortName: 'apply_time, status'
+            sortBy: 'asc, desc',
+            sortName: 'status, apply_time'
           }
         }
         return getRepairApplicationFormPage(Object.assign(parameter, this.queryParam))
@@ -329,7 +341,7 @@ export default {
     this.levelMap = this.DictCache.getLabelByValueMapByType(this.DictCache.TYPE.REPAIR_APPLICATION_FORM_LEVEL)
     this.statusMap = this.DictCache.getLabelByValueMapByType(this.DictCache.TYPE.REPAIR_APPLICATION_FORM_STATUS)
     this.needStopMap = this.DictCache.getLabelByValueMapByType(this.DictCache.TYPE.YES_NO)
-    this.planFlagMap = this.DictCache.getLabelByValueMapByType(this.DictCache.TYPE.REPAIR_APPLICATION_FORM_CATEGORY)
+    this.categoryMap = this.DictCache.getLabelByValueMapByType(this.DictCache.TYPE.REPAIR_APPLICATION_FORM_CATEGORY)
     // 获取浏览器的请求参数:报修单编号:no
     const no = this.$route.query.no
     if (no != null) {

+ 2 - 2
src/views/repair/application-form/RepairCheckForm.vue

@@ -278,8 +278,8 @@ export default {
           ...parameter,
           ...this.queryParam,
           dataScope: {
-            sortBy: 'desc, asc',
-            sortName: 'apply_time, status'
+            sortBy: 'asc, desc',
+            sortName: 'status, apply_time'
           }
         }
         return getRepairApplicationFormPage(Object.assign(parameter, this.queryParam))

+ 2 - 11
src/views/repair/application-form/RepairForm.vue

@@ -209,15 +209,6 @@ export default {
           width: '120px',
           dataIndex: 'repairUserName'
         },
-        /*{
-          title: '报修来源',
-          checked: true,
-          width: '100px',
-          dataIndex: 'source',
-          customRender: (text, record, index) => {
-            return this.BaseTool.Object.getField(this.sourceMap, text)
-          }
-        },*/
         {
           title: '工单类型',
           checked: true,
@@ -312,8 +303,8 @@ export default {
           ...this.queryParam,
           type: 1,
           dataScope: {
-            sortBy: 'desc, asc',
-            sortName: 'apply_time, status'
+            sortBy: 'asc, desc',
+            sortName: 'status, apply_time'
           }
         }
         return getRepairApplicationFormPage(Object.assign(parameter, this.queryParam))

+ 3 - 3
src/views/repair/application-form/modules/BaseForm.vue

@@ -46,7 +46,7 @@
           >
             <a-select @change="changePlanFlag" v-decorator="['category', {rules: [{required: true, message: '计划性维修不能为空'}]}]" placeholder="请选择">
               <a-select-option
-                v-for="(label,value) in planFlagMap"
+                v-for="(label,value) in categoryMap"
                 :key="value"
                 :label="label"
                 :value="parseInt(value)">{{ label }}
@@ -269,7 +269,7 @@ export default {
       needStop: null,
       needStopMap: {},
       category: 0,
-      planFlagMap: {},
+      categoryMap: {},
       statusMap: {},
       userInfo: this.$store.getters.userInfo,
       userList: [],
@@ -298,7 +298,7 @@ export default {
     this.statusMap = this.DictCache.getLabelByValueMapByType(this.DictCache.TYPE.REPAIR_APPLICATION_FORM_STATUS)
     this.questionMap = this.DictCache.getLabelByValueMapByType(this.DictCache.TYPE.REPAIR_QUESTION)
     this.needStopMap = this.DictCache.getLabelByValueMapByType(this.DictCache.TYPE.YES_NO)
-    this.planFlagMap = this.DictCache.getLabelByValueMapByType(this.DictCache.TYPE.REPAIR_APPLICATION_FORM_CATEGORY)
+    this.categoryMap = this.DictCache.getLabelByValueMapByType(this.DictCache.TYPE.REPAIR_APPLICATION_FORM_CATEGORY)
     this.getUsers()
   },
   methods: {

+ 6 - 6
src/views/repair/application-form/modules/Detail.vue

@@ -19,11 +19,11 @@
             <detail-list-item term="使用位置">{{ model.sbCph }}</detail-list-item>
             <!--<detail-list-item term="部件名称">{{ model.partName }}</detail-list-item>-->
             <detail-list-item term="工单类别">{{ BaseTool.Object.getField(planFlagMap,model.category) }}</detail-list-item>
-<!--            <detail-list-item term="是否停机">{{ BaseTool.Object.getField(needStopMap,model.needStop) }}</detail-list-item>-->
+            <!--            <detail-list-item term="是否停机">{{ BaseTool.Object.getField(needStopMap,model.needStop) }}</detail-list-item>-->
 
             <detail-list-item term="报修人">{{ model.actualUser }}</detail-list-item>
             <detail-list-item term="报修来源">{{ BaseTool.Object.getField(this.sourceMap, model.source) }}</detail-list-item>
-<!--            <detail-list-item term="紧急等级"><badge :text="BaseTool.Object.getField(levelMap,model.level)" :status="DictCache.COLOR.REPAIR_APPLICATION_FORM_LEVEL[model.applicationLevel]"/></detail-list-item>-->
+            <!--            <detail-list-item term="紧急等级"><badge :text="BaseTool.Object.getField(levelMap,model.level)" :status="DictCache.COLOR.REPAIR_APPLICATION_FORM_LEVEL[model.applicationLevel]"/></detail-list-item>-->
             <detail-list-item term="报修时间">{{ model.applyTime }}</detail-list-item>
             <detail-list-item term="报修状态"><badge :text="BaseTool.Object.getField(statusMap,model.status)" :status="DictCache.COLOR.REPAIR_APPLICATION_FORM_STATUS[model.status]"/></detail-list-item>
             <detail-list-item term="要求时间">{{ model.limitHours }}小时</detail-list-item>
@@ -46,10 +46,10 @@
           </detail-list>
           <a-divider orientation="left">维修详情</a-divider>
           <detail-list title="" :col="3">
-<!--            <detail-list-item term="故障类别">{{ model.repairErrorTypeName }}</detail-list-item>-->
+            <!--            <detail-list-item term="故障类别">{{ model.repairErrorTypeName }}</detail-list-item>-->
             <detail-list-item term="维修开始时间">{{ model.repairStartTime }}</detail-list-item>
             <detail-list-item term="维修结束时间">{{ model.repairEndTime }}</detail-list-item>
-            <detail-list-item term="维修耗时">{{ model.repairMinutes }}分钟</detail-list-item>
+            <detail-list-item term="维修耗时">{{ model.repairMinutes }}小时</detail-list-item>
             <detail-list-item term="维修人员">{{ model.repairUserName }}</detail-list-item>
           <!--<detail-list-item term="维修次数">{{ model.repairTimes }}</detail-list-item>-->
           </detail-list>
@@ -68,7 +68,7 @@
             </detail-list-item>
           </detail-list>
           <a-divider v-if="dispatchList != null" orientation="left">转派详情</a-divider>
-          <detail-list v-for="item in dispatchList" title="" :col="3">
+          <detail-list v-for="(item,index) in dispatchList" title="" :key="index" :col="3">
             <detail-list-item term="转派人">{{ item.username }}</detail-list-item>
             <detail-list-item term="转派时间">{{ item.time }}</detail-list-item>
             <detail-list-item term="转派备注">{{ item.remark }}</detail-list-item>
@@ -566,4 +566,4 @@ export default {
   margin: 5px;
   display: inline-block;
 }
-</style>
+</style>

+ 4 - 4
src/views/repair/application-form/modules/DetailCheck.vue

@@ -54,7 +54,7 @@
             <!--            <detail-list-item term="故障类别">{{ model.repairErrorTypeName }}</detail-list-item>-->
             <detail-list-item term="维修开始时间">{{ model.repairStartTime }}</detail-list-item>
             <detail-list-item term="维修结束时间">{{ model.repairEndTime }}</detail-list-item>
-            <detail-list-item term="维修耗时">{{ model.repairMinutes }}分钟</detail-list-item>
+            <detail-list-item term="维修耗时">{{ model.repairMinutes }}小时</detail-list-item>
             <detail-list-item term="维修人员">{{ model.repairUserName }}</detail-list-item>
             <!--<detail-list-item term="维修次数">{{ model.repairTimes }}</detail-list-item>-->
           </detail-list>
@@ -142,7 +142,7 @@
       </a-table>
       <title-divider title="维修报告" width="90px"></title-divider>
       <div class="table-operator" >
-        <a-button type="primary" v-if="$auth('repair-application-forms-finish') && ((dataReason === null) || (dataReason.length===0))" @click="handleAddReason">
+        <a-button type="primary" v-if="$auth('repair-repair-reasons-add') && ((dataReason === null) || (dataReason.length===0))" @click="handleAddReason">
           <a-icon type="plus"/>
           添加
         </a-button>
@@ -156,10 +156,10 @@
           <template>
             <a @click="handleViewReason(record)">查看</a>
             <operation-button
-              v-if="$auth('repair-application-forms-finish')"
+              v-if="$auth('repair-repair-reasons-edit')"
               @click="handleEditReason(record)" >修改</operation-button>
             <operation-button
-              v-if="$auth('repair-application-forms-finish')"
+              v-if="$auth('repair-repair-reasons-del')"
               :type="2"
               title="确认删除该记录?"
               @confirm="batchDeleteReason(record.id)" >删除</operation-button>

+ 15 - 17
src/views/repair/application-form/modules/DetailRepair.vue

@@ -6,18 +6,18 @@
           <span class="table-page-search-submitButtons" style="float: right">
             <a-button v-if="$auth('repair-application-forms-finish')" style="margin-left: 16px" type="default" @ok="handleOk" @click="handleViewBom()">备件BOM</a-button>
             <a-button v-if="$auth('repair-application-forms-finish')" style="margin-left: 16px" type="default" @ok="handleOk" @click="handleViewCheck()">维护项目</a-button>
-            <a-button v-if="$auth('repair-application-forms-assign') && (DictCache.VALUE.REPAIR_APPLICATION_FORM_STATUS.NOT_ALLOCATED === model.status || DictCache.VALUE.REPAIR_APPLICATION_FORM_STATUS.PROCESSING === model.status || DictCache.VALUE.REPAIR_APPLICATION_FORM_STATUS.REBACK === model.status)" style="margin-left: 16px" type="primary" @click="handleAssign">派工</a-button>
+            <a-button v-if="$auth('repair-application-forms-assign') && (DictCache.VALUE.REPAIR_APPLICATION_FORM_STATUS.NOT_ALLOCATED === model.status || DictCache.VALUE.REPAIR_APPLICATION_FORM_STATUS.PROCESSING === model.status || DictCache.VALUE.REPAIR_APPLICATION_FORM_STATUS.REBACK === model.status)" style="margin-left: 16px" type="default" @click="handleAssign">派工</a-button>
             <a-popconfirm v-if="$auth('repair-application-forms-deal') && (DictCache.VALUE.REPAIR_APPLICATION_FORM_STATUS.NOT_ALLOCATED === model.status || DictCache.VALUE.REPAIR_APPLICATION_FORM_STATUS.REBACK === model.status)" title="是否要接收?" @confirm="receive">
               <a-button style="margin-left: 8px">接收</a-button>
             </a-popconfirm>
-            <a-button v-if="$auth('repair-application-forms-out') && (DictCache.VALUE.REPAIR_APPLICATION_FORM_STATUS.PROCESSING >= model.status) && model.type != 2" style="margin-left: 8px" type="primary" @click="handleOut">委外</a-button>
-            <a-button v-if="$auth('repair-application-forms-dispatch') && DictCache.VALUE.REPAIR_APPLICATION_FORM_STATUS.REBACK === model.status" style="margin-left: 8px" type="primary" @click="handleDispatch">转派</a-button>
-            <a-button v-if="$auth('repair-application-forms-finish') && DictCache.VALUE.REPAIR_APPLICATION_FORM_STATUS.PROCESSING === model.status" style="margin-left: 8px" type="primary" @click="handleFinish()">完成</a-button>
-            <a-button v-if="$auth('repair-application-forms-edit')" style="margin-left: 8px" type="default" @click="handleFinish()">修改</a-button>
+            <a-button v-if="$auth('repair-application-forms-out') && (DictCache.VALUE.REPAIR_APPLICATION_FORM_STATUS.PROCESSING >= model.status) && model.type != 2" style="margin-left: 8px" type="default" @click="handleOut">委外</a-button>
+            <a-button v-if="$auth('repair-application-forms-dispatch') && DictCache.VALUE.REPAIR_APPLICATION_FORM_STATUS.REBACK === model.status" style="margin-left: 8px" type="default" @click="handleDispatch">转派</a-button>
+            <a-button v-if="$auth('repair-application-forms-finish') && DictCache.VALUE.REPAIR_APPLICATION_FORM_STATUS.PROCESSING === model.status" style="margin-left: 8px" type="default" @click="handleFinish()">完成</a-button>
+            <a-button v-if="$auth('repair-application-forms-edit')" style="margin-left: 8px" type="default" @click="handleEdit()">修改</a-button>
             <a-popconfirm v-if="DictCache.VALUE.REPAIR_APPLICATION_FORM_STATUS.WAIT_SUBMIT === model.status" title="是否要提交审核该条数据?" @confirm="handleExamine">
-              <a-button style="margin-left: 8px" type="primary">提交审核</a-button>
+              <a-button style="margin-left: 8px" type="default">提交审核</a-button>
             </a-popconfirm>
-            <a-button style="margin-left: 8px" @click="handleCancel">返回</a-button>
+            <a-button style="margin-left: 8px" type="primary" @click="handleCancel">返回</a-button>
           </span>
         </a-col>
       </a-row>
@@ -60,7 +60,7 @@
 <!--            <detail-list-item term="故障类别">{{ model.repairErrorTypeName }}</detail-list-item>-->
             <detail-list-item term="维修开始时间">{{ model.repairStartTime }}</detail-list-item>
             <detail-list-item term="维修结束时间">{{ model.repairEndTime }}</detail-list-item>
-            <detail-list-item term="维修耗时">{{ model.repairMinutes }}分钟</detail-list-item>
+            <detail-list-item term="维修耗时">{{ model.repairMinutes }}小时</detail-list-item>
             <detail-list-item term="维修人员">{{ model.repairUserName }}</detail-list-item>
           <!--<detail-list-item term="维修次数">{{ model.repairTimes }}</detail-list-item>-->
           </detail-list>
@@ -172,14 +172,11 @@
               <template>
                 <a @click="handleViewReason(record)">查看</a>
                 <operation-button
-                  v-if="$auth('repair-application-forms-finish') && ( DictCache.VALUE.REPAIR_APPLICATION_FORM_STATUS.PROCESSING === model.status || DictCache.VALUE.REPAIR_APPLICATION_FORM_STATUS.REBACK === model.status)"
                   @click="handleEditReason(record)" >修改</operation-button>
-                <operation-button
+<!--                <operation-button
                   v-if="$auth('repair-application-forms-finish') && ( DictCache.VALUE.REPAIR_APPLICATION_FORM_STATUS.PROCESSING === model.status || DictCache.VALUE.REPAIR_APPLICATION_FORM_STATUS.REBACK === model.status)"
-                  @click="handleCopyReason(record)" >复制</operation-button>
-
+                  @click="handleCopyReason(record)" >复制</operation-button>-->
                 <operation-button
-                  v-if="$auth('repair-application-forms-finish') && ( DictCache.VALUE.REPAIR_APPLICATION_FORM_STATUS.PROCESSING === model.status || DictCache.VALUE.REPAIR_APPLICATION_FORM_STATUS.REBACK === model.status)"
                   :type="2"
                   title="确认删除该记录?"
                   @confirm="batchDeleteReason(record.id)" >删除</operation-button>
@@ -220,6 +217,7 @@
     <detail-sb-check ref="detailSbCheckModal" @ok="handleOk"/>
     <base-form ref="baseRepairProjectModal" @ok="handleOk"/>
     <detail ref="detailRepairProjectModal"/>
+    <edit-form ref="editForm" @ok="handleOk" />
   </div>
 </template>
 
@@ -229,6 +227,7 @@ import { fetchRepairApplicationForm, examine, approve, receive } from '@/api/rep
 import CheckForm from './CheckForm'
 import BaseOutForm from './BaseOutForm'
 import FinishForm from './FinishForm'
+import EditForm from './EditForm'
 import DispatchForm from './DispatchForm'
 import AssignForm from './AssignForm'
 import SparePickBaseForm from '../../../store/sparepickform/modules/BaseForm'
@@ -258,6 +257,7 @@ export default {
   name: 'RepairApplicationFormDetail',
   components: {
     CheckForm,
+    EditForm,
     DetailList,
     DetailSbCheck,
     DetailSbBom,
@@ -701,10 +701,8 @@ export default {
       })
     },
     handleEdit (record) {
-      fetchRepairProject({ id: record.id }).then(res => {
-        const modal = this.$refs.baseRepairProjectModal
-        modal.base(res.data)
-      })
+      const modal = this.$refs.editForm
+      modal.base(this.model)
     },
     handleRepairProjectAdd () {
       this.$refs.baseRepairProjectModal.base({ repairId: this.model.id })

+ 1 - 1
src/views/repair/application-form/modules/EditForm.vue

@@ -122,7 +122,7 @@ export default {
         this.modalTitle = '添加'
         return
       }
-      this.modalTitle = '维修完成'
+      this.modalTitle = '修改工单'
       const { form: { setFieldsValue } } = this
       // 日期处理
       record.repairStartTime = this.BaseTool.Date.formatter(record.repairStartTime, this.BaseTool.Date.PICKER_NORM_DATETIME_PATTERN)

+ 89 - 2
src/views/repair/fee/RepairFee.vue

@@ -8,6 +8,54 @@
               <a-input v-model="queryParam.keyword" placeholder="请输入名称/类型名称"/>
             </a-form-item>
           </a-col>
+          <a-col :md="6" :sm="24">
+            <a-form-item label="设备新号">
+              <a-input v-model="queryParam.sbNo" placeholder="请输入设备新号"/>
+            </a-form-item>
+          </a-col>
+          <a-col :md="6" :sm="24">
+            <a-form-item label="设备名称">
+              <a-input v-model="queryParam.sbName" placeholder="请输入设备名称"/>
+            </a-form-item>
+          </a-col>
+          <a-col :md="6" :sm="24">
+            <a-form-item label="设备类型">
+              <a-tree-select
+                style="width: 100%"
+                :dropdownStyle="{ maxHeight: '400px', overflow: 'auto' }"
+                :treeData="treeData"
+                :treeNodeFilterProp="'title'"
+                :showSearch="true"
+                v-model="queryParam.typeId"
+                placeholder="请选择"
+              >
+              </a-tree-select>
+            </a-form-item>
+          </a-col>
+          <a-col :md="6" :sm="24">
+            <a-form-item label="设备等级">
+              <a-select v-model="queryParam.sbLevel" placeholder="请选择">
+                <a-select-option
+                  v-for="(label,value) in sbLevelMap"
+                  :key="value"
+                  :label="label"
+                  :value="parseInt(value)">{{ label }}
+                </a-select-option>
+              </a-select>
+            </a-form-item>
+          </a-col>
+          <a-col :md="6" :sm="24">
+            <a-form-item label="维修类别">
+              <a-select v-model="queryParam.category" placeholder="请选择">
+                <a-select-option
+                  v-for="(label,value) in categoryMap"
+                  :key="value"
+                  :label="label"
+                  :value="parseInt(value)">{{ label }}
+                </a-select-option>
+              </a-select>
+            </a-form-item>
+          </a-col>
           <a-col :md="8 || 24" :sm="24">
             <span class="table-page-search-submitButtons">
               <a-button type="primary" @click="$refs.table.refresh(true)">查询</a-button>
@@ -65,6 +113,7 @@ import { STable, Ellipsis } from '@/components'
 import BaseForm from './modules/BaseForm'
 import Detail from './modules/Detail'
 import { getRepairFeePage, deleteRepairFees, fetchRepairFee, exportRepairFee } from '@/api/repair/fee'
+import { fetchSbTypeTree } from '@/api/sb/type'
 
 export default {
   name: 'RepairFeeList',
@@ -80,6 +129,8 @@ export default {
       queryParam: {
       },
       moneyTypeMap: {},
+      categoryMap: {},
+      sbLevelMap: {},
       // 表头
       columns: [
         {
@@ -90,12 +141,43 @@ export default {
           }
         },
         {
-          title: '维修单id',
+          title: '设备编号',
+          width: '100px',
+          dataIndex: 'sbNo'
+        },
+        {
+          title: '设备名称',
+          width: '150px',
+          dataIndex: 'sbName'
+        },
+        {
+          title: '设备类型',
+          width: '150px',
+          dataIndex: 'sbTypeName'
+        },
+        {
+          title: '设备等级',
+          width: '150px',
+          dataIndex: 'sbLevel',
+          customRender: (text, record, index) => {
+            return this.BaseTool.Object.getField(this.sbLevelMap, text)
+          }
+        },
+        {
+          title: '维修单号',
           dataIndex: 'repairId',
           customRender: (text, record, index) => {
             return record.repairNo
           }
         },
+        {
+          title: '维修单类型',
+          width: '150px',
+          dataIndex: 'category',
+          customRender: (text, record, index) => {
+            return this.BaseTool.Object.getField(this.categoryMap, text)
+          }
+        },
         {
           title: '委外单号',
           dataIndex: 'no'
@@ -168,7 +250,7 @@ export default {
       },
       selectedRowKeys: [],
       selectedRows: [],
-
+      treeData: [],
       options: {
         alert: { show: true, clear: () => { this.selectedRowKeys = [] } },
         rowSelection: {
@@ -183,6 +265,11 @@ export default {
     // 下拉框map
     this.typeMap = this.DictCache.getLabelByValueMapByType(this.DictCache.TYPE.REPAIR_FEE_TYPE)
     this.moneyTypeMap = this.DictCache.getLabelByValueMapByType(this.DictCache.TYPE.MONEY_TYPE)
+    this.sbLevelMap = this.DictCache.getLabelByValueMapByType(this.DictCache.TYPE.SBINFO_LEVEL)
+    fetchSbTypeTree().then(res => {
+      this.treeData = res.data
+    })
+    this.categoryMap = this.DictCache.getLabelByValueMapByType(this.DictCache.TYPE.REPAIR_APPLICATION_FORM_CATEGORY)
     this.tableOption()
   },
   methods: {

+ 27 - 28
src/views/report/instorecount/InStoreCount.vue

@@ -5,7 +5,7 @@
         <a-row :gutter="48">
           <a-col :md="6" :sm="24">
             <a-form-item label="仓库">
-               <a-tree-select
+              <a-tree-select
                 style="width: 100%"
                 :dropdownStyle="{ maxHeight: '400px', overflow: 'auto' }"
                 :treeData="storeTreeData"
@@ -18,24 +18,24 @@
               </a-tree-select>
             </a-form-item>
           </a-col>
-           <a-col :md="6" :sm="24">
-              <a-form-item label="单据起始日期">
-                 <a-date-picker
-                  v-model="queryParam.searchStartTime"
-                  style="width: 100%"
-                  :format="BaseTool.Date.PICKER_NORM_DATE_PATTERN"
-                  v-decorator="['searchStartTime']"/>
-              </a-form-item>
-            </a-col>
-            <a-col :md="6" :sm="24">
-              <a-form-item label="单据结束日期">
-                   <a-date-picker
-                    v-model="queryParam.searchEndTime"
-                    style="width: 100%"
-                    :format="BaseTool.Date.PICKER_NORM_DATE_PATTERN"
-                    v-decorator="['searchEndTime']"/>
-              </a-form-item>
-            </a-col>
+          <a-col :md="6" :sm="24">
+            <a-form-item label="单据起始日期">
+              <a-date-picker
+                v-model="queryParam.searchStartTime"
+                style="width: 100%"
+                :format="BaseTool.Date.PICKER_NORM_DATE_PATTERN"
+                v-decorator="['searchStartTime']"/>
+            </a-form-item>
+          </a-col>
+          <a-col :md="6" :sm="24">
+            <a-form-item label="单据结束日期">
+              <a-date-picker
+                v-model="queryParam.searchEndTime"
+                style="width: 100%"
+                :format="BaseTool.Date.PICKER_NORM_DATE_PATTERN"
+                v-decorator="['searchEndTime']"/>
+            </a-form-item>
+          </a-col>
           <a-col :md="4 || 24" :sm="24">
             <span class="table-page-search-submitButtons">
               <a-button type="primary" @click="handleOk">查询</a-button>
@@ -71,7 +71,7 @@
 import { STable, Ellipsis } from '@/components'
 import BaseForm from './modules/BaseForm'
 import Detail from './modules/Detail'
-import {fetchStoreTree} from '@/api/store/store'
+import { fetchStoreTree } from '@/api/store/store'
 import { getInStoreDetailPage, deleteInStoreDetails, fetchInStoreDetail, exportInStoreDetail } from '@/api/report/instoredetail'
 
 export default {
@@ -84,12 +84,12 @@ export default {
   },
   data () {
     return {
-     storeTreeData:[],
+      storeTreeData: [],
       // 查询参数
       queryParam: {
-        storeId:null,
-        searchStartTime:null,
-        searchEndTime:null
+        storeId: null,
+        searchStartTime: null,
+        searchEndTime: null
       },
       // 表头
       columns: [
@@ -140,7 +140,6 @@ export default {
           ...this.queryParam,
           searchStartTime: this.queryParam.searchStartTime ? this.queryParam.searchStartTime.format(this.BaseTool.Date.PICKER_NORM_DATETIME_PATTERN) : null,
           searchEndTime: this.queryParam.searchEndTime ? this.queryParam.searchEndTime.format(this.BaseTool.Date.PICKER_NORM_DATETIME_PATTERN) : null,
-
           dataScope: {
           }
         }
@@ -165,11 +164,11 @@ export default {
   created () {
     // 下拉框map
     this.tableOption()
-      // 设置仓库选项
-        this.setTree()
+    // 设置仓库选项
+    this.setTree()
   },
   methods: {
-   setTree () {
+    setTree () {
       fetchStoreTree().then(res => {
         this.storeTreeData = res.data
       })

+ 1 - 1
src/views/report/instoredetail/InStoreDetail.vue

@@ -269,7 +269,7 @@ export default {
     },
     doExport () {
       const parameter = {
-        ...this.queryParam
+        ...this.queryParam,
       }
       exportInStoreDetail(parameter).then(file => {
         this.BaseTool.UPLOAD.downLoadExportExcel(file)

+ 71 - 10
src/views/sb/info/SbInfo.vue

@@ -18,12 +18,68 @@
               <a-row :gutter="48">
                 <a-col :md="6" :sm="24">
                   <a-form-item label="关键字">
-                    <a-input v-model="queryParam.keyword" placeholder="请输入名称/设备新号"/>
+                    <a-input v-model="queryParam.keyword" placeholder="名称/设备新号"/>
                   </a-form-item>
                 </a-col>
                 <a-col :md="6" :sm="24">
                   <a-form-item label="设备旧号">
-                    <a-input v-model="queryParam.zbh" placeholder="请输入设备旧号"/>
+                    <a-input v-model="queryParam.zbh" placeholder="设备旧号"/>
+                  </a-form-item>
+                </a-col>
+                <a-col :md="6" :sm="24">
+                  <a-form-item label="第一维修人">
+                    <a-input v-model="queryParam.repairUserName" placeholder="第一维修人"/>
+                  </a-form-item>
+                </a-col>
+                <a-col :md="6" :sm="24">
+                  <a-form-item label="第二维修人">
+                    <a-input v-model="queryParam.repairUserSecondName" placeholder="第二维修人"/>
+                  </a-form-item>
+                </a-col>
+                <a-col :md="6" :sm="24">
+                  <a-form-item label="设备等级">
+                    <a-select v-model="queryParam.level" placeholder="请选择">
+                      <a-select-option
+                        v-for="(label,value) in levelMap"
+                        :key="value"
+                        :label="label"
+                        :value="parseInt(value)">{{ label }}
+                      </a-select-option>
+                    </a-select>
+                  </a-form-item>
+                </a-col>
+                <a-col :md="6" :sm="24">
+                  <a-form-item label="自定义类型">
+                    <a-select v-model="queryParam.useType" placeholder="请选择">
+                      <a-select-option
+                        v-for="(label,value) in useTypeMap"
+                        :key="value"
+                        :label="label"
+                        :value="parseInt(value)">{{ label }}
+                      </a-select-option>
+                    </a-select>
+                  </a-form-item>
+                </a-col>
+                <a-col :md="6" :sm="24">
+                  <a-form-item label="规格型号">
+                    <a-input v-model="queryParam.model" placeholder="规格型号"/>
+                  </a-form-item>
+                </a-col>
+                <a-col :md="6" :sm="24">
+                  <a-form-item label="所属车间">
+                    <a-select v-model="queryParam.positionId" placeholder="请选择">
+                      <a-select-option
+                        v-for="({id,name}) in sbPositionData"
+                        :key="id"
+                        :label="name"
+                        :value="id">{{ name }}
+                      </a-select-option>
+                    </a-select>
+                  </a-form-item>
+                </a-col>
+                <a-col :md="6" :sm="24">
+                  <a-form-item label="生产商">
+                    <a-input v-model="queryParam.producerName" placeholder="生产商名称"/>
                   </a-form-item>
                 </a-col>
                 <a-col :md="6" :sm="24">
@@ -46,6 +102,7 @@
                       <a-select-option
                         v-for="(label,value) in statusMap"
                         :key="value"
+                        :defaultValue="DictCache.VALUE.SB_INFO_STATUS.IN_USE"
                         :label="label"
                         :value="parseInt(value)">{{ label }}
                       </a-select-option>
@@ -176,7 +233,7 @@ import BaseFormStatusLog from '@/views/sb/status-log/modules/BaseForm'
 import Detail from './modules/Detail'
 import DownloadModal from '@/views/download/DownloadModal'
 import PreviewModal from '@/views/preview/PreviewModal'
-import { updateSbInfoStatus, getSbInfoPage, deleteSbInfos, fetchSbInfo, fetchSbInfos, exportSbInfo } from '@/api/sb/info'
+import { getSbInfoPage, deleteSbInfos, fetchSbInfo, fetchSbInfos, exportSbInfo } from '@/api/sb/info'
 import { queryDept } from '@/api/upms/dept'
 import { generateSbCodeAll } from '@/api/upms/code'
 import { fetchSbTypeTree } from '@/api/sb/type'
@@ -184,6 +241,7 @@ import ImportFormAdd from './modules/ImportFormAdd'
 import ImportFormUpdate from './modules/ImportFormUpdate'
 import PrintSbCode from '@/views/sb/info/modules/PrintSbCode'
 import PrintInSbInfoBatch from '@/views/sb/info/modules/PrintInSbInfoBatch'
+import { querySbPosition } from '@/api/sb/position'
 
 export default {
   name: 'SbInfoList',
@@ -219,6 +277,7 @@ export default {
       },
       depreciationTypeMap: {},
       visible: true,
+      sbPositionData: [],
       levelMap: {},
       unitMap: {},
       areaList: {},
@@ -309,13 +368,13 @@ export default {
           dataIndex: 'repairUserNameSecond'
         },
         {
-          title: '使用位置',
+          title: '所属车间',
           checked: true,
           width: 200,
-          dataIndex: 'cph'
+          dataIndex: 'positionName'
         },
         {
-          title: '使用部门',
+          title: '使用机台',
           checked: true,
           width: 200,
           dataIndex: 'saveUserName'
@@ -326,7 +385,6 @@ export default {
           width: 120,
           checked: true
         },
-
         {
           title: '大小尺寸',
           dataIndex: 'zz',
@@ -388,7 +446,7 @@ export default {
           width: 120,
           checked: true
         },
-        {
+        /* {
           title: '检定日期',
           dataIndex: 'checkDate',
           width: 150,
@@ -425,7 +483,7 @@ export default {
               return this.BaseTool.Date.getCountBetween(new Date(), record.nextCheckDate, 1) + '天'
             }
           }
-        },
+        }, */
         {
           title: '状态',
           checked: true,
@@ -482,6 +540,9 @@ export default {
     this.useTypeMap = this.DictCache.getLabelByValueMapByType(this.DictCache.TYPE.SB_USE_TYPE)
     this.isChildMap = this.DictCache.getLabelByValueMapByType(this.DictCache.TYPE.SB_IS_CHILD)
     this.isShowMap = this.DictCache.getLabelByValueMapByType(this.DictCache.TYPE.SB_IS_SHOW)
+    querySbPosition().then(res => {
+      this.sbPositionData = res.data
+    })
   },
   methods: {
     tableOption () {
@@ -556,7 +617,7 @@ export default {
       let ids = []
       const length = this.selectedRows.length
       if (length === 0) {
-        this.$message.info('请选择要打印的记录')
+        this.$message.info('请选择要打印的设备')
         return
       }
       ids = this.selectedRows.map(item => item.id)

+ 6 - 4
src/views/sb/info/modules/BaseForm.vue

@@ -191,7 +191,7 @@
       </a-row>
 
       <a-row class="form-row" :gutter="BaseTool.Constant.row.gutter">
-        <a-col :lg="12" :md="24" :sm="24">
+<!--        <a-col :lg="12" :md="24" :sm="24">
           <a-form-item
             label="使用位置"
             :labelCol="BaseTool.Constant.labelCol"
@@ -200,7 +200,7 @@
             <a-input
               v-decorator="['cph']" />
           </a-form-item>
-        </a-col>
+        </a-col>-->
         <a-col :lg="12" :md="24" :sm="24">
           <a-form-item
             label="生产商"
@@ -528,7 +528,7 @@
         </a-button>
       </div>
       <a-row class="form-row" :gutter="BaseTool.Constant.row.gutter">
-        <a-col v-for="(item, index) in paramList" :lg="12" :md="24" :sm="24">
+        <a-col :key="index" v-for="(item, index) in paramList" :lg="12" :md="24" :sm="24">
           <a-form-item
             :label="item.name"
             :labelCol="BaseTool.Constant.labelCol"
@@ -1201,7 +1201,9 @@ export default {
         values.nextCheckDate = BaseTool.Date.formatter(values.nextCheckDate, BaseTool.Date.PICKER_NORM_DATE_PATTERN)
         values.guaranteeDate = BaseTool.Date.formatter(values.guaranteeDate, BaseTool.Date.PICKER_NORM_DATE_PATTERN)
         values.retirementDate = BaseTool.Date.formatter(values.retirementDate, BaseTool.Date.PICKER_NORM_DATE_PATTERN)
-
+        if (values.registerDate != null) {
+          values.registerDate = BaseTool.Date.formatter(values.registerDate, BaseTool.Date.PICKER_NORM_DATE_PATTERN)
+        }
         values.lastRepaireTime = this.BaseTool.Date.formatter(values.lastRepaireTime, this.BaseTool.Date.PICKER_NORM_DATE_PATTERN)
         values.lastBaoyangTime = this.BaseTool.Date.formatter(values.lastBaoyangTime, this.BaseTool.Date.PICKER_NORM_DATE_PATTERN)
         values.spDate = this.BaseTool.Date.formatter(values.spDate, this.BaseTool.Date.PICKER_NORM_DATE_PATTERN)

+ 21 - 3
src/views/sb/info/modules/Detail.vue

@@ -20,7 +20,9 @@
               <a-button style="margin-left: 8px" type="default" @click="handleViewCheckJob()">保养任务</a-button>
             </a-badge>
             <a-button v-show="model.useType==4" style="margin-left: 8px" type="default" @click="handleMeasure()">检定记录</a-button>
-            <a-button v-if="$auth('check-polling-jobs-tui-calendar-first')" style="margin-left: 8px" type="error" @click="handleTuiCalendar(1)">保养日历</a-button>
+            <a-button style="margin-left: 8px" type="error" @click="handleTuiCalendar(1)">保养日历</a-button>
+            <a-button style="margin-left: 8px" type="default" @click="handleRepairReportSbInfo()">工单分析</a-button>
+            <a-button style="margin-left: 8px" type="default" @click="handleRepairReportSbInfoFee()">费用分析</a-button>
             <a-button style="margin-left: 8px" type="primary" @click="handleCancel()">返回</a-button>
           </span>
         </a-col>
@@ -165,6 +167,8 @@
     <detail-sb-measure ref="detailSbMeasureModal" @ok="handleOk"/>
     <detail-sb-info ref="detailSbInfoModal" @ok="handleOk"/>
     <part-info-list ref="partInfoList" />
+    <repair-report-sb-info ref="repairReportSbInfo" :sb-id="model.id" @ok="handleOk"/>
+    <repair-report-sb-info-fee ref="repairReportSbInfoFee" :sb-id="model.id" @ok="handleOk"/>
     <!--    <check-job-table-wait-do :type="2" :check-type="2" ref="checkJobTableWaitDo" @ok="handleOk"/>-->
   </a-card>
 </template>
@@ -192,6 +196,8 @@ import DetailSbCheckJob from '@/views/check/checkjob/modules/DetailSbCheckJob'
 import DetailSbMeasure from '@/views/sb/measurelog/modules/DetailSbCheck'
 import DetailSbInfo from '@/views/sb/info/modules/DetailSbInfo'
 import RepairFeeTable from '@/views/repair/fee/modules/RepairFeeTable'
+import RepairReportSbInfo from '@/views/dashboard/RepairReportSbInfo'
+import RepairReportSbInfoFee from '@/views/dashboard/RepairReportSbInfoFee'
 import PartInfoList from '@/views/part/info/modules/PartInfoList'
 const DetailListItem = DetailList.Item
 
@@ -214,7 +220,9 @@ export default {
     DetailSbInfo,
     RepairFeeTable,
     SbStatusLogTable,
-    SbStopLogTable
+    SbStopLogTable,
+    RepairReportSbInfo,
+    RepairReportSbInfoFee
   },
   data () {
     return {
@@ -374,6 +382,16 @@ export default {
       const modal = this.$refs.detailSbMeasureModal
       modal.base(this.model)
     },
+    handleRepairReportSbInfo  () {
+      this.visible = false
+      const modal = this.$refs.repairReportSbInfo
+      modal.base()
+    },
+    handleRepairReportSbInfoFee  () {
+      this.visible = false
+      const modal = this.$refs.repairReportSbInfoFee
+      modal.base()
+    },
     base (record) {
       this.visible = true
       this.visibleDetail = true
@@ -454,7 +472,7 @@ export default {
     },
     handleTuiCalendar (level) {
       const that = this
-      queryTuiCalendarIgnores({ sbId: this.model.id, type: 2, standardLevel: level }).then(res => {
+      queryTuiCalendarIgnores({ sbId: this.model.id, type: 2 }).then(res => {
         const a = document.createElement('a')
         a.target = '_blank'
         a.href = '/tui-calendar/checkJobCalendar.html?'

+ 1 - 1
src/views/sb/info/modules/PrintInSbInfoBatch.vue

@@ -84,7 +84,7 @@ import { formatDate } from '@/utils/util'
 import { configData, updateSysConfigBatch } from '@/api/upms/config'
 
 export default {
-  name: 'PrintInStoreForm',
+  name: 'PrintInSbInfoBatch',
   components: { },
   data () {
     return {

+ 59 - 14
src/views/sb/measure/MeasureSbInfo.vue

@@ -8,30 +8,35 @@
               <a-row :gutter="48">
                 <a-col :md="8" :sm="24">
                   <a-form-item label="关键字">
-                    <a-input v-model="queryParam.keyword" placeholder="请输入名称"/>
+                    <a-input v-model.trim="queryParam.keyword" placeholder="请输入设备名称"/>
                   </a-form-item>
                 </a-col>
                 <a-col :md="8" :sm="24">
                   <a-form-item label="设备新号">
-                    <a-input v-model="queryParam.no"/>
+                    <a-input v-model.trim="queryParam.no"/>
+                  </a-form-item>
+                </a-col>
+                <a-col :md="8" :sm="24">
+                  <a-form-item label="设备型号">
+                    <a-input v-model.trim="queryParam.model"/>
                   </a-form-item>
                 </a-col>
                 <a-col :md="8" :sm="24">
                   <a-form-item label="测量设备编号">
-                    <a-input v-model="queryParam.cardNo" />
+                    <a-input v-model.trim="queryParam.cardNo" />
                   </a-form-item>
                 </a-col>
                 <a-col :md="8" :sm="24">
                   <a-form-item label="使用部门">
-                    <a-input v-model="queryParam.useDept" />
+                    <a-input v-model.trim="queryParam.useDept" />
                   </a-form-item>
                 </a-col>
                 <a-col :md="8" :sm="24">
                   <a-form-item label="出厂编号">
-                    <a-input v-model="queryParam.zzh"/>
+                    <a-input v-model.trim="queryParam.zzh"/>
                   </a-form-item>
                 </a-col>
-                <a-col :md="6" :sm="24">
+                <a-col :md="8" :sm="24">
                   <a-form-item label="管理状态">
                     <a-select v-model="queryParam.status" placeholder="请选择">
                       <a-select-option
@@ -43,8 +48,13 @@
                     </a-select>
                   </a-form-item>
                 </a-col>
-                <a-col :md="10" :sm="24">
-                  <a-form-item label="有效日期">
+                <a-col :md="8" :sm="24">
+                  <a-form-item label="检定日期范围">
+                    <a-range-picker v-model="dateRangeCheck" :style="{width: '256px'}" />
+                  </a-form-item>
+                </a-col>
+                <a-col :md="8" :sm="24">
+                  <a-form-item label="有效日期范围">
                     <a-range-picker v-model="dateRange" :style="{width: '256px'}" />
                   </a-form-item>
                 </a-col>
@@ -80,6 +90,7 @@
             ref="table"
             size="default"
             rowKey="id"
+            @change="onTableChange"
             :widthSpace="true"
             :columns="columns"
             :data="loadData"
@@ -94,7 +105,7 @@
                   <a-dropdown>
                     <a-menu slot="overlay">
                       <a-menu-item key="0">
-                        <a @click="handleView(record)">查看</a>
+                        <a @click="handleMeasure(record)">查看</a>
                       </a-menu-item>
                       <a-menu-item key="1">
                         <a v-if="$auth('sb-infos-edit')" @click="handleEdit(record)">修改</a>
@@ -107,7 +118,7 @@
             </span>
             <span slot="status" slot-scope="text">
               <badge
-                :status="DictCache.COLOR.SB_INFO_STATUS[text]"
+                :status="DictCache.COLOR.SB_MEASURE_STATUS[text]"
                 :text="statusMap[text]" />
             </span>
           </s-table>
@@ -161,15 +172,23 @@ export default {
     seatNumber: {
       type: Number,
       default: null
+    },
+    statusList: {
+      type: Array,
+      default: () => {
+        return null
+      }
     }
   },
   data () {
     return {
       dateRange: [],
+      dateRangeCheck: [],
       deptUserList: [],
       // 查询参数
       queryParam: {
-        seatNumber: this.seatNumber
+        seatNumber: this.seatNumber,
+        statusList: this.statusList
       },
       depreciationTypeMap: {},
       visible: true,
@@ -194,12 +213,14 @@ export default {
           title: '测量设备编号',
           dataIndex: 'cardNo',
           width: 150,
+          sorter: (a, b) => a.cardNo - b.cardNo,
           checked: true
         },
         {
           title: '设备名称',
           checked: true,
           width: 200,
+          sorter: (a, b) => a.name - b.name,
           dataIndex: 'name'
         },
         {
@@ -385,8 +406,8 @@ export default {
           ...parameter,
           ...this.queryParam,
           dataScope: {
-            sortBy: 'asc',
-            sortName: 'no'
+            sortBy: 'asc,asc',
+            sortName: 'status,next_check_date'
           }
         }
         return getSbInfoPage(Object.assign(parameter, this.queryParam))
@@ -493,17 +514,29 @@ export default {
         this.queryParam.nextCheckDateStart = this.queryParam.nextCheckDateStart ? this.queryParam.nextCheckDateStart.format(this.BaseTool.Date.PICKER_NORM_DATE_PATTERN) : null
         this.queryParam.nextCheckDateEnd = this.queryParam.nextCheckDateEnd ? this.queryParam.nextCheckDateEnd.format(this.BaseTool.Date.PICKER_NORM_DATE_PATTERN) : null
       }
+      if (this.dateRangeCheck != null) {
+        this.queryParam.checkDateStart = this.dateRangeCheck[0]
+        this.queryParam.checkDateEnd = this.dateRangeCheck[1]
+        this.queryParam.checkDateStart = this.queryParam.checkDateStart ? this.queryParam.checkDateStart.format(this.BaseTool.Date.PICKER_NORM_DATE_PATTERN) : null
+        this.queryParam.checkDateEnd = this.queryParam.checkDateEnd ? this.queryParam.checkDateEnd.format(this.BaseTool.Date.PICKER_NORM_DATE_PATTERN) : null
+      }
       this.$refs.table.refresh()
     },
+    onTableChange (pagination, filters, sorter) {
+      console.log('onTableChange', pagination, filters, sorter)
+    },
     onSelectChange (selectedRowKeys, selectedRows) {
+      console.log('onSelectChange', selectedRowKeys, selectedRows)
       this.selectedRowKeys = selectedRowKeys
       this.selectedRows = selectedRows
     },
     resetSearchForm () {
       this.queryParam = {
-        seatNumber: this.seatNumber
+        seatNumber: this.seatNumber,
+        statusList: this.statusList
       }
       this.dateRange = []
+      this.dateRangeCheck = []
       this.visible = true
       this.$refs.table.refresh(true)
     },
@@ -514,6 +547,12 @@ export default {
         this.queryParam.nextCheckDateStart = this.queryParam.nextCheckDateStart ? this.queryParam.nextCheckDateStart.format(this.BaseTool.Date.PICKER_NORM_DATE_PATTERN) : null
         this.queryParam.nextCheckDateEnd = this.queryParam.nextCheckDateEnd ? this.queryParam.nextCheckDateEnd.format(this.BaseTool.Date.PICKER_NORM_DATE_PATTERN) : null
       }
+      if (this.dateRangeCheck != null) {
+        this.queryParam.checkDateStart = this.dateRangeCheck[0]
+        this.queryParam.checkDateEnd = this.dateRangeCheck[1]
+        this.queryParam.checkDateStart = this.queryParam.checkDateStart ? this.queryParam.checkDateStart.format(this.BaseTool.Date.PICKER_NORM_DATE_PATTERN) : null
+        this.queryParam.checkDateEnd = this.queryParam.checkDateEnd ? this.queryParam.checkDateEnd.format(this.BaseTool.Date.PICKER_NORM_DATE_PATTERN) : null
+      }
       const parameter = {
         ...this.queryParam
       }
@@ -528,6 +567,12 @@ export default {
         this.queryParam.nextCheckDateStart = this.queryParam.nextCheckDateStart ? this.queryParam.nextCheckDateStart.format(this.BaseTool.Date.PICKER_NORM_DATE_PATTERN) : null
         this.queryParam.nextCheckDateEnd = this.queryParam.nextCheckDateEnd ? this.queryParam.nextCheckDateEnd.format(this.BaseTool.Date.PICKER_NORM_DATE_PATTERN) : null
       }
+      if (this.dateRangeCheck != null) {
+        this.queryParam.checkDateStart = this.dateRangeCheck[0]
+        this.queryParam.checkDateEnd = this.dateRangeCheck[1]
+        this.queryParam.checkDateStart = this.queryParam.checkDateStart ? this.queryParam.checkDateStart.format(this.BaseTool.Date.PICKER_NORM_DATE_PATTERN) : null
+        this.queryParam.checkDateEnd = this.queryParam.checkDateEnd ? this.queryParam.checkDateEnd.format(this.BaseTool.Date.PICKER_NORM_DATE_PATTERN) : null
+      }
       const parameter = {
         ...this.queryParam
       }

+ 1 - 1
src/views/sb/measure/MeasureSbInfoWarn.vue

@@ -1,5 +1,5 @@
 <template>
-  <MeasureSbInfo :seat-number="30"/>
+  <MeasureSbInfo :seat-number="30" :status-list="[1,2]"/>
 </template>
 
 <script>

+ 14 - 2
src/views/sb/measure/modules/BaseForm.vue

@@ -56,7 +56,7 @@
             :wrapperCol="BaseTool.Constant.wrapperCol"
           >
             <a-input
-              v-decorator="['model', {rules: [{required: true, message: '设备型号不能为空'}]}]" />
+              v-decorator="['model', {rules: [{required: false, message: '设备型号不能为空'}]}]" />
           </a-form-item>
         </a-col>
 
@@ -281,12 +281,13 @@
 
         <a-col :lg="12" :md="24" :sm="24">
           <a-form-item
-            label="检定有效期"
+            label="检定有效期"
             :labelCol="BaseTool.Constant.labelCol"
             :wrapperCol="BaseTool.Constant.wrapperCol"
           >
             <a-date-picker
               style="width: 100%"
+              disabled
               :format="BaseTool.Date.PICKER_NORM_DATE_PATTERN"
               v-decorator="['nextCheckDate']" />
           </a-form-item>
@@ -311,6 +312,16 @@
               v-decorator="['remark']" />
           </a-form-item>
         </a-col>
+        <a-col :lg="12" :md="24" :sm="24">
+          <a-form-item
+            label="备注2"
+            :labelCol="BaseTool.Constant.labelCol"
+            :wrapperCol="BaseTool.Constant.wrapperCol"
+          >
+            <a-input
+              v-decorator="['remark2']" />
+          </a-form-item>
+        </a-col>
       </a-row>
     </a-form>
     <sb-model-select-modal ref="sbModelSelectModal" @selected="handleSbModelSelected"/>
@@ -526,6 +537,7 @@ export default {
           // 'sbImage',
           'status',
           'remark',
+          'remark2',
           'zzh',
           'zz',
           'zjm',

+ 1 - 0
src/views/sb/measure/modules/Detail.vue

@@ -168,6 +168,7 @@ export default {
         'qrCode': null,
         'status': null,
         'remark': null,
+        'remark2': null,
         'parentName': null,
         'createdUserName': null,
         'typeName': null,

+ 23 - 1
src/views/sb/measurelog/modules/BaseForm.vue

@@ -103,6 +103,27 @@
               v-decorator="['requirement', {rules: [{required: false, message: '备注不能为空'}]}]"/>
           </a-form-item>
         </row-item>
+        <row-item>
+          <a-form-item
+            label="准确度等级"
+            :labelCol="BaseTool.Constant.labelCol"
+            :wrapperCol="BaseTool.Constant.wrapperCol"
+          >
+            <a-input
+              disabled
+              v-decorator="['fdjxh']" />
+          </a-form-item>
+        </row-item>
+        <row-item>
+          <a-form-item
+            label="备注"
+            :labelCol="BaseTool.Constant.labelCol"
+            :wrapperCol="BaseTool.Constant.wrapperCol"
+          >
+            <a-input
+              v-decorator="['remark']" />
+          </a-form-item>
+        </row-item>
         <row-item>
           <a-form-item
             label="管理状态"
@@ -227,7 +248,7 @@ export default {
           const { form: { setFieldsValue } } = this
           // 日期处理
           this.$nextTick(() => {
-            setFieldsValue({ sbId: sbInfo.id, cardNo: sbInfo.cardNo, sbStatus: sbInfo.status, sbModel: sbInfo.model, sbName: sbInfo.name, checkPeriod: sbInfo.checkPeriod })
+            setFieldsValue({ sbId: sbInfo.id, fdjxh: sbInfo.fdjxh, cardNo: sbInfo.cardNo, sbStatus: sbInfo.status, sbModel: sbInfo.model, sbName: sbInfo.name, checkPeriod: sbInfo.checkPeriod })
           })
         }
         return
@@ -271,6 +292,7 @@ export default {
           'actionType',
           'enable',
           'requirement',
+          'fdjxh',
           'remark'
         ])))
       })

+ 4 - 1
src/views/sb/measurelog/modules/DetailSbCheck.vue

@@ -17,8 +17,11 @@
       <detail-list-item term="检定日期">{{ model.checkDate }}</detail-list-item>
       <detail-list-item term="检定周期">{{ model.checkPeriod }}个月</detail-list-item>
       <detail-list-item term="检定有效期">{{ model.nextCheckDate }}</detail-list-item>
+      <detail-list-item term="准确度等级">{{ model.fdjxh }}</detail-list-item>
       <detail-list-item term="预警天数">{{ model.seatNumber }}天</detail-list-item>
-      <detail-list-item term="管理状态">{{ BaseTool.Object.getField(statusMap,model.status) }}</detail-list-item>
+      <detail-list-item term="管理状态"> <badge
+        :status="DictCache.COLOR.SB_MEASURE_STATUS[model.status]"
+        :text="statusMap[model.status]" /></detail-list-item>
     </detail-list>
     <title-divider title="检定信息" width="90px"></title-divider>
     <div class="table-operator">

+ 75 - 7
src/views/sqarepartmanage/sparepartinfo/SparePartInfo.vue

@@ -78,10 +78,28 @@
                   </a-select>
                 </a-form-item>
               </a-col>
+              <a-col :md="6" :sm="24">
+                <a-form-item label="是否专用">
+                  <a-select v-model="queryParam.isSpecial" placeholder="请选择">
+                    <a-select-option
+                      v-for="(label,value) in specialMap"
+                      :key="value"
+                      :label="label"
+                      :value="parseInt(value)">{{ label }}
+                    </a-select-option>
+                  </a-select>
+                </a-form-item>
+              </a-col>
+              <a-col :md="6" :sm="24">
+                <a-form-item label="关联设备">
+                  <a-input v-model="queryParam.model" placeholder="新号/旧号/名称/规格"/>
+                </a-form-item>
+              </a-col>
               <a-col :md="6 || 24" :sm="24">
                 <span class="table-page-search-submitButtons">
                   <a-button type="primary" @click="$refs.table.refresh(true)">查询</a-button>
                   <a-button style="margin-left: 8px" @click="resetSearchForm">重置</a-button>
+                  <a-button style="margin-left: 8px" @click="searchTypeNull">空类型</a-button>
                 </span>
               </a-col>
             </a-row>
@@ -91,9 +109,11 @@
         <div class="table-operator">
           <a-button v-if="$auth('sqarepartmanage-spare-part-info-add')" type="primary" icon="plus" @click="handleAdd">新增</a-button>
           <a-button style="margin-left: 8px" v-if="$auth('sqarepartmanage-spare-part-info-export')" type="primary" icon="download" @click="doExport">导出</a-button>
-          <a-button style="margin-left: 8px" v-if="$auth('sb-infos-export')" type="primary" icon="upload" @click="doImport">初始化新增导入</a-button>
-          <a-button style="margin-left: 8px" v-if="$auth('sb-infos-export')" type="primary" icon="upload" @click="doImportForUpdate">修改导入</a-button>
-          <a-button style="margin-left: 8px" v-if="selectedRowKeys.length > 0 && $auth('sqarepartmanage-spare-part-info-del')" type="primary" icon="upload" @click="handleSpareSelect">批量矫正</a-button>
+          <a-button style="margin-left: 8px" v-if="$auth('sqarepartmanage-spare-part-info-export')" type="primary" icon="upload" @click="doImport">初始化新增导入</a-button>
+          <a-button style="margin-left: 8px" v-if="$auth('sqarepartmanage-spare-part-info-export')" type="primary" icon="upload" @click="doImportForUpdate">修改导入</a-button>
+          <!--          <a-button style="margin-left: 8px" v-if="selectedRowKeys.length > 0 && $auth('sqarepartmanage-spare-part-info-del')" type="primary" icon="upload" @click="handleSpareSelect">批量矫正</a-button>-->
+          <a-button style="margin-left: 8px" type="primary" icon="printer" @click="handlePrintBatch()">批量打印</a-button>
+          <a-button style="margin-left: 8px" v-if="$auth('sb-infos-generate-code-all')" :loading="confirmLoading" type="primary" @click="batchGenerate()">重新生成二维码</a-button>
           <a-dropdown v-action:edit v-if="selectedRowKeys.length > 0 && $auth('sqarepartmanage-spare-part-info-del')">
             <a-menu slot="overlay">
               <a-popconfirm title="是否要删除所选数据?" @confirm="batchDelete()">
@@ -148,6 +168,7 @@
     <spare-part-info-select-modal-for-adjust :type="'radio'" ref="spareSelectModal" @selected="handleSpareSelected"/>
     <import-form-add ref="importModal" @ok="handleOk"/>
     <import-form-update ref="importModalForUpdate" @ok="handleOk"/>
+    <print-in-spare-batch ref="printInSbInfoBatch" @ok="handleOk"/>
   </a-card>
 </template>
 
@@ -160,16 +181,28 @@ import StoreList from './modules/StoreList'
 import InStoreList from './modules/InStoreList'
 import OutStoreList from './modules/OutStoreList'
 import SparePartUsedSelectModal from '@/views/sqarepartmanage/sparepartused/modules/SparePartUsedSelectModal'
-import { getSparePartInfoPage, updateSpareIdsBatch, deleteSparePartInfos, fetchSparePartInfo, fetchStoreList, fetchInStoreList, fetchOutStoreList, exportSparePartInfo } from '@/api/sqarepartmanage/sparepartinfo'
+import {
+  getSparePartInfoPage,
+  updateSpareIdsBatch,
+  deleteSparePartInfos,
+  fetchSparePartInfo,
+  fetchStoreList,
+  fetchInStoreList,
+  fetchOutStoreList,
+  exportSparePartInfo,
+  fetchSparePartInfos
+} from '@/api/sqarepartmanage/sparepartinfo'
 import { fetchSpareTypeTree } from '@/api/sqarepartmanage/sparetype'
 import ImportFormAdd from './modules/ImportFormAdd'
 import ImportFormUpdate from './modules/ImportFormUpdate'
 import SparePartInfoSelectModalForAdjust from '@/views/sqarepartmanage/sparepartinfo/modules/SparePartInfoSelectModalForAdjust'
-
+import PrintInSpareBatch from '@/views/sqarepartmanage/sparepartinfo/modules/PrintInSpareBatch'
+import { generateSpareCodeAll } from '@/api/upms/code'
 export default {
   name: 'SparePartInfoList',
   components: {
     STable,
+    PrintInSpareBatch,
     Ellipsis,
     BaseForm,
     Detail,
@@ -187,6 +220,7 @@ export default {
       // 查询参数
       queryParam: {
       },
+      confirmLoading: false,
       // 表头
       columns: [
         /** {
@@ -206,6 +240,12 @@ export default {
             return record.typeName
           }
         },
+        {
+          title: '备件编码',
+          dataIndex: 'no',
+          checked: true,
+          width: '150px'
+        },
         {
           title: '备件名称',
           dataIndex: 'name',
@@ -227,7 +267,6 @@ export default {
             return this.BaseTool.Amount.formatter(text)
           }
         },
-
         {
           title: '计量单位',
           checked: true,
@@ -346,6 +385,7 @@ export default {
       unitMap: {},
       cdMap: {},
       ytMap: {},
+      specialMap: {},
       id: null,
       visible: true,
       spareTypeTreeData: [],
@@ -365,6 +405,7 @@ export default {
     this.unitMap = this.DictCache.getLabelByValueMapByType(this.DictCache.TYPE.SBINFO_UNIT)
     this.cdMap = this.DictCache.getLabelByValueMapByType(this.DictCache.TYPE.PRODUCER_AREA)
     this.ytMap = this.DictCache.getLabelByValueMapByType(this.DictCache.TYPE.SPARE_USE_TYPE)
+    this.specialMap = this.DictCache.getLabelByValueMapByType(this.DictCache.TYPE.YES_NO)
     this.tableOption()
     fetchSpareTypeTree({}).then(res => {
       this.spareTypeTreeData = res.data
@@ -496,7 +537,34 @@ export default {
         this.BaseTool.UPLOAD.downLoadExportExcel(file)
       })
     },
-
+    searchTypeNull () {
+      this.queryParam.searchType = true
+      this.$refs.table.refresh(true)
+    },
+    batchGenerate () {
+      this.confirmLoading = true
+      this.$message.info('正在生成请稍后')
+      generateSpareCodeAll().then(res => {
+        this.confirmLoading = false
+        this.$message.info('生成成功')
+        this.handleOk()
+        this.$refs.table.clearSelected()
+      })
+    },
+    handlePrintBatch () {
+      this.visible = false
+      let ids = []
+      const length = this.selectedRows.length
+      if (length === 0) {
+        this.$message.info('请选择要打印的备件')
+        return
+      }
+      ids = this.selectedRows.map(item => item.id)
+      fetchSparePartInfos(ids).then(res => {
+        const modal = this.$refs.printInSbInfoBatch
+        modal.base(res.data)
+      })
+    },
     doImport () {
       this.$refs.importModal.base()
     },

+ 25 - 25
src/views/sqarepartmanage/sparepartinfo/SparePartInfoSbModel.vue

@@ -1,17 +1,17 @@
 <template>
   <a-card :bordered="false">
-     <a-row :gutter="8">
-       <a-col :span="4">
-         <a-tree
-           @expand="onExpand"
-           :expandedKeys="expandedKeys"
-           :autoExpandParent="true"
-           @select="onSelect"
-           :selectedKeys="selectedKeys"
-           :treeData="spareTypeTreeData"
-         />
-       </a-col>
-       <a-col :span="20">
+    <a-row :gutter="8">
+      <a-col :span="4">
+        <a-tree
+          @expand="onExpand"
+          :expandedKeys="expandedKeys"
+          :autoExpandParent="true"
+          @select="onSelect"
+          :selectedKeys="selectedKeys"
+          :treeData="spareTypeTreeData"
+        />
+      </a-col>
+      <a-col :span="20">
         <div class="table-page-search-wrapper">
           <a-form layout="inline">
             <a-row :gutter="48">
@@ -22,7 +22,7 @@
               </a-col>
               <a-col :md="6" :sm="24">
                 <a-form-item label="等级">
-                  <a-select v-model="queryParam.level"  placeholder="请选择">
+                  <a-select v-model="queryParam.level" placeholder="请选择">
                     <a-select-option
                       v-for="(label,value) in levelMap"
                       :key="value"
@@ -80,7 +80,7 @@
           showPagination="auto"
         >
           <span slot="status" slot-scope="text, record">
-            <a @click="handleStore(record)">{{text||"无"}}</a>
+            <a @click="handleStore(record)">{{ text||"无" }}</a>
           </span>
           <span slot="action" slot-scope="record">
             <template>
@@ -116,7 +116,7 @@ import InStoreList from './modules/InStoreList'
 import OutStoreList from './modules/OutStoreList'
 import SparePartUsedSelectModal from '@/views/sqarepartmanage/sparepartused/modules/SparePartUsedSelectModal'
 import { fetchSpareTypeAndSbModelTree } from '@/api/sqarepartmanage/sparetype'
-import { addSbModelBomBatch, selectSpareInfoListByModelId, deleteSbModelBoms} from '@/api/sb/modelbom'
+import { addSbModelBomBatch, selectSpareInfoListByModelId, deleteSbModelBoms } from '@/api/sb/modelbom'
 
 export default {
   name: 'SparePartInfoList',
@@ -160,10 +160,10 @@ export default {
           title: '原厂编号',
           dataIndex: 'initNo'
         },
-       // {
-         // title: '规格型号',
-         // dataIndex: 'ggxh'
-        //},
+        // {
+        // title: '规格型号',
+        // dataIndex: 'ggxh'
+        // },
         {
           title: '等级',
           dataIndex: 'level',
@@ -178,11 +178,11 @@ export default {
             return this.BaseTool.Amount.formatter(text)
           }
         },
-       // {
-         // title: '当前库存',
-         // dataIndex: 'currentStock',
-          //scopedSlots: { customRender: 'status' }
-       // },
+        // {
+        // title: '当前库存',
+        // dataIndex: 'currentStock',
+        // scopedSlots: { customRender: 'status' }
+        // },
         {
           title: '最高库存',
           dataIndex: 'maxStock'
@@ -357,7 +357,7 @@ export default {
       })
     },
     handleSparePartUsed (record) {
-      this.$refs.sparePartUsedSelectModal.base({}, { spareId:record.id })
+      this.$refs.sparePartUsedSelectModal.base({}, { spareId: record.id })
     },
     handleOutStore (record) {
       fetchOutStoreList({ id: record.id }).then(res => {

+ 295 - 0
src/views/sqarepartmanage/sparepartinfo/SpareStoreTotal.vue

@@ -0,0 +1,295 @@
+<template>
+  <a-card :bordered="false">
+    <div class="table-page-search-wrapper" @keyup.enter="handleEnter">
+      <a-form layout="inline">
+        <a-row :gutter="48">
+          <a-col :md="6" :sm="24">
+            <a-form-item label="关键字">
+              <a-input v-model="queryParam.keyword" placeholder="请输入备件名称/备件编码"/>
+            </a-form-item>
+          </a-col>
+          <a-col :md="6" :sm="24">
+            <a-form-item label="备件类别">
+              <a-tree-select
+                style="width: 100%"
+                :dropdownStyle="{ maxHeight: '400px', overflow: 'auto' }"
+                :treeData="spareTypeTreeData"
+                :treeNodeFilterProp="'title'"
+                :showSearch="true"
+                v-model="queryParam.typeId"
+                placeholder="请选择"
+              >
+              </a-tree-select>
+            </a-form-item>
+          </a-col>
+          <a-col :md="6 || 24" :sm="24">
+            <span class="table-page-search-submitButtons">
+              <a-button type="primary" @click="$refs.table.refresh(true)">查询</a-button>
+              <a-button style="margin-left: 8px" @click="resetSearchForm">重置</a-button>
+            </span>
+          </a-col>
+        </a-row>
+      </a-form>
+    </div>
+
+    <div class="table-operator">
+      <!--<a-button v-if="$auth('store-spare-stores-add')" type="primary" icon="plus" @click="$refs.baseModal.base()">新增</a-button>-->
+      <a-button style="margin-left: 8px" v-if="$auth('store-spare-stores-export')" type="primary" icon="download" @click="doExport">导出</a-button>
+    </div>
+
+    <s-table
+      ref="table"
+      size="default"
+      rowKey="spareId"
+      :columns="columns"
+      :data="loadData"
+      :alert="options.alert"
+      :rowSelection="options.rowSelection"
+      showPagination="auto"
+    >
+      <span slot="action" slot-scope="record">
+        <template>
+          <a v-if="record.warnStatus != 1" @click="handleUpdateStatus(record, 1)">待处理</a>
+          <a-divider type="vertical" />
+          <a v-if="record.warnStatus != 2" @click="handleUpdateStatus(record, 2)">询价中</a>
+          <a-divider type="vertical" />
+          <a v-if="record.warnStatus != 3"@click="handleUpdateStatus(record, 3)">采购中</a>
+          <a-divider type="vertical" />
+          <a v-if="record.warnStatus != 0" @click="handleUpdateStatus(record, 0)">正常</a>
+        </template>
+      </span>
+      <span slot="status" slot-scope="text">
+              <badge
+                :status="DictCache.COLOR.SPARE_WARN_STATUS[text]"
+                :text="warnStatusMap[text]" />
+            </span>
+    </s-table>
+    <base-form ref="baseModal" @ok="handleOk"/>
+    <detail ref="detailModal"/>
+  </a-card>
+</template>
+
+<script>
+import { STable, Ellipsis } from '@/components'
+import BaseForm from './modules/BaseForm'
+import Detail from './modules/Detail'
+import { fetchSpareTypeTree } from '@/api/sqarepartmanage/sparetype'
+import { getSparePartInfoPage, updateSparePartInfoWarnStatus, exportSparePartInfo } from '@/api/sqarepartmanage/sparepartinfo'
+import { queryDept, getDeptsAllByParentId } from '@/api/upms/dept'
+
+export default {
+  name: 'SpareStoreTotal',
+  components: {
+    STable,
+    Ellipsis,
+    BaseForm,
+    Detail
+  },
+  props: {
+    filter: {
+      type: Number,
+      default: -1
+    },
+    warnStatusList: {
+      type: Array,
+      default: null
+    },
+    forecastStatusList: {
+      type: Array,
+      default: null
+    }
+  },
+  data () {
+    return {
+      companyList: {},
+      projectList: {},
+      warnStatusMap: {},
+      spareTypeTreeData: [],
+      // 查询参数
+      queryParam: {
+        filter: this.filter,
+        warnStatusList: this.warnStatusList,
+        forecastStatusList: this.forecastStatusList
+      },
+      // 表头
+      columns: [
+        {
+          title: '序号',
+          dataIndex: 'index',
+          checked: true,
+          customRender: (text, record, index) => {
+            return `${(this.$refs.table.localPagination.current - 1) * this.$refs.table.localPagination.pageSize + index + 1}`
+          }
+        },
+        {
+          title: '编号',
+          checked: true,
+          dataIndex: 'no'
+        },
+        {
+          title: '备件名称',
+          checked: true,
+          dataIndex: 'name'
+        },
+        {
+          title: '规格型号',
+          checked: true,
+          dataIndex: 'ggxh'
+        },
+        {
+          title: '计量单位',
+          checked: true,
+          dataIndex: 'unit'
+        },
+        {
+          title: '单价',
+          checked: true,
+          dataIndex: 'price'
+        },
+        {
+          title: '最低库存',
+          checked: true,
+          dataIndex: 'minStock'
+        },
+        {
+          title: '最高库存',
+          checked: true,
+          dataIndex: 'maxStock'
+        },
+        {
+          title: '实际库存',
+          checked: true,
+          dataIndex: 'totalStock',
+          customRender: (text, record, index) => {
+            if (text == null) {
+              return 0
+            } else {
+              return text
+            }
+          }
+        },
+        {
+          title: '状态',
+          checked: true,
+          dataIndex: 'warnStatus',
+          scopedSlots: { customRender: 'status' }
+        },
+        {
+          title: '操作',
+          checked: true,
+          key: 'action',
+          width: '200px',
+          align: 'center',
+          scopedSlots: { customRender: 'action' }
+        }
+      ],
+      // 下拉框map
+      delFlagMap: {},
+      // 加载数据方法 必须为 Promise 对象
+      loadData: parameter => {
+        parameter = {
+          ...parameter,
+          ...this.queryParam,
+          dataScope: {
+          }
+        }
+        return getSparePartInfoPage(Object.assign(parameter, this.queryParam))
+          .then(res => {
+            return res.data
+          })
+      },
+      selectedRowKeys: [],
+      selectedRows: [],
+
+      options: {
+        alert: { show: true, clear: () => { this.selectedRowKeys = [] } },
+        rowSelection: {
+          selectedRowKeys: this.selectedRowKeys,
+          onChange: this.onSelectChange
+        }
+      },
+      optionAlertShow: false
+    }
+  },
+  created () {
+    // 下拉框map
+    this.warnStatusMap = this.DictCache.getLabelByValueMapByType(this.DictCache.TYPE.SPARE_WARN_STATUS)
+    this.tableOption()
+    queryDept({ nature: this.DictCache.VALUE.SYS_DEPT_NATURE.FEN_GONG_SI }).then(res => {
+      this.companyList = res.data
+    })
+    fetchSpareTypeTree({}).then(res => {
+      this.spareTypeTreeData = res.data
+    })
+  },
+  methods: {
+    handleCompanyChange (value) {
+      getDeptsAllByParentId({ deptId: value, nature: this.DictCache.VALUE.SYS_DEPT_NATURE.XIANG_MU_BU }).then(res => {
+        this.projectList = res.data
+      })
+    },
+    tableOption () {
+      if (!this.optionAlertShow) {
+        this.options = {
+          alert: { show: true, clear: () => { this.selectedRowKeys = [] } },
+          rowSelection: {
+            selectedRowKeys: this.selectedRowKeys,
+            onChange: this.onSelectChange,
+            getCheckboxProps: record => ({
+              props: {
+                disabled: false,
+                name: record.id
+              }
+            })
+          }
+        }
+        this.optionAlertShow = true
+      } else {
+        this.options = {
+          alert: false,
+          rowSelection: null
+        }
+        this.optionAlertShow = false
+      }
+    },
+    handleUpdateStatus (record, warnStatus) {
+      const parameter = {}
+      parameter.id = record.id
+      parameter.warnStatus = warnStatus
+      parameter.type = 1
+      updateSparePartInfoWarnStatus(parameter)
+        .then(() => {
+          this.handleOk()
+        }).catch(() => {
+          this.confirmLoading = false
+        })
+    },
+    handleOk () {
+      this.$refs.table.refresh()
+    },
+    onSelectChange (selectedRowKeys, selectedRows) {
+      this.selectedRowKeys = selectedRowKeys
+      this.selectedRows = selectedRows
+    },
+    resetSearchForm () {
+      this.queryParam = {
+        filter: this.filter,
+        warnStatusList: this.warnStatusList,
+        forecastStatusList: this.forecastStatusList
+      }
+      this.$refs.table.refresh(true)
+    },
+    doExport () {
+      const parameter = {
+        ...this.queryParam
+      }
+      exportSparePartInfo(parameter).then(file => {
+        this.BaseTool.UPLOAD.downLoadExportExcel(file)
+      })
+    },
+    handleEnter () {
+      this.$refs.table.refresh(true)
+    }
+  }
+}
+</script>

+ 19 - 0
src/views/sqarepartmanage/sparepartinfo/SpareStoreTotalCheckStock.vue

@@ -0,0 +1,19 @@
+<template>
+  <SpareStoreTotal :forecast-status-list="[1,2,3]"/>
+</template>
+
+<script>
+import SpareStore from './SpareStoreTotal'
+import SpareStoreTotal from '@/views/sqarepartmanage/sparepartinfo/SpareStoreTotal'
+export default {
+  name: 'SpareStoreTotalMinStock',
+  components: {
+    SpareStoreTotal,
+    SpareStore
+  }
+}
+</script>
+
+<style scoped>
+
+</style>

+ 19 - 0
src/views/sqarepartmanage/sparepartinfo/SpareStoreTotalMinStock.vue

@@ -0,0 +1,19 @@
+<template>
+  <SpareStoreTotal :warn-status-list="[1,2,3]"/>
+</template>
+
+<script>
+import SpareStore from './SpareStoreTotal'
+import SpareStoreTotal from '@/views/sqarepartmanage/sparepartinfo/SpareStoreTotal'
+export default {
+  name: 'SpareStoreTotalMinStock',
+  components: {
+    SpareStoreTotal,
+    SpareStore
+  }
+}
+</script>
+
+<style scoped>
+
+</style>

+ 58 - 16
src/views/sqarepartmanage/sparepartinfo/modules/BaseForm.vue

@@ -338,21 +338,14 @@
         </row-item>
         <row-item>
           <a-form-item
-            label="备件图片"
+            label="图片"
             :labelCol="BaseTool.Constant.labelCol"
             :wrapperCol="BaseTool.Constant.wrapperCol"
           >
-            <a-upload
-              :action="uploadUrl"
-              :multiple="true"
-              list-type="picture"
-              :file-list="this.defaultApplicationFileList"
-              @change="handleApplicationFileChange"
-              accept="image/*"
-              :headers="headers"
-            >
-              <a-button> <a-icon type="upload" /> 上传图片 </a-button>
-            </a-upload>
+            <upload-spare-file
+              ref="imageUpload"
+              @catchImage="catchImage"
+            ></upload-spare-file>
           </a-form-item>
         </row-item>
         <row-item>
@@ -381,6 +374,22 @@
             </a-select>
           </a-form-item>
         </row-item>
+        <row-item>
+          <a-form-item
+            label="是否专用"
+            :labelCol="BaseTool.Constant.labelCol"
+            :wrapperCol="BaseTool.Constant.wrapperCol"
+          >
+            <a-select v-decorator="['isSpecial', {rules: [{required: true, message: '是否专用不能为空'}]}]" placeholder="请选择">
+              <a-select-option
+                v-for="(label,value) in specialMap"
+                :key="value"
+                :label="label"
+                :value="parseInt(value)">{{ label }}
+              </a-select-option>
+            </a-select>
+          </a-form-item>
+        </row-item>
         <row-item>
           <a-form-item
             label="备注"
@@ -452,6 +461,7 @@ import { fetchStoreTree } from '@/api/store/store'
 import { selectSbModelListBySpareId } from '@/api/sb/modelbom'
 import SbInfoSelectModal from '@/views/sb/info/modules/SbInfoSelectModal'
 import BaseFormSpare from '@/views/sb/modelbom/modules/BaseFormSpare'
+
 export default {
   name: 'BaseSparePartInfo',
   components: {
@@ -488,6 +498,7 @@ export default {
       unitMap: {},
       cdMap: {},
       ytMap: {},
+      specialMap: {},
       spareTypeData: [],
       spareTypeDataMiddle: [],
       spareTypeDataChild: [],
@@ -536,6 +547,7 @@ export default {
       ],
       data: [],
       sbId: null,
+      image: '',
       selectedRowKeys: [],
       selectedRows: [],
       options: {
@@ -549,6 +561,8 @@ export default {
   },
   created () {
     // 下拉框map
+    this.setTree()
+    this.specialMap = this.DictCache.getLabelByValueMapByType(this.DictCache.TYPE.YES_NO)
     this.levelMap = this.DictCache.getLabelByValueMapByType(this.DictCache.TYPE.SPARE_PART_INFO_LEVEL)
     this.unitMap = this.DictCache.getLabelByValueMapByType(this.DictCache.TYPE.SBINFO_UNIT)
     this.cdMap = this.DictCache.getLabelByValueMapByType(this.DictCache.TYPE.PRODUCER_AREA)
@@ -557,7 +571,6 @@ export default {
   },
   methods: {
     base (record, sbId) {
-      this.setTree(record)
       this.visible = true
       this.sbId = sbId
       console.log('sbId: ', sbId)
@@ -565,6 +578,7 @@ export default {
       if (this.BaseTool.Object.isBlank(record)) {
         this.modalTitle = '添加'
         this.isAdd = true
+        this.$refs.imageUpload.base(1, [])
         return
       }
       this.modalTitle = '编辑'
@@ -616,13 +630,29 @@ export default {
           'ggxh',
           'yt',
           'zjm',
+          'isSpecial',
           'zbh',
+          'agePeriod',
+          'usePeriod',
+          'purchasePeriod',
           'maxStock',
           'minStock',
           'initStock',
           'remark'
         ])))
       })
+      this.image = record.image
+      const fileList = []
+      if (record.image) {
+        fileList.push({
+          uid: '-1',
+          name: record.name,
+          status: 'done',
+          url: this.BaseTool.Constant.FILE_URL + record.image,
+          originUrl: record.image
+        })
+      }
+      this.$refs.imageUpload.base(1, fileList)
     },
     save () {
       const { form: { validateFieldsAndScroll, setFieldsValue } } = this
@@ -640,6 +670,7 @@ export default {
         }
         values.applicationFileList = this.applicationFileList
         values.detailList = this.data
+        values.image = this.image
         // 日期处理
         if (this.BaseTool.String.isBlank(values.id)) {
           addSparePartInfo(values)
@@ -700,9 +731,16 @@ export default {
     /**
      * 设置仓库、备件类别树
      */
-    setTree (record = {}) {
+    setTree () {
       fetchStoreTree().then(res => {
-        this.storeTreeDate = res.data
+        this.storeTreeDate = this.BaseTool.TREE.treeFilter(res.data, (item) => {
+          console.log(item.title + ',,' + item.level)
+          if (item.level === this.DictCache.VALUE.STORE_LEVEL.ZONGCANG) {
+            console.log(false)
+            item.selectable = false
+            item.disabled = true
+          }
+        })
       })
       fetchSpareTypeTree().then(res => {
         this.spareTypeData = res.data
@@ -717,7 +755,11 @@ export default {
         this.ggList = res.data
       })
     },
-
+    catchImage (fileList) {
+      if (fileList.length !== 0) {
+        this.image = fileList[0].url
+      }
+    },
     checkSpareNo () {
       const { form: { getFieldValue } } = this
       const typeId = getFieldValue('typeId')

+ 8 - 10
src/views/sqarepartmanage/sparepartinfo/modules/Detail.vue

@@ -38,21 +38,15 @@
       <detail-list-item term="助记码">{{ model.zjm }}</detail-list-item>
       <detail-list-item term="产地">{{ BaseTool.Object.getField(cdMap,model.cd) }}</detail-list-item>
       <detail-list-item term="用途">{{ BaseTool.Object.getField(ytMap,model.yt) }}</detail-list-item>
+      <detail-list-item term="用途">{{ BaseTool.Object.getField(specialMap,model.isSpecial) }}</detail-list-item>
       <detail-list-item term="参数">{{ model.params }}</detail-list-item>
       <detail-list-item term="备注">{{ model.remark }}</detail-list-item>
       <detail-list-item term="创建人">{{ model.createdUserName }}</detail-list-item>
       <detail-list-item term="更新人">{{ model.updateUserName }}</detail-list-item>
       <detail-list-item term="更新日期">{{ model.updateTime }}</detail-list-item>
-    </detail-list>
-    <title-divider title="图片信息" width="90px"></title-divider>
-    <detail-list title="" :col="1">
-      <detail-list-item term="" v-if="model.applicationFileList != null && model.applicationFileList.length > 0">
-        <viewer :images="model.applicationFileList" @inited="inited" ref="viewer" :index="1" >
-          <img v-for="item in model.applicationFileList" :src="item.url" :key="item.id" class="image">
-        </viewer>
-      </detail-list-item>
-      <detail-list-item term="" v-if="model.applicationFileList == null || model.applicationFileList.length === 0">
-        暂无
+      <detail-list-item term="图片"><img :src="BaseTool.Constant.FILE_URL + model.image" width="200px" height="200px"/></detail-list-item>
+      <detail-list-item>
+        <img-code :src="model.qrCode" :type="2" title="点击重新生成二维码" :code-id="model.id" :width="200"></img-code>
       </detail-list-item>
     </detail-list>
     <title-divider title="设备信息" width="100px"></title-divider>
@@ -93,6 +87,7 @@ export default {
       unitMap: {},
       cdMap: {},
       ytMap: {},
+      specialMap: {},
       model: {
         'no': null,
         'name': null,
@@ -115,6 +110,7 @@ export default {
         'qrCode': null,
         'applicationFileList': [],
         'minStock': null,
+        'image': null,
         'initStock': null,
         'params': null,
         'remark': null,
@@ -173,6 +169,7 @@ export default {
     this.unitMap = this.DictCache.getLabelByValueMapByType(this.DictCache.TYPE.SBINFO_UNIT)
     this.cdMap = this.DictCache.getLabelByValueMapByType(this.DictCache.TYPE.PRODUCER_AREA)
     this.ytMap = this.DictCache.getLabelByValueMapByType(this.DictCache.TYPE.SPARE_USE_TYPE)
+    this.specialMap = this.DictCache.getLabelByValueMapByType(this.DictCache.TYPE.YES_NO)
     this.periodTypeMap = this.DictCache.getLabelByValueMapByType(this.DictCache.TYPE.CHECK_PLAN_PERIOD_TYPE)
   },
   methods: {
@@ -208,6 +205,7 @@ export default {
 <style scoped>
 .image {
   width: calc(20% - 10px);
+  height: auto;
   cursor: pointer;
   margin: 5px;
   display: inline-block;

+ 322 - 0
src/views/sqarepartmanage/sparepartinfo/modules/PrintInSpareBatch.vue

@@ -0,0 +1,322 @@
+<template>
+  <div class="print-content" v-show="visible">
+    <a-row :gutter="48" slot="extra">
+      <a-col :md="48" :sm="48">
+        <span class="table-page-search-submitButtons" style="float: right">
+          <a-button type="dashed" @click="handleEdit()">保存参数</a-button>
+          <a-button type="primary" style="margin-left: 8px" v-print="'#print-container-batch'" :disabled="disabled">打印</a-button>
+          <a-button style="margin-left: 8px" @click="handleCancel()">返回列表</a-button>
+        </span>
+      </a-col>
+    </a-row>
+    <a-row>
+      <a-col :span="4">
+        标签纸宽度(黑色背景)
+      </a-col>
+      <a-col :span="12">
+        <a-slider v-model="labelWidth" :min="1" :max="1000" />
+      </a-col>
+      <a-col :span="2">
+        <a-input-number v-model="labelWidth" style="marginLeft: 8px" />
+      </a-col>
+    </a-row>
+    <a-row>
+      <a-col :span="4">
+        标签表格宽度
+      </a-col>
+      <a-col :span="12">
+        <a-slider v-model="labelContentWidth" :min="1" :max="1000" />
+      </a-col>
+      <a-col :span="2">
+        <a-input-number v-model="labelContentWidth" suffix="px" style="marginLeft: 8px" />
+      </a-col>
+    </a-row>
+    <a-row>
+      <a-col :span="4">
+        标签表格高度
+      </a-col>
+      <a-col :span="12">
+        <a-slider v-model="labelContentHeight" :min="1" :max="1000" />
+      </a-col>
+      <a-col :span="2">
+        <a-input-number v-model="labelContentHeight" suffix="px" style="marginLeft: 8px" />
+      </a-col>
+    </a-row>
+    <a-row>
+      <a-col :span="4">
+        二维码宽度
+      </a-col>
+      <a-col :span="12">
+        <a-slider v-model="imgWidth" :min="1" :max="1000" />
+      </a-col>
+      <a-col :span="2">
+        <a-input-number v-model="imgWidth" suffix="px" style="marginLeft: 8px" />
+      </a-col>
+    </a-row>
+    <div class="container" :style="labelWidthProgress" id="print-container-batch">
+      <table class="gridtable list" :style="labelContentWidthProgress" :id="'printDiv' + record.id" v-for="record in sbInfoList" :key="record.id">
+        <tbody>
+          <tr>
+            <td class="text-center">备件名称</td>
+            <td class="text-center">{{ record.name }}</td>
+            <td rowspan="4" style="padding: 0 !important;" class="text-center"><img :style="imageProgress" :src="record.qrCode"></img></td>
+          </tr>
+          <tr>
+            <td class="text-center">备件编号</td>
+            <td class="text-center">{{ record.no }}</td>
+          </tr>
+          <tr>
+            <td class="text-center">规格型号</td>
+            <td class="text-center">{{ record.ggxh }}</td>
+          </tr>
+          <tr>
+            <td class="text-center" width='17%'>备件类型</td>
+            <td class="text-center">{{ record.typeName }}</td>
+          </tr>
+        </tbody>
+      </table>
+    </div>
+  </div>
+</template>
+
+<script>
+import { formatDate } from '@/utils/util'
+import { configData, updateSysConfigBatch } from '@/api/upms/config'
+
+export default {
+  name: 'PrintSpareBatch',
+  components: { },
+  data () {
+    return {
+      visible: false,
+      disabled: true,
+      sbInfoList: [],
+      count: 0,
+      levelMap: {},
+      user: this.$store.getters.userInfo,
+      labelWidth: 200,
+      labelContentWidth: 100,
+      labelContentHeight: 100,
+      imgWidth: 50,
+      configMap: {}
+      // 下拉框map
+    }
+  },
+  computed: {
+    labelWidthProgress () {
+      const style = {}
+      style.width = this.labelWidth + 'px'
+      style.backgroundColor = 'black'
+      style.textAlign = 'center'
+      return style
+    },
+    labelContentWidthProgress () {
+      const style = {}
+      style.width = this.labelContentWidth + 'px'
+      style.height = this.labelContentHeight + 'px'
+      style.backgroundColor = 'white'
+      style.textAlign = 'center'
+      style.margin = '4px auto'
+      return style
+    },
+    imageProgress () {
+      const style = {}
+      style.width = this.imgWidth + 'px'
+      return style
+    }
+  },
+  props: {},
+  created () {
+    // 下拉框map
+    this.levelMap = this.DictCache.getLabelByValueMapByType(this.DictCache.TYPE.SPARE_PART_INFO_LEVEL)
+    configData().then(res => {
+      this.configMap = res.data['config:open:value']
+      this.labelWidth = parseInt(this.configMap[this.DictCache.TYPE.SPARE_QR_CODE_LABEL_WIDTH])
+      this.labelContentWidth = parseInt(this.configMap[this.DictCache.TYPE.SPARE_QR_CODE_LABEL_CONTENT_WIDTH])
+      this.labelContentHeight = parseInt(this.configMap[this.DictCache.TYPE.SPARE_QR_CODE_LABEL_CONTENT_HEIGHT])
+      this.imgWidth = parseInt(this.configMap[this.DictCache.TYPE.SPARE_QR_CODE_LABEL_IMG_WIDTH])
+    })
+  },
+  methods: {
+    base (sbInfoList) {
+      this.disabled = true
+      this.visible = true
+      this.sbInfoList = sbInfoList
+      this.disabled = false
+    },
+    formatDateEn (value) {
+      return formatDate(new Date(value), 'yyyy-MM-dd')
+    },
+    formatDateCh (value) {
+      return formatDate(new Date(value), 'yyyy年MM月dd日')
+    },
+    handleCancel (values) {
+      this.visible = false
+      this.$emit('ok', values)
+    },
+    print () {
+      this.count = this.count + 1
+    },
+    handleEdit () {
+      const parameter = []
+      parameter.push({ code: this.DictCache.TYPE.SPARE_QR_CODE_LABEL_WIDTH, content: this.labelWidth })
+      parameter.push({ code: this.DictCache.TYPE.SPARE_QR_CODE_LABEL_CONTENT_WIDTH, content: this.labelContentWidth })
+      parameter.push({ code: this.DictCache.TYPE.SPARE_QR_CODE_LABEL_CONTENT_HEIGHT, content: this.labelContentHeight })
+      parameter.push({ code: this.DictCache.TYPE.SPARE_QR_CODE_LABEL_IMG_WIDTH, content: this.imgWidth })
+      updateSysConfigBatch(parameter).then(res => {
+        this.$message.info('更新成功, 退出,重新登录后全局生效')
+      })
+    }
+
+  }
+}
+</script>
+<style media=print>
+/* 应用这个样式的在打印时隐藏 */
+.noPrint {
+  display: none;
+}
+
+/* 应用这个样式的,从那个标签结束开始另算一页,之后在遇到再起一页,以此类推 */
+.page {
+  page-break-after: always;
+}
+</style>
+<style>
+.print-content{
+  margin: 0 auto;
+  width: 1000px;
+  background-color: #fff;
+}
+
+.container {
+  width: 100%;
+  padding-right: 15px;
+  padding-left: 15px;
+  margin-right: auto;
+  margin-left: auto;
+}
+
+.col-xs-1, .col-sm-1, .col-md-1, .col-lg-1, .col-xs-2, .col-sm-2, .col-md-2, .col-lg-2, .col-xs-3, .col-sm-3, .col-md-3, .col-lg-3, .col-xs-4, .col-sm-4, .col-md-4, .col-lg-4, .col-xs-5, .col-sm-5, .col-md-5, .col-lg-5, .col-xs-6, .col-sm-6, .col-md-6, .col-lg-6, .col-xs-7, .col-sm-7, .col-md-7, .col-lg-7, .col-xs-8, .col-sm-8, .col-md-8, .col-lg-8, .col-xs-9, .col-sm-9, .col-md-9, .col-lg-9, .col-xs-10, .col-sm-10, .col-md-10, .col-lg-10, .col-xs-11, .col-sm-11, .col-md-11, .col-lg-11, .col-xs-12, .col-sm-12, .col-md-12, .col-lg-12 {
+  position: relative;
+  min-height: 1px;
+  padding-right: 15px;
+  padding-left: 15px;
+}
+
+.text-left {
+  text-align: left;
+}
+
+.text-right {
+  text-align: right;
+}
+
+.text-center {
+  text-align: center;
+}
+
+table.gridtable {
+  width: 100%;
+  font-family: verdana, arial, sans-serif;
+  font-size: 11px;
+  color: #333333;
+  border-width: 1px;
+  border-color: #666666;
+  border-collapse: collapse;
+  page-break-after: always;
+}
+
+table.gridtable th {
+  border-width: 1px;
+  padding: 8px 0px;
+  border-style: solid;
+  border-color: #666666;
+  background-color: #dedede;
+}
+
+table.gridtable td {
+  border-width: 1px;
+  padding: 0;
+  border-style: solid;
+  color: black;
+  font-weight: bold;
+  border-color: #666666;
+  background-color: #ffffff;
+}
+
+.row {
+  margin-right: -15px;
+  margin-left: -15px;
+}
+
+.container:before,
+.container:after,
+.row:before, .row:after {
+  display: table;
+  content: " ";
+}
+
+.container:after, .row:after {
+  clear: both;
+}
+
+.col-md-1, .col-md-2, .col-md-3, .col-md-4, .col-md-5, .col-md-6, .col-md-7, .col-md-8, .col-md-9, .col-md-10, .col-md-11, .col-md-12 {
+  float: left;
+}
+
+.col-md-12 {
+  width: 100%;
+}
+
+.col-md-11 {
+  width: 91.66666667%;
+}
+
+.col-md-10 {
+  width: 83.33333333%;
+}
+
+.col-md-9 {
+  width: 75%;
+}
+
+.col-md-8 {
+  width: 66.66666667%;
+}
+
+.col-md-7 {
+  width: 58.33333333%;
+}
+
+.col-md-6 {
+  width: 50%;
+}
+
+.col-md-5 {
+  width: 41.66666667%;
+}
+
+.col-md-4 {
+  width: 33.33333333%;
+}
+
+.col-md-3 {
+  width: 25%;
+}
+
+.col-md-2 {
+  width: 16.66666667%;
+}
+
+.col-md-1 {
+  width: 8.33333333%;
+}
+
+ .node-line{
+   position: absolute;
+   width: 60px;
+   height: 10px;
+   left:20%;
+ }
+</style>

+ 19 - 0
src/views/sqarepartmanage/sparepartinfo/modules/SparePartInfoSelectModal.vue

@@ -38,6 +38,23 @@
                     <a-input v-model="queryParam.initNo" placeholder="原厂编号"/>
                   </a-form-item>
                 </a-col>
+                <a-col :md="6 || 24" :sm="24">
+                  <a-form-item label="">
+                    <a-select v-model="queryParam.isSpecial" placeholder="请选择">
+                      <a-select-option
+                        v-for="(label,value) in specialMap"
+                        :key="value"
+                        :label="label"
+                        :value="parseInt(value)">{{ label }}
+                      </a-select-option>
+                    </a-select>
+                  </a-form-item>
+                </a-col>
+                <a-col :md="8" :sm="24">
+                  <a-form-item label="关联设备">
+                    <a-input v-model="queryParam.model" placeholder="新号/旧号/名称/规格"/>
+                  </a-form-item>
+                </a-col>
                 <a-col :md="6 || 24" :sm="24">
                   <span class="table-page-search-submitButtons">
                     <a-button type="primary" @click="$refs.table.refresh(true)">查询</a-button>
@@ -119,6 +136,7 @@ export default {
       confirmLoading: false,
       mdl: {},
       modalTitle: null,
+      specialMap: {},
       visible: false,
       record: null,
       spareTypeTreeData: [],
@@ -203,6 +221,7 @@ export default {
     // 下拉框map
     this.levelMap = this.DictCache.getLabelByValueMapByType(this.DictCache.TYPE.SPARE_PART_INFO_LEVEL)
     this.unitMap = this.DictCache.getLabelByValueMapByType(this.DictCache.TYPE.SBINFO_UNIT)
+    this.specialMap = this.DictCache.getLabelByValueMapByType(this.DictCache.TYPE.YES_NO)
   },
   methods: {
     tableOption () {

+ 9 - 9
src/views/store/instoredetail/InStoreDetail.vue

@@ -83,7 +83,7 @@ export default {
     return {
       // 查询参数
       queryParam: {
-        inId:this.inId
+        inId: this.inId
       },
       // 表头
       columns: [
@@ -94,10 +94,10 @@ export default {
             return `${(this.$refs.table.localPagination.current - 1) * this.$refs.table.localPagination.pageSize + index + 1}`
           }
         },
-        //{
+        // {
         //  title: '入库单号',
-         // dataIndex: 'inNo'
-        //},
+        // dataIndex: 'inNo'
+        // },
         {
           title: '入库仓库',
           dataIndex: 'storeId',
@@ -105,10 +105,10 @@ export default {
             return record.storeName
           }
         },
-        {
+        /* {
           title: '备件编号',
-          dataIndex: 'spareNo',
-        },
+          dataIndex: 'spareNo'
+        }, */
         {
           title: '备件名称',
           dataIndex: 'spareId',
@@ -142,10 +142,10 @@ export default {
             return this.BaseTool.Amount.formatter(text)
           }
         },
-        //{
+        // {
         //  title: '创建日期',
         //  dataIndex: 'createdTime'
-       // },
+        // },
         {
           title: '操作',
           key: 'action',

+ 32 - 18
src/views/store/instoreform/modules/BaseForm.vue

@@ -17,7 +17,26 @@
               v-decorator="['inNo', {rules: [{required: false, message: '入库单号不能为空'}]}]" />
           </a-form-item>
         </a-col>
-<!--        <a-col :lg="12" :md="24" :sm="24">
+        <a-col :lg="12" :md="24" :sm="24">
+          <a-form-item
+            label="仓库"
+            :labelCol="BaseTool.Constant.labelCol"
+            :wrapperCol="BaseTool.Constant.wrapperCol"
+          >
+            <a-tree-select
+              style="width: 100%"
+              @change="handleStoreChange"
+              :dropdownStyle="{ maxHeight: '400px', overflow: 'auto' }"
+              :treeData="storeTreeDate"
+              :treeNodeFilterProp="'title'"
+              :showSearch="true"
+              v-decorator="['storeId', {rules: [{required: false, message: '仓库不能为空'}]}]"
+              placeholder="请选择"
+            >
+            </a-tree-select>
+          </a-form-item>
+        </a-col>
+        <!--        <a-col :lg="12" :md="24" :sm="24">
           <a-form-item
             label="采购单号"
             :labelCol="BaseTool.Constant.labelCol"
@@ -58,7 +77,7 @@
               v-decorator="['userTime']" />
           </a-form-item>
         </a-col>
-<!--        <a-col :lg="12" :md="24" :sm="24">
+        <!--        <a-col :lg="12" :md="24" :sm="24">
           <a-form-item
             label="发运单号"
             :labelCol="BaseTool.Constant.labelCol"
@@ -71,19 +90,6 @@
             <a-button type="primary" style="width:30%" @click="handlePurchaseOrderSelect">查看明细</a-button>
           </a-form-item>
         </a-col>-->
-        <a-col :lg="12" :md="24" :sm="24">
-          <a-form-item
-            label="仓库"
-            :labelCol="BaseTool.Constant.labelCol"
-            :wrapperCol="BaseTool.Constant.wrapperCol"
-          >
-            <a-input
-              disabled
-              style="width:70%"
-              v-decorator="['storeName', {rules: [{required: true, message: '仓库不能为空'}]}]" />
-            <a-button type="primary" style="width:30%"  @click="handleStoreSelect">选择仓库</a-button>
-          </a-form-item>
-        </a-col>
         <a-col :lg="12" :md="24" :sm="24">
           <a-form-item
             label="入库类型"
@@ -181,8 +187,9 @@ import PurchaseOrderSelectModal from '@/views/purchase/purchase-order/modules/Pu
 import StoreSelectModal from '@/views/store/store/modules/StoreSelectModal'
 import SparePartInfoSelectModal from '@/views/sqarepartmanage/sparepartinfo/modules/SparePartInfoSelectModal'
 import SpareStoreSelectModal from '@/views/store/sparestore/modules/SpareStoreSelectModal'
-import {queryUsersByParentDeptNatureAll} from "@/api/upms/user";
-import BaseTool from "@/utils/tool";
+import { queryUsersByParentDeptNatureAll } from '@/api/upms/user'
+import BaseTool from '@/utils/tool'
+import { fetchStoreTree } from '@/api/store/store'
 
 export default {
   name: 'BaseInStoreForm',
@@ -203,6 +210,7 @@ export default {
       storeId: null,
       typeMap: {},
       userList: {},
+      storeTreeDate: [],
       rowSelection: {
         onChange: (selectedRowKeys, selectedRows) => {
           this.selectedRowKeys = selectedRowKeys
@@ -287,6 +295,9 @@ export default {
       queryUsersByParentDeptNatureAll(params).then(res => {
         this.userList = res.data
       })
+      fetchStoreTree().then(res => {
+        this.storeTreeDate = res.data
+      })
       // 如果是空标识添加
       if (this.BaseTool.Object.isBlank(record)) {
         this.modalTitle = '添加'
@@ -358,6 +369,9 @@ export default {
         this.$emit('ok')
       }
     },
+    handleStoreChange (value) {
+      this.storeId = value
+    },
     handleStoreSelect () {
       this.$refs.storeSelectModal.base({}, { filter: -1 })
     },
@@ -424,7 +438,7 @@ export default {
         this.$message.error('请先选择入库仓库')
         return
       }
-      this.$refs.spareStoreSelectModal.base({}, { storeId: this.storeId })
+      this.$refs.spareStoreSelectModal.base()
     },
     handleSpareStoreSelected (record, keys, rows) {
       const { data } = this

+ 4 - 2
src/views/store/outstoredetail/OutStoreDetail.vue

@@ -99,10 +99,10 @@ export default {
             return record.storeName
           }
         },
-        {
+/*        {
           title: '备件编号',
           dataIndex: 'spareNo'
-        },
+        },*/
         {
           title: '备件名称',
           dataIndex: 'spareId',
@@ -141,6 +141,8 @@ export default {
           ...parameter,
           ...this.queryParam,
           dataScope: {
+            sortBy: 'desc',
+            sortName: 'created_time'
           }
         }
         return getOutStoreDetailPage(Object.assign(parameter, this.queryParam))

+ 34 - 14
src/views/store/outstoreform/modules/BaseForm.vue

@@ -18,7 +18,7 @@
               v-decorator="['outNo', {rules: [{required: false, message: '出库单号不能为空'}]}]" />
           </a-form-item>
         </a-col>
-        <a-col :lg="12" :md="24" :sm="24">
+<!--        <a-col :lg="12" :md="24" :sm="24">
           <a-form-item
             label="领用/退货单号"
             :labelCol="BaseTool.Constant.labelCol"
@@ -37,20 +37,26 @@
             :labelCol="BaseTool.Constant.labelCol"
             :wrapperCol="BaseTool.Constant.wrapperCol"
           >
-            <a-input
-              disabled
-              style="width:70%"
-              v-decorator="['storeName', {rules: [{required: true, message: '仓库不能为空'}]}]" />
-            <a-button type="primary" style="width:30%" @click="handleStoreSelect">选择仓库</a-button>
+            <a-tree-select
+              style="width: 100%"
+              @change="handleStoreChange"
+              :dropdownStyle="{ maxHeight: '400px', overflow: 'auto' }"
+              :treeData="storeTreeDate"
+              :treeNodeFilterProp="'title'"
+              :showSearch="true"
+              v-decorator="['storeId', {rules: [{required: false, message: '仓库不能为空'}]}]"
+              placeholder="请选择"
+            >
+            </a-tree-select>
           </a-form-item>
-        </a-col>
+        </a-col>-->
         <a-col :lg="12" :md="24" :sm="24">
           <a-form-item
             label="出库类型"
             :labelCol="BaseTool.Constant.labelCol"
             :wrapperCol="BaseTool.Constant.wrapperCol"
           >
-            <a-select @change="typeChange" v-decorator="['type', {rules: [{required: true, message: '出库类型不能为空'}]}]" placeholder="请选择">
+            <a-select @change="typeChange" v-decorator="['type', {initValue: 1, rules: [{required: true, message: '出库类型不能为空'}]}]" placeholder="请选择">
               <a-select-option
                 v-for="(label,value) in typeMap"
                 :key="value"
@@ -60,7 +66,7 @@
             </a-select>
           </a-form-item>
         </a-col>
-        <a-col :lg="12" :md="24" :sm="24">
+<!--        <a-col :lg="12" :md="24" :sm="24">
           <a-form-item
             label="操作人"
             :labelCol="BaseTool.Constant.labelCol"
@@ -75,7 +81,7 @@
               </a-select-option>
             </a-select>
           </a-form-item>
-        </a-col>
+        </a-col>-->
         <a-col :lg="12" :md="24" :sm="24">
           <a-form-item
             label="操作时间"
@@ -85,7 +91,7 @@
             <a-date-picker
               style="width: 100%"
               :format="BaseTool.Date.PICKER_NORM_DATE_PATTERN"
-              v-decorator="['userTime']" />
+              v-decorator="['userTime', {rules: [{required: true, message: '操作时间不能为空'}]}]" />
           </a-form-item>
         </a-col>
         <a-col :lg="12" :md="24" :sm="24">
@@ -165,8 +171,9 @@ import DetailBaseForm from './DetailBaseForm'
 import StoreSelectModal from '@/views/store/store/modules/StoreSelectModal'
 import SpareStoreSelectModal from '@/views/store/sparestore/modules/SpareStoreSelectModal'
 import BaseFormForModify from '@/views/store/outstoredetail/modules/BaseFormForModify'
-import BaseTool from "@/utils/tool";
-import {queryUsersByParentDeptNatureAll} from "@/api/upms/user";
+import BaseTool from '@/utils/tool'
+import { queryUsersByParentDeptNatureAll } from '@/api/upms/user'
+import { fetchStoreTree } from '@/api/store/store'
 
 export default {
   name: 'BaseOutStoreForm',
@@ -237,6 +244,10 @@ export default {
             return this.BaseTool.Amount.formatter(text)
           }
         },
+        {
+          title: '所在仓库',
+          dataIndex: 'storeName'
+        },
         {
           title: '操作',
           key: 'action',
@@ -245,6 +256,7 @@ export default {
         }
       ],
       data: [],
+      storeTreeDate: [],
       userList: {},
       user: this.$store.getters.userInfo,
       selectedRowKeys: [],
@@ -276,6 +288,9 @@ export default {
       queryUsersByParentDeptNatureAll(params).then(res => {
         this.userList = res.data
       })
+      fetchStoreTree().then(res => {
+        this.storeTreeDate = res.data
+      })
       // 如果是空标识添加
       if (this.BaseTool.Object.isBlank(record)) {
         this.modalTitle = '添加'
@@ -418,7 +433,7 @@ export default {
       this.data = data.filter(item => id !== item.id)
     },
     handleSpareStoreSelect () {
-      this.$refs.spareStoreSelectModal.base({}, { storeId: this.storeId, num: 0 })
+      this.$refs.spareStoreSelectModal.base({}, { num: 0 })
     },
     handleSpareStoreSelected (record, keys, rows) {
       const { data } = this
@@ -434,10 +449,15 @@ export default {
           const selectData = rows[i]
           selectData.num = 1
           selectData.totalPrice = selectData.price
+          selectData.storeId = rows[i].storeId
+          selectData.storeName = rows[i].storeName
           data.push(selectData)
         }
       }
     },
+    handleStoreChange (value) {
+      this.storeId = value
+    },
     handleBaseFormForModifySelect (record) {
       this.$refs.baseFormForModify.base(record)
     },

+ 3 - 3
src/views/store/outstoreform/modules/Detail.vue

@@ -14,10 +14,10 @@
     <detail-list title="" :col="3">
       <detail-list-item term="出库单号">{{ model.outNo }}</detail-list-item>
       <detail-list-item term="出库类型">{{ BaseTool.Object.getField(typeMap,model.type) }}</detail-list-item>
-      <detail-list-item term="仓库">{{ model.storeName }}</detail-list-item>
+<!--      <detail-list-item term="仓库">{{ model.storeName }}</detail-list-item>-->
       <detail-list-item term="总价">{{ model.totalPrice }}</detail-list-item>
-      <detail-list-item term="领用/退货单id">{{ model.pickId }}</detail-list-item>
-      <detail-list-item term="领用/退货单号">{{ model.pickNo }}</detail-list-item>
+<!--      <detail-list-item term="领用/退货单id">{{ model.pickId }}</detail-list-item>
+      <detail-list-item term="领用/退货单号">{{ model.pickNo }}</detail-list-item>-->
       <detail-list-item term="状态"><badge :text="BaseTool.Object.getField(statusMap,model.status)" :status="statusMap[model.status]"/></detail-list-item>
       <detail-list-item term="创建人">{{ model.createdUserName }}</detail-list-item>
       <detail-list-item term="更新人">{{ model.updateUserName }}</detail-list-item>

+ 0 - 17
src/views/store/sparestore/CompanySpareStore.vue

@@ -1,17 +0,0 @@
-<template>
-  <SpareStore :filter="3"/>
-</template>
-
-<script>
-import SpareStore from './SpareStore'
-export default {
-  name: 'CompanySpareStore',
-  components: {
-    SpareStore
-  }
-}
-</script>
-
-<style scoped>
-
-</style>

+ 0 - 17
src/views/store/sparestore/CompanySpareStoreTotal.vue

@@ -1,17 +0,0 @@
-<template>
-  <SpareStoreTotal :filter="3"/>
-</template>
-
-<script>
-import SpareStoreTotal from './SpareStoreTotal'
-export default {
-  name: 'MySpareStoreTotal',
-  components: {
-    SpareStoreTotal
-  }
-}
-</script>
-
-<style scoped>
-
-</style>

+ 0 - 17
src/views/store/sparestore/ProjectSpareStore.vue

@@ -1,17 +0,0 @@
-<template>
-  <SpareStore :filter="2"/>
-</template>
-
-<script>
-import SpareStore from './SpareStore'
-export default {
-  name: 'ProjectSpareStore',
-  components: {
-    SpareStore
-  }
-}
-</script>
-
-<style scoped>
-
-</style>

+ 0 - 17
src/views/store/sparestore/ProjectSpareStoreTotal.vue

@@ -1,17 +0,0 @@
-<template>
-  <SpareStoreTotal :filter="2"/>
-</template>
-
-<script>
-import SpareStoreTotal from './SpareStoreTotal'
-export default {
-  name: 'MySpareStoreTotal',
-  components: {
-    SpareStoreTotal
-  }
-}
-</script>
-
-<style scoped>
-
-</style>

+ 12 - 8
src/views/store/sparestore/SpareStore.vue

@@ -30,6 +30,16 @@
                   <a-input v-model="queryParam.initNo" placeholder="请输入原厂编号"/>
                 </a-form-item>
               </a-col>
+              <a-col :md="8" :sm="24">
+                <a-form-item label="关联设备">
+                  <a-input v-model="queryParam.model" placeholder="新号/旧号/名称/规格"/>
+                </a-form-item>
+              </a-col>
+              <a-col :md="8" :sm="24">
+                <a-form-item label="最低数量">
+                  <a-input v-model="queryParam.num" placeholder="请输入数量"/>
+                </a-form-item>
+              </a-col>
               <a-col :md="8" :sm="24">
                 <a-form-item
                   label="仓库"
@@ -59,7 +69,7 @@
         </div>
 
         <div class="table-operator">
-          <a-button  type="primary" icon="plus" @click="$refs.baseModal.base()">新增</a-button>
+          <a-button type="primary" icon="plus" @click="$refs.baseModal.base()">新增</a-button>
           <a-button style="margin-left: 8px" type="primary" icon="download" @click="doExport">导出</a-button>
         </div>
 
@@ -76,7 +86,7 @@
           <span slot="action" slot-scope="record">
             <template>
               <a @click="handleView(record)">查看</a>
-<!--              <a-divider type="vertical" />
+              <!--              <a-divider type="vertical" />
               <a v-if="$auth('store-spare-stores-edit')" @click="handleEdit(record)">出入库详情</a>-->
             </template>
           </span>
@@ -213,12 +223,6 @@ export default {
     fetchSpareTypeTree({}).then(res => {
       this.spareTypeTreeData = res.data
     })
-    //queryDept({ nature: this.DictCache.VALUE.SYS_DEPT_NATURE.FEN_GONG_SI }).then(res => {
-    //  this.companyList = res.data
-    //})
-    //getDeptsAllByParentId({ deptId: record.useCompany, nature: this.DictCache.VALUE.SYS_DEPT_NATURE.XIANG_MU_BU }).then(res => {
-    //  this.projectList = res.data
-    //})
   },
   methods: {
     handleCompanyChange (value) {

+ 94 - 64
src/views/store/sparestore/SpareStoreTotal.vue

@@ -9,43 +9,19 @@
             </a-form-item>
           </a-col>
           <a-col :md="6" :sm="24">
-            <a-form-item label="所属公司">
-              <a-select @change="handleCompanyChange" v-model="queryParam.useCompany" placeholder="请选择">
-                <a-select-option
-                  v-for="({deptId, name}) in companyList"
-                  :key="deptId"
-                  :label="name"
-                  :value="deptId">{{ name }}
-                </a-select-option>
-              </a-select>
+            <a-form-item label="备件类别">
+              <a-tree-select
+                style="width: 100%"
+                :dropdownStyle="{ maxHeight: '400px', overflow: 'auto' }"
+                :treeData="spareTypeTreeData"
+                :treeNodeFilterProp="'title'"
+                :showSearch="true"
+                v-model="queryParam.typeId"
+                placeholder="请选择"
+              >
+              </a-tree-select>
             </a-form-item>
           </a-col>
-          <a-col :md="6" :sm="24">
-            <a-form-item label="所属项目">
-              <a-select v-model="queryParam.useProject" placeholder="请选择">
-                <a-select-option
-                  v-for="({deptId, name}) in projectList"
-                  :key="deptId"
-                  :label="name"
-                  :value="deptId">{{ name }}
-                </a-select-option>
-              </a-select>
-            </a-form-item>
-          </a-col>
-           <a-col :md="6" :sm="24">
-              <a-form-item label="备件类别">
-                <a-tree-select
-                  style="width: 100%"
-                  :dropdownStyle="{ maxHeight: '400px', overflow: 'auto' }"
-                  :treeData="spareTypeTreeData"
-                  :treeNodeFilterProp="'title'"
-                  :showSearch="true"
-                  v-model="queryParam.typeId"
-                  placeholder="请选择"
-                >
-                </a-tree-select>
-              </a-form-item>
-            </a-col>
           <a-col :md="6 || 24" :sm="24">
             <span class="table-page-search-submitButtons">
               <a-button type="primary" @click="$refs.table.refresh(true)">查询</a-button>
@@ -71,13 +47,17 @@
       :rowSelection="options.rowSelection"
       showPagination="auto"
     >
-      <!--<span slot="action" slot-scope="record">
+      <span slot="action" slot-scope="record">
         <template>
-          <a @click="handleView(record)">仓库台账</a>
+          <a v-if="record.warnStatus != 1" @click="handleUpdateStatus(record, 1)">待处理</a>
+          <a-divider type="vertical" />
+          <a v-if="record.warnStatus != 2" @click="handleUpdateStatus(record, 2)">询价中</a>
+          <a-divider type="vertical" />
+          <a v-if="record.warnStatus != 3"@click="handleUpdateStatus(record, 3)">采购中</a>
           <a-divider type="vertical" />
-          <a v-if="$auth('store-spare-stores-edit')" @click="handleEdit(record)">出入库详情</a>
+          <a v-if="record.warnStatus != 0" @click="handleUpdateStatus(record, 0)">正常</a>
         </template>
-      </span>-->
+      </span>
       <span slot="delFlag" slot-scope="text">
         <badge
           :status="DictCache.COLOR.DELFLAG[text]"
@@ -94,11 +74,17 @@ import { STable, Ellipsis } from '@/components'
 import BaseForm from './modules/BaseForm'
 import Detail from './modules/Detail'
 import { fetchSpareTypeTree } from '@/api/sqarepartmanage/sparetype'
-import { queryDept,getDeptsAllByParentId } from '@/api/upms/dept'
-import { getSpareStoreTotalPage, deleteSpareStores, fetchSpareStore, exportSpareStore } from '@/api/store/sparestore'
+import { updateSparePartInfoWarnStatus } from '@/api/sqarepartmanage/sparepartinfo'
+import { queryDept, getDeptsAllByParentId } from '@/api/upms/dept'
+import {
+  getSpareStoreTotalPage,
+  deleteSpareStores,
+  fetchSpareStore,
+  exportSpareStore
+} from '@/api/store/sparestore'
 
 export default {
-  name: 'SpareStoreList',
+  name: 'SpareStoreTotal',
   components: {
     STable,
     Ellipsis,
@@ -109,6 +95,14 @@ export default {
     filter: {
       type: Number,
       default: -1
+    },
+    minStock: {
+      type: Boolean,
+      default: true
+    },
+    maxStock: {
+      type: Boolean,
+      default: null
     }
   },
   data () {
@@ -118,53 +112,75 @@ export default {
       spareTypeTreeData: [],
       // 查询参数
       queryParam: {
-        filter: this.filter
+        filter: this.filter,
+        minStock: this.minStock,
+        maxStock: this.maxStock
       },
       // 表头
       columns: [
         {
           title: '序号',
           dataIndex: 'index',
+          checked: true,
           customRender: (text, record, index) => {
             return `${(this.$refs.table.localPagination.current - 1) * this.$refs.table.localPagination.pageSize + index + 1}`
           }
         },
         {
           title: '编号',
+          checked: true,
           dataIndex: 'no'
         },
         {
           title: '备件名称',
+          checked: true,
           dataIndex: 'name'
         },
         {
           title: '规格型号',
+          checked: true,
           dataIndex: 'ggxh'
         },
         {
           title: '计量单位',
+          checked: true,
           dataIndex: 'unit'
         },
         {
           title: '单价',
+          checked: true,
           dataIndex: 'price'
         },
         {
-          title: '总库存',
-          dataIndex: 'totalStock'
+          title: '最低库存',
+          checked: true,
+          dataIndex: 'minStock'
+        },
+        {
+          title: '最高库存',
+          checked: true,
+          dataIndex: 'maxStock'
+        },
+        {
+          title: '实际库存',
+          checked: true,
+          dataIndex: 'totalStock',
+          customRender: (text, record, index) => {
+            if (text == null) {
+              return 0
+            } else {
+              return text
+            }
+          }
+        },
+        {
+          title: '操作',
+          checked: true,
+          key: 'action',
+          width: '200px',
+          align: 'center',
+          scopedSlots: { customRender: 'action' }
         }
-
-        //{
-         // title: '创建日期',
-         // dataIndex: 'createdTime'
-        //},
-        //{
-         // title: '操作',
-         // key: 'action',
-         // width: '200px',
-         // align: 'center',
-          //scopedSlots: { customRender: 'action' }
-       // }
       ],
       // 下拉框map
       delFlagMap: {},
@@ -206,8 +222,8 @@ export default {
     })
   },
   methods: {
-    handleCompanyChange(value) {
-      getDeptsAllByParentId({ deptId: value, nature: this.DictCache.VALUE.SYS_DEPT_NATURE.XIANG_MU_BU}).then(res => {
+    handleCompanyChange (value) {
+      getDeptsAllByParentId({ deptId: value, nature: this.DictCache.VALUE.SYS_DEPT_NATURE.XIANG_MU_BU }).then(res => {
         this.projectList = res.data
       })
     },
@@ -265,6 +281,18 @@ export default {
         modal.base(res.data)
       })
     },
+    handleUpdateStatus (record, warnStatus) {
+      const parameter = {}
+      parameter.id = record.spareId
+      parameter.warnStatus = warnStatus
+      parameter.type = 1
+      updateSparePartInfoWarnStatus(parameter)
+        .then(() => {
+          this.handleOk()
+        }).catch(() => {
+          this.confirmLoading = false
+        })
+    },
     handleOk () {
       this.$refs.table.refresh()
     },
@@ -274,7 +302,9 @@ export default {
     },
     resetSearchForm () {
       this.queryParam = {
-        filter: this.filter
+        filter: this.filter,
+        minStock: this.minStock,
+        maxStock: this.maxStock
       }
       this.$refs.table.refresh(true)
     },
@@ -282,12 +312,12 @@ export default {
       const parameter = {
         ...this.queryParam
       }
-      if(this.queryParam.useCompany == null){
-        this.$message.error("请先选择分公司")
+      if (this.queryParam.useCompany == null) {
+        this.$message.error('请先选择分公司')
         return
       }
-      if(this.queryParam.useProject == null){
-        this.$message.error("请先选择项目部")
+      if (this.queryParam.useProject == null) {
+        this.$message.error('请先选择项目部')
         return
       }
       exportSpareStore(parameter).then(file => {

+ 19 - 0
src/views/store/sparestore/SpareStoreTotalMinStock.vue

@@ -0,0 +1,19 @@
+<template>
+  <SpareStoreTotal :min-stock="true"/>
+</template>
+
+<script>
+import SpareStore from './SpareStoreTotal'
+import SpareStoreTotal from '@/views/store/sparestore/SpareStoreTotal'
+export default {
+  name: 'SpareStoreTotalMinStock',
+  components: {
+    SpareStoreTotal,
+    SpareStore
+  }
+}
+</script>
+
+<style scoped>
+
+</style>

+ 29 - 15
src/views/store/sparestore/modules/BaseForm.vue

@@ -12,24 +12,20 @@
         <a-input v-decorator="['id']" type="hidden"/>
       </a-form-item>
       <a-form-item
-        label="仓库id"
-        :labelCol="BaseTool.Constant.labelCol"
-        :wrapperCol="BaseTool.Constant.wrapperCol"
-        v-show="false"
-      >
-        <a-input
-          v-decorator="['storeId', {rules: [{required: true, message: '仓库id不能为空'}]}]" />
-      </a-form-item>
-      <a-form-item
-        label="仓库名称"
+        label="仓库"
         :labelCol="BaseTool.Constant.labelCol"
         :wrapperCol="BaseTool.Constant.wrapperCol"
       >
-        <a-input
-          style="width: 70%"
-          disabled
-          v-decorator="['storeName', {rules: [{required: true, message: '仓库名称不能为空'}]}]" />
-        <a-button type="primary" @click="handleStoreSelect">选择仓库</a-button>
+        <a-tree-select
+          style="width: 100%"
+          :dropdownStyle="{ maxHeight: '400px', overflow: 'auto' }"
+          :treeData="storeTreeDate"
+          :treeNodeFilterProp="'title'"
+          :showSearch="true"
+          v-decorator="['storeId', {rules: [{required: false, message: '仓库库位不能为空'}]}]"
+          placeholder="请选择"
+        >
+        </a-tree-select>
       </a-form-item>
       <a-form-item
         label="备件id"
@@ -139,6 +135,7 @@ import pick from 'lodash.pick'
 import { addSpareStore, updateSpareStore } from '@/api/store/sparestore'
 import StoreSelectModal from '@/views/store/store/modules/StoreSelectModal'
 import SparePartInfoSelectModal from '@/views/sqarepartmanage/sparepartinfo/modules/SparePartInfoSelectModal'
+import { fetchStoreTree } from '@/api/store/store'
 
 export default {
   name: 'BaseSpareStore',
@@ -148,6 +145,7 @@ export default {
       modalTitle: null,
       form: this.$form.createForm(this),
       visible: false,
+      storeTreeDate: [],
       // 下拉框map
       delFlagMap: {}
     }
@@ -159,10 +157,26 @@ export default {
   props: {
   },
   created () {
+    this.setTree()
     // 下拉框map
     this.delFlagMap = this.DictCache.getLabelByValueMapByType(this.DictCache.TYPE.DELFLAG)
   },
   methods: {
+    /**
+     * 设置仓库、备件类别树
+     */
+    setTree () {
+      fetchStoreTree().then(res => {
+        this.storeTreeDate = this.BaseTool.TREE.treeFilter(res.data, (item) => {
+          console.log(item.title + ',,' + item.level)
+          if (item.level === this.DictCache.VALUE.STORE_LEVEL.ZONGCANG) {
+            console.log(false)
+            item.selectable = false
+            item.disabled = true
+          }
+        })
+      })
+    },
     base (record) {
       this.visible = true
       // 如果是空标识添加

+ 64 - 10
src/views/store/sparestore/modules/SpareStoreSelectModal.vue

@@ -9,7 +9,7 @@
   >
     <a-card :bordered="false">
       <a-row :gutter="8">
-        <a-col :span="5">
+<!--        <a-col :span="5">
           <a-tree
             @expand="onExpand"
             :expandedKeys="expandedKeys"
@@ -18,14 +18,61 @@
             :selectedKeys="selectedKeys"
             :treeData="spareTypeTreeData"
           />
-        </a-col>
-        <a-col :span="19">
+        </a-col>-->
+        <a-col :span="24">
           <div class="table-page-search-wrapper">
             <a-form layout="inline">
               <a-row :gutter="48">
                 <a-col :md="8" :sm="24">
                   <a-form-item label="关键字">
-                    <a-input v-model="queryParam.keyword" placeholder="请输入名称/类型名称"/>
+                    <a-input v-model="queryParam.keyword" placeholder="请输入备件名称"/>
+                  </a-form-item>
+                </a-col>
+                <a-col :md="8" :sm="24">
+                  <a-form-item label="类型">
+                    <a-tree-select
+                      style="width: 100%"
+                      :dropdownStyle="{ maxHeight: '400px', overflow: 'auto' }"
+                      :treeData="spareTypeTreeData"
+                      :treeNodeFilterProp="'title'"
+                      :showSearch="true"
+                      v-model="queryParam.typeId"
+                      placeholder="请选择"
+                    >
+                    </a-tree-select>
+                  </a-form-item>
+                </a-col>
+                <a-col :md="8" :sm="24">
+                  <a-form-item label="规格型号">
+                    <a-input v-model="queryParam.ggxh" placeholder="模糊查询"/>
+                  </a-form-item>
+                </a-col>
+                <a-col :md="8" :sm="24">
+                  <a-form-item label="原厂编号">
+                    <a-input v-model="queryParam.initNo" placeholder="模糊查询"/>
+                  </a-form-item>
+                </a-col>
+                <a-col :md="8" :sm="24">
+                  <a-form-item label="关联设备">
+                    <a-input v-model="queryParam.model" placeholder="新号/旧号/名称/规格"/>
+                  </a-form-item>
+                </a-col>
+                <a-col :md="8" :sm="24">
+                  <a-form-item
+                    label="仓库"
+                    :labelCol="BaseTool.Constant.labelCol"
+                    :wrapperCol="BaseTool.Constant.wrapperCol"
+                  >
+                    <a-tree-select
+                      style="width: 100%"
+                      :dropdownStyle="{ maxHeight: '400px', overflow: 'auto' }"
+                      :treeData="storeTreeDate"
+                      :treeNodeFilterProp="'title'"
+                      :showSearch="true"
+                      v-model="queryParam.storeId"
+                      placeholder="请选择"
+                    >
+                    </a-tree-select>
                   </a-form-item>
                 </a-col>
                 <a-col :md="8 || 24" :sm="24">
@@ -74,6 +121,7 @@ import { STable, Ellipsis } from '@/components'
 import Detail from './Detail'
 import { getSpareStorePage, fetchSpareStore } from '@/api/store/sparestore'
 import { fetchSpareTypeTree } from '@/api/sqarepartmanage/sparetype'
+import { fetchStoreTree } from '@/api/store/store'
 
 export default {
   name: 'SpareStoreSelectModal',
@@ -104,6 +152,7 @@ export default {
     return {
       confirmLoading: false,
       mdl: {},
+      storeTreeDate: [],
       modalTitle: null,
       visible: false,
       record: null,
@@ -142,10 +191,10 @@ export default {
           title: '原厂编号',
           dataIndex: 'initNo'
         },
-        // {
-        //  title: '仓库名称',
-        //  dataIndex: 'storeName'
-        // },
+        {
+          title: '仓库名称',
+          dataIndex: 'storeName'
+        },
         {
           title: '库存数量',
           dataIndex: 'num'
@@ -203,6 +252,9 @@ export default {
     fetchSpareTypeTree({}).then(res => {
       this.spareTypeTreeData = res.data
     })
+    fetchStoreTree({}).then(res => {
+      this.storeTreeDate = res.data
+    })
   },
   methods: {
     tableOption () {
@@ -260,6 +312,8 @@ export default {
     resetSearchForm () {
       this.queryParam.keyword = null
       this.queryParam.typeId = null
+      this.queryParam.model = null
+      this.queryParam.storeId = null
       this.$refs.table.refresh(true)
     },
     base (record, queryParam = {}) {
@@ -284,11 +338,11 @@ export default {
       if (this.selectedRowKeys.length === 0) {
         this.$message.warn('请至少选择一项信息')
       } else {
-        /*console.log(this.selectedRows[0].num)
+        /* console.log(this.selectedRows[0].num)
          if (this.selectedRows[0].num == 0) {
          this.$message.error('不能选择库存为0的物品,请重新选择')
          return
-       }*/
+       } */
         this.confirmLoading = true
         this.$emit('selected', this.record, this.selectedRowKeys, this.selectedRows)
         this.confirmLoading = false