浏览代码

数据质量报告

zhangkunling 2 年之前
父节点
当前提交
cfd958cbcd

+ 143 - 7
package-lock.json

@@ -1071,7 +1071,6 @@
       "version": "7.16.3",
       "resolved": "https://registry.npmmirror.com/@babel/runtime/download/@babel/runtime-7.16.3.tgz",
       "integrity": "sha512-WBwekcqacdY2e9AF/Q7WLFUWmdJGJTkbjqTjoMDgXkVZ3ZRUvOPsLb5KdwISoQVsbP+DQzVZW4Zhci0DvpbNTQ==",
-      "dev": true,
       "requires": {
         "regenerator-runtime": "^0.13.4"
       }
@@ -1368,6 +1367,12 @@
       "integrity": "sha1-Y7t9Bn2xB8weRXwwO8JdUR/r9ss=",
       "dev": true
     },
+    "@types/raf": {
+      "version": "3.4.0",
+      "resolved": "https://registry.npmmirror.com/@types/raf/-/raf-3.4.0.tgz",
+      "integrity": "sha512-taW5/WYqo36N7V39oYyHP9Ipfd5pNFvGTIQsNGj86xV88YQ7GnI30/yMfKDF7Zgin0m3e+ikX88FvImnK4RjGw==",
+      "optional": true
+    },
     "@types/range-parser": {
       "version": "1.2.4",
       "resolved": "https://registry.npmmirror.com/@types/range-parser/download/@types/range-parser-1.2.4.tgz?cache=0&sync_timestamp=1637270332188&other_urls=https%3A%2F%2Fregistry.npmmirror.com%2F%40types%2Frange-parser%2Fdownload%2F%40types%2Frange-parser-1.2.4.tgz",
@@ -2294,8 +2299,7 @@
     "atob": {
       "version": "2.1.2",
       "resolved": "https://registry.npm.taobao.org/atob/download/atob-2.1.2.tgz",
-      "integrity": "sha1-bZUX654DDSQ2ZmZR6GvZ9vE1M8k=",
-      "dev": true
+      "integrity": "sha1-bZUX654DDSQ2ZmZR6GvZ9vE1M8k="
     },
     "autoprefixer": {
       "version": "9.8.8",
@@ -2452,6 +2456,11 @@
         }
       }
     },
+    "base64-arraybuffer": {
+      "version": "1.0.2",
+      "resolved": "https://registry.npmmirror.com/base64-arraybuffer/-/base64-arraybuffer-1.0.2.tgz",
+      "integrity": "sha512-I3yl4r9QB5ZRY3XuJVEPfc2XhZO6YweFPI+UovAzn+8/hb3oJ6lnysaFcjVpkCPfVWFUDvoZ8kmVDP7WyRtYtQ=="
+    },
     "base64-js": {
       "version": "1.5.1",
       "resolved": "https://registry.npm.taobao.org/base64-js/download/base64-js-1.5.1.tgz",
@@ -2734,6 +2743,11 @@
         "picocolors": "^1.0.0"
       }
     },
+    "btoa": {
+      "version": "1.2.1",
+      "resolved": "https://registry.npmmirror.com/btoa/-/btoa-1.2.1.tgz",
+      "integrity": "sha512-SB4/MIGlsiVkMcHmT+pSmIPoNDoHg+7cMzmt3Uxt628MTz2487DKSqK/fuhFBrkuqrYv5UCEnACpF4dTFNKc/g=="
+    },
     "buffer": {
       "version": "4.9.2",
       "resolved": "https://registry.npm.taobao.org/buffer/download/buffer-4.9.2.tgz?cache=0&sync_timestamp=1606098189689&other_urls=https%3A%2F%2Fregistry.npm.taobao.org%2Fbuffer%2Fdownload%2Fbuffer-4.9.2.tgz",
@@ -2909,6 +2923,22 @@
       "integrity": "sha512-YhF/hG6nqBEllymSIjLtR2iWDDnChvhnVJqp+vloyt2tEHFG1yBR+ac2B/rOw0qOK0m0lEXU2dv4E/sMk5P9Kg==",
       "dev": true
     },
+    "canvg": {
+      "version": "3.0.10",
+      "resolved": "https://registry.npmmirror.com/canvg/-/canvg-3.0.10.tgz",
+      "integrity": "sha512-qwR2FRNO9NlzTeKIPIKpnTY6fqwuYSequ8Ru8c0YkYU7U0oW+hLUvWadLvAu1Rl72OMNiFhoLu4f8eUjQ7l/+Q==",
+      "optional": true,
+      "requires": {
+        "@babel/runtime": "^7.12.5",
+        "@types/raf": "^3.4.0",
+        "core-js": "^3.8.3",
+        "raf": "^3.4.1",
+        "regenerator-runtime": "^0.13.7",
+        "rgbcolor": "^1.0.1",
+        "stackblur-canvas": "^2.0.0",
+        "svg-pathdata": "^6.0.3"
+      }
+    },
     "case-sensitive-paths-webpack-plugin": {
       "version": "2.4.0",
       "resolved": "https://registry.npm.taobao.org/case-sensitive-paths-webpack-plugin/download/case-sensitive-paths-webpack-plugin-2.4.0.tgz?cache=0&sync_timestamp=1614019098201&other_urls=https%3A%2F%2Fregistry.npm.taobao.org%2Fcase-sensitive-paths-webpack-plugin%2Fdownload%2Fcase-sensitive-paths-webpack-plugin-2.4.0.tgz",
@@ -3763,6 +3793,14 @@
         "timsort": "^0.3.0"
       }
     },
+    "css-line-break": {
+      "version": "2.1.0",
+      "resolved": "https://registry.npmmirror.com/css-line-break/-/css-line-break-2.1.0.tgz",
+      "integrity": "sha512-FHcKFCZcAha3LwfVBhCQbW2nCNbkZXn7KVUJcsT5/P8YmfsVja0FMPJr0B903j/E69HUphKiV9iQArX8SDYA4w==",
+      "requires": {
+        "utrie": "^1.0.2"
+      }
+    },
     "css-loader": {
       "version": "3.6.0",
       "resolved": "https://registry.npmmirror.com/css-loader/download/css-loader-3.6.0.tgz?cache=0&sync_timestamp=1635968760879&other_urls=https%3A%2F%2Fregistry.npmmirror.com%2Fcss-loader%2Fdownload%2Fcss-loader-3.6.0.tgz",
@@ -4376,6 +4414,12 @@
         }
       }
     },
+    "dompurify": {
+      "version": "2.3.6",
+      "resolved": "https://registry.npmmirror.com/dompurify/-/dompurify-2.3.6.tgz",
+      "integrity": "sha512-OFP2u/3T1R5CEgWCEONuJ1a5+MFKnOYpkywpUSxv/dj1LeBT1erK+JwM7zK0ROy2BRhqVCf0LRw/kHqKuMkVGg==",
+      "optional": true
+    },
     "domutils": {
       "version": "1.7.0",
       "resolved": "https://registry.nlark.com/domutils/download/domutils-1.7.0.tgz",
@@ -4441,6 +4485,15 @@
         "safer-buffer": "^2.1.0"
       }
     },
+    "echarts": {
+      "version": "5.3.1",
+      "resolved": "https://registry.npmmirror.com/echarts/-/echarts-5.3.1.tgz",
+      "integrity": "sha512-nWdlbgX3OVY0hpqncSvp0gDt1FRSKWn7lsWEH+PHmfCuvE0QmSw17pczQvm8AvawnLEkmf1Cts7YwQJZNC0AEQ==",
+      "requires": {
+        "tslib": "2.3.0",
+        "zrender": "5.3.1"
+      }
+    },
     "ee-first": {
       "version": "1.1.1",
       "resolved": "https://registry.npm.taobao.org/ee-first/download/ee-first-1.1.1.tgz",
@@ -5000,6 +5053,11 @@
         "websocket-driver": ">=0.5.1"
       }
     },
+    "fflate": {
+      "version": "0.4.8",
+      "resolved": "https://registry.npmmirror.com/fflate/-/fflate-0.4.8.tgz",
+      "integrity": "sha512-FJqqoDBR00Mdj9ppamLa/Y7vxm+PRmNWA67N846RvsoYVMKB4q3y/de5PA7gUmRMYK/8CMz2GDZQmCRN1wBcWA=="
+    },
     "figgy-pudding": {
       "version": "3.5.2",
       "resolved": "https://registry.npm.taobao.org/figgy-pudding/download/figgy-pudding-3.5.2.tgz",
@@ -5658,6 +5716,15 @@
         }
       }
     },
+    "html2canvas": {
+      "version": "1.4.1",
+      "resolved": "https://registry.npmmirror.com/html2canvas/-/html2canvas-1.4.1.tgz",
+      "integrity": "sha512-fPU6BHNpsyIhr8yyMpTLLxAbkaK8ArIBcmZIRiBLiDhjeqvXolaEmDGmELFuX9I4xDcaKKcJl+TKZLqruBbmWA==",
+      "requires": {
+        "css-line-break": "^2.1.0",
+        "text-segmentation": "^1.0.3"
+      }
+    },
     "htmlparser2": {
       "version": "6.1.0",
       "resolved": "https://registry.npmmirror.com/htmlparser2/download/htmlparser2-6.1.0.tgz?cache=0&sync_timestamp=1636640990615&other_urls=https%3A%2F%2Fregistry.npmmirror.com%2Fhtmlparser2%2Fdownload%2Fhtmlparser2-6.1.0.tgz",
@@ -6518,6 +6585,21 @@
         "graceful-fs": "^4.1.6"
       }
     },
+    "jspdf": {
+      "version": "2.5.1",
+      "resolved": "https://registry.npmmirror.com/jspdf/-/jspdf-2.5.1.tgz",
+      "integrity": "sha512-hXObxz7ZqoyhxET78+XR34Xu2qFGrJJ2I2bE5w4SM8eFaFEkW2xcGRVUss360fYelwRSid/jT078kbNvmoW0QA==",
+      "requires": {
+        "@babel/runtime": "^7.14.0",
+        "atob": "^2.1.2",
+        "btoa": "^1.2.1",
+        "canvg": "^3.0.6",
+        "core-js": "^3.6.0",
+        "dompurify": "^2.2.0",
+        "fflate": "^0.4.8",
+        "html2canvas": "^1.0.0-rc.5"
+      }
+    },
     "jsprim": {
       "version": "1.4.1",
       "resolved": "https://registry.npmmirror.com/jsprim/download/jsprim-1.4.1.tgz?cache=0&sync_timestamp=1637110704505&other_urls=https%3A%2F%2Fregistry.npmmirror.com%2Fjsprim%2Fdownload%2Fjsprim-1.4.1.tgz",
@@ -7650,8 +7732,7 @@
     "performance-now": {
       "version": "2.1.0",
       "resolved": "https://registry.npm.taobao.org/performance-now/download/performance-now-2.1.0.tgz",
-      "integrity": "sha1-Ywn04OX6kT7BxpMHrjZLSzd8nns=",
-      "dev": true
+      "integrity": "sha1-Ywn04OX6kT7BxpMHrjZLSzd8nns="
     },
     "picocolors": {
       "version": "1.0.0",
@@ -8683,6 +8764,15 @@
       "integrity": "sha1-M0WUG0FTy50ILY7uTNogFqmu9/Y=",
       "dev": true
     },
+    "raf": {
+      "version": "3.4.1",
+      "resolved": "https://registry.npmmirror.com/raf/-/raf-3.4.1.tgz",
+      "integrity": "sha512-Sq4CW4QhwOHE8ucn6J34MqtZCeWFP2aQSmrlroYgqAV1PjStIhJXxYuTgUIfkEk7zTLjmIjLmU5q+fbD1NnOJA==",
+      "optional": true,
+      "requires": {
+        "performance-now": "^2.1.0"
+      }
+    },
     "randombytes": {
       "version": "2.1.0",
       "resolved": "https://registry.npm.taobao.org/randombytes/download/randombytes-2.1.0.tgz",
@@ -8775,8 +8865,7 @@
     "regenerator-runtime": {
       "version": "0.13.9",
       "resolved": "https://registry.nlark.com/regenerator-runtime/download/regenerator-runtime-0.13.9.tgz",
-      "integrity": "sha1-iSV0Kpj/2QgUmI11Zq0wyjsmO1I=",
-      "dev": true
+      "integrity": "sha1-iSV0Kpj/2QgUmI11Zq0wyjsmO1I="
     },
     "regenerator-transform": {
       "version": "0.14.5",
@@ -9065,6 +9154,12 @@
       "integrity": "sha1-QzdOLiyglosO8VI0YLfXMP8i7rM=",
       "dev": true
     },
+    "rgbcolor": {
+      "version": "1.0.1",
+      "resolved": "https://registry.npmmirror.com/rgbcolor/-/rgbcolor-1.0.1.tgz",
+      "integrity": "sha512-9aZLIrhRaD97sgVhtJOW6ckOEh6/GnvQtdVNfdZ6s67+3/XwLS9lBcQYzEEhYVeUowN7pRzMLsyGhK2i/xvWbw==",
+      "optional": true
+    },
     "rimraf": {
       "version": "2.7.1",
       "resolved": "https://registry.npm.taobao.org/rimraf/download/rimraf-2.7.1.tgz",
@@ -9736,6 +9831,12 @@
       "integrity": "sha1-g26zyDgv4pNv6vVEYxAXzn1Ho88=",
       "dev": true
     },
+    "stackblur-canvas": {
+      "version": "2.5.0",
+      "resolved": "https://registry.npmmirror.com/stackblur-canvas/-/stackblur-canvas-2.5.0.tgz",
+      "integrity": "sha512-EeNzTVfj+1In7aSLPKDD03F/ly4RxEuF/EX0YcOG0cKoPXs+SLZxDawQbexQDBzwROs4VKLWTOaZQlZkGBFEIQ==",
+      "optional": true
+    },
     "stackframe": {
       "version": "1.2.0",
       "resolved": "https://registry.npm.taobao.org/stackframe/download/stackframe-1.2.0.tgz",
@@ -9972,6 +10073,12 @@
         "has-flag": "^3.0.0"
       }
     },
+    "svg-pathdata": {
+      "version": "6.0.3",
+      "resolved": "https://registry.npmmirror.com/svg-pathdata/-/svg-pathdata-6.0.3.tgz",
+      "integrity": "sha512-qsjeeq5YjBZ5eMdFuUa4ZosMLxgr5RZ+F+Y1OrDhuOCEInRMA3x74XdBtggJcj9kOeInz0WE+LgCPDkZFlBYJw==",
+      "optional": true
+    },
     "svg-tags": {
       "version": "1.0.0",
       "resolved": "https://registry.npm.taobao.org/svg-tags/download/svg-tags-1.0.0.tgz",
@@ -10130,6 +10237,14 @@
         }
       }
     },
+    "text-segmentation": {
+      "version": "1.0.3",
+      "resolved": "https://registry.npmmirror.com/text-segmentation/-/text-segmentation-1.0.3.tgz",
+      "integrity": "sha512-iOiPUo/BGnZ6+54OsWxZidGCsdU8YbE4PSpdPinp7DeMtUJNJBoJ/ouUSTJjHkh1KntHaltHl/gDs2FC4i5+Nw==",
+      "requires": {
+        "utrie": "^1.0.2"
+      }
+    },
     "thenify": {
       "version": "3.3.1",
       "resolved": "https://registry.npm.taobao.org/thenify/download/thenify-3.3.1.tgz",
@@ -10283,6 +10398,11 @@
       "integrity": "sha1-pQCtCEsHmPHDBxrzkeZZEshrypI=",
       "dev": true
     },
+    "tslib": {
+      "version": "2.3.0",
+      "resolved": "https://registry.npmmirror.com/tslib/-/tslib-2.3.0.tgz",
+      "integrity": "sha512-N82ooyxVNm6h1riLCoyS9e3fuJ3AMG2zIZs2Gd1ATcSFjSA23Q0fzjjZeh0jbJvWVDZ0cJT8yaNNaaXHzueNjg=="
+    },
     "tty-browserify": {
       "version": "0.0.0",
       "resolved": "https://registry.npm.taobao.org/tty-browserify/download/tty-browserify-0.0.0.tgz",
@@ -10609,6 +10729,14 @@
       "integrity": "sha1-n5VxD1CiZ5R7LMwSR0HBAoQn5xM=",
       "dev": true
     },
+    "utrie": {
+      "version": "1.0.2",
+      "resolved": "https://registry.npmmirror.com/utrie/-/utrie-1.0.2.tgz",
+      "integrity": "sha512-1MLa5ouZiOmQzUbjbu9VmjLzn1QLXBhwpUa7kdLUQK+KQ5KA9I1vk5U4YHe/X2Ch7PYnJfWuWT+VbuxbGwljhw==",
+      "requires": {
+        "base64-arraybuffer": "^1.0.2"
+      }
+    },
     "uuid": {
       "version": "3.4.0",
       "resolved": "https://registry.npmmirror.com/uuid/download/uuid-3.4.0.tgz",
@@ -11640,6 +11768,14 @@
       "resolved": "https://registry.npmmirror.com/yargs-parser/download/yargs-parser-20.2.9.tgz?cache=0&sync_timestamp=1637031073527&other_urls=https%3A%2F%2Fregistry.npmmirror.com%2Fyargs-parser%2Fdownload%2Fyargs-parser-20.2.9.tgz",
       "integrity": "sha1-LrfcOwKJcY/ClfNidThFxBoMlO4=",
       "dev": true
+    },
+    "zrender": {
+      "version": "5.3.1",
+      "resolved": "https://registry.npmmirror.com/zrender/-/zrender-5.3.1.tgz",
+      "integrity": "sha512-7olqIjy0gWfznKr6vgfnGBk7y4UtdMvdwFmK92vVQsQeDPyzkHW1OlrLEKg6GHz1W5ePf0FeN1q2vkl/HFqhXw==",
+      "requires": {
+        "tslib": "2.3.0"
+      }
     }
   }
 }

+ 3 - 0
package.json

@@ -9,7 +9,10 @@
   "dependencies": {
     "axios": "^0.24.0",
     "core-js": "^3.6.5",
+    "echarts": "^5.3.1",
+    "html2canvas": "^1.4.1",
     "js-md5": "^0.7.3",
+    "jspdf": "^2.5.1",
     "lib-flexible": "^0.3.2",
     "lodash": "^4.17.21",
     "moment": "^2.29.1",

+ 1 - 1
public/index.html

@@ -8,7 +8,7 @@
     <!-- <title><%= htmlWebpackPlugin.options.title %></title> -->
     <title>智慧城轨大数据后台管理平台</title>
   </head>
-  <body>
+  <body class="common-scroll">
     <noscript>
       <strong>We're sorry but <%= htmlWebpackPlugin.options.title %> doesn't work properly without JavaScript enabled. Please enable it to continue.</strong>
     </noscript>

+ 11 - 3
src/assets/iconfont/iconfont.css

@@ -1,8 +1,8 @@
 @font-face {
   font-family: "iconfont"; /* Project id 2962009 */
-  src: url('iconfont.woff2?t=1647486573632') format('woff2'),
-       url('iconfont.woff?t=1647486573632') format('woff'),
-       url('iconfont.ttf?t=1647486573632') format('truetype');
+  src: url('iconfont.woff2?t=1648434488364') format('woff2'),
+       url('iconfont.woff?t=1648434488364') format('woff'),
+       url('iconfont.ttf?t=1648434488364') format('truetype');
 }
 
 .iconfont {
@@ -13,6 +13,14 @@
   -moz-osx-font-smoothing: grayscale;
 }
 
+.icon-_chakanxiazai:before {
+  content: "\e619";
+}
+
+.icon-chakan:before {
+  content: "\e618";
+}
+
 .icon-wancheng:before {
   content: "\e844";
 }

文件差异内容过多而无法显示
+ 0 - 0
src/assets/iconfont/iconfont.js


+ 14 - 0
src/assets/iconfont/iconfont.json

@@ -6,6 +6,20 @@
   "description": "",
   "glyphs": [
     {
+      "icon_id": "9231386",
+      "name": "2_查看下载1",
+      "font_class": "_chakanxiazai",
+      "unicode": "e619",
+      "unicode_decimal": 58905
+    },
+    {
+      "icon_id": "201556",
+      "name": "查看",
+      "font_class": "chakan",
+      "unicode": "e618",
+      "unicode_decimal": 58904
+    },
+    {
       "icon_id": "1474234",
       "name": "完成",
       "font_class": "wancheng",

二进制
src/assets/iconfont/iconfont.ttf


二进制
src/assets/iconfont/iconfont.woff


二进制
src/assets/iconfont/iconfont.woff2


二进制
src/assets/images/dataReport1.png


二进制
src/assets/images/dataReport2.png


二进制
src/assets/images/dataReport3.png


二进制
src/assets/images/dataReport4.png


二进制
src/assets/images/dataReport5.png


二进制
src/assets/images/reportBg.png


+ 6 - 3
src/components/StatisticsList.vue

@@ -1,7 +1,7 @@
 <template>
   <div class="tabs-list-wrap">
     <Row :gutter="16">
-      <Col :span="spanNum" v-for="(item, index) in tabsData" :key="index">
+      <Col :span="spanNum" v-for="(item, index) in tabsData" :key="index" :style="'width:'+ w">
         <div class="tabs-list">
           <img :src="tabsIcon[index].imgSrc" >
           <div>
@@ -45,7 +45,11 @@ export default {
       type: Number,
       default: 6
     },
-     url: {
+    url: {
+      type: String,
+      default: ''
+    },
+    w:{
       type: String,
       default: ''
     }
@@ -66,7 +70,6 @@ export default {
      this.$get(this.url).then(res=>{
         if (res.httpCode == 1){
           this.tabsData = res.data.data
-          console.log(this.tabsData)
         } else {
           this.tabsData = this.tabsInitData
           this.$Message.info(res.msg)

+ 14 - 0
src/libs/http.js

@@ -129,4 +129,18 @@ export function put(url,data = {}){
            console.log(err)
          })
   })
+}
+/*
+处理同时发送多个请求,可以实现在多个请求都完成后再执行一些逻辑 
+*/
+export function axiosAll(arr){
+  return new Promise((resolve,reject) => {
+    axios.all(arr)
+         .then(response => {
+           resolve(response)
+         },err => {
+           reject(err)
+           console.log(err)
+         })
+  })
 }

+ 2037 - 0
src/login/DownAllQualityReport.vue

@@ -0,0 +1,2037 @@
+<template>
+  <div class="quality-report">
+    <nav style="" class="nav-content">
+      <a class="nav-list" v-for="(item, index) in navList" :key="index" @click="jump(index)" :class="index==currentIndex?'current-item':''">{{item}}</a>
+    </nav>
+    <div class="report-container" id="report" ref="downReport">
+      <div class="report-header">
+        <div class="header-title">数据质量报告</div>
+        <div class="header-subtitle">
+          <span>数据范围:全部</span>
+          <span>报告类型:{{queryParams.reportClassName}}</span>
+           <span v-if="queryParams.reportClassName == '日报'">时间范围:{{queryParams.beginDate}}</span>
+          <span v-else>时间范围:{{queryParams.beginDate}}~{{queryParams.endDate}}</span>
+        </div>
+      </div>
+      <div class="report-content">
+        <div class="report-section">
+          <div class="title-content">
+            <div class="title-line">
+              <span></span>综合数据质量分析
+            </div>
+          </div>
+          <div class="report-echarts">
+            <Row :gutter="16" class-name="report-echarts-row">
+              <Col :span="12">
+                <div class="report-echarts-main">
+                  <div class="echarts-title">1. 综合得分</div>
+                  <div id="guage" class="echart-detail"></div>
+                </div>
+             </Col>
+              <Col :span="12">
+                <div class="report-echarts-main">
+                  <div class="echarts-title">2. 评估维度</div>
+                  <div id="radar" class="echart-detail"></div>
+                </div>
+              </Col>
+            </Row>
+            <Row :gutter="16" class-name="report-echarts-row">
+              <Col :span="24">
+                <div class="report-echarts-main">
+                  <div class="echarts-title">3. 综合数据质量趋势</div>
+                  <div id="line3" class="echart-detail"></div>
+                </div>
+             </Col>
+            </Row>
+            <Row :gutter="16" class-name="report-echarts-row">
+              <Col :span="24">
+                <div class="report-echarts-main no-truncation">
+                  <div class="echarts-title">4. 综合数据质量分析-按应用</div>
+                  <div id="bar4" class="echart-detail"></div>
+                  <div class="report-echarts-table">
+                    <Table :columns="columns4" :data="tableData4" class="common-table report-table-detail" no-data-text="" :row-class-name="rowClassName">
+                      <template slot-scope="{row,index}" slot="paramDou01">
+                        <span :style="index==0 ? 'color:#5EB6FC': ''">{{row.paramDou01+'%'}}</span>
+                      </template>
+                      <template slot-scope="{row,index}" slot="paramDou02">
+                        <span :style="index==0 ? 'color:#5EB6FC': ''">{{row.paramDou02+'%'}}</span>
+                      </template>
+                      <template slot-scope="{row}" slot="paramDou04">
+                        <Icon type="md-arrow-up" style="color: #09CB09;font-size:20px" v-show="row.paramDou04>0"/>
+                        <Icon type="md-arrow-down" style="color: #F32F2F;font-size:20px" v-show="row.paramDou04<0" />
+                        {{Math.abs(row.paramDou04)+'%'}}
+                      </template>
+                    </Table>
+                  </div>
+                </div>
+             </Col>
+            </Row>
+             <Row :gutter="16" class-name="report-echarts-row">
+              <Col :span="24">
+                <div class="report-echarts-main no-truncation">
+                  <div class="echarts-title">5. 综合数据质量分析-按规则类型</div>
+                  <div id="bar5" class="echart-detail"></div>
+                  <div class="report-echarts-table">
+                    <Table :columns="columns5" :data="tableData5" class="common-table report-table-detail" no-data-text="" :row-class-name="rowClassName">
+                      <template slot-scope="{row,index}" slot="paramDou01">
+                        <span :style="index==0 ? 'color:#5EB6FC': ''">{{row.paramDou01+'%'}}</span>
+                      </template>
+                      <template slot-scope="{row,index}" slot="paramDou02">
+                        <span :style="index==0 ? 'color:#5EB6FC': ''">{{row.paramDou02+'%'}}</span>
+                      </template>
+                       <template slot-scope="{row}" slot="paramDou04">
+                        <Icon type="md-arrow-up" style="color: #09CB09;font-size:20px" v-show="row.paramDou04>0"/>
+                        <Icon type="md-arrow-down" style="color: #F32F2F;font-size:20px" v-show="row.paramDou04<0" />
+                        {{Math.abs(row.paramDou04)+'%'}}
+                      </template>
+                    </Table>
+                  </div>
+                </div>
+             </Col>
+            </Row>
+          </div>
+        </div>
+         <div class="report-section">
+          <div class="title-content no-truncation">
+            <div class="title-line">
+              <span></span>数据异常分析
+            </div>
+          </div>
+          <div class="report-echarts">
+            <Row :gutter="16" class-name="report-echarts-row">
+                <Col :span="24">
+                  <div class="report-echarts-main no-truncation">
+                    <div class="echarts-title">6. 数据异常分析 - 按应用</div>
+                    <div class="echarts-sub-title">数据质量检测异常,按来源应用区分数据如下:</div>
+                    <Row :gutter="16" align="middle">
+                      <Col :span="8">
+                        <div id="pie6" class="echart-detail echart-pie"></div>
+                      </Col>
+                      <Col :span="16">
+                        <div class="report-echarts-table report-echarts-right-table">
+                           <Table :columns="columnsRule" :data="tableData6" class="common-table report-table-detail" no-data-text="" :row-class-name="rowClassName">
+                             <template slot-scope="{ index }" slot="xAxis">
+                              <span class="table-legend" :style="'background:'+tableColumnColor6[index]" v-show="index>0"></span>
+                            </template>
+                             <template slot-scope="{row,index}" slot="paramDou01">
+                                <span :style="index==0 ? 'color:#ECCF0C': ''">{{row.paramDou01}}%</span>
+                              </template>
+                           </Table>
+                        </div>
+                      </Col>
+                    </Row>
+                  </div>
+               </Col>
+            </Row>
+            <Row :gutter="16" class-name="report-echarts-row">
+                <Col :span="24">
+                  <div class="report-echarts-main no-truncation">
+                    <div class="echarts-title">7. 数据异常分析 - 按规则类型</div>
+                    <div class="echarts-sub-title">数据质量检测异常,按来源规则类型区分数据如下:</div>
+                    <Row :gutter="16" align="middle">
+                      <Col :span="8">
+                        <div id="pie7" class="echart-detail"></div>
+                      </Col>
+                      <Col :span="16">
+                         <div class="report-echarts-table report-echarts-right-table">
+                           <Table :columns="columnsRule" :data="tableData7" class="common-table report-table-detail" no-data-text="" :row-class-name="rowClassName">
+                             <template slot-scope="{ index }" slot="xAxis">
+                              <span class="table-legend" :style="'background:'+tableColumnColor7[index]" v-show="index>0"></span>
+                            </template>
+                             <template slot-scope="{row,index}" slot="paramDou01">
+                                <span :style="index==0 ? 'color:#ECCF0C': ''">{{row.paramDou01}}%</span>
+                              </template>
+                           </Table>
+                        </div>
+                      </Col>
+                    </Row>
+                  </div>
+               </Col>
+            </Row>
+          </div>
+        <div class="report-section">
+          <div class="title-content no-truncation">
+            <div class="title-line">
+              <span></span>分规则数据质量分析
+            </div>
+          </div>
+          <div class="report-echarts">
+            <Row :gutter="16" class-name="report-echarts-row">
+                <Col :span="24">
+                  <div class="report-echarts-main no-truncation">
+                    <div class="echarts-title">8. 分规则数据质量分析 - 一致性</div>
+                    <div class="echarts-sub-title">数据一致性检测异常,按来源应用区分数据如下:</div>
+                    <Row :gutter="16" align="middle">
+                      <Col :span="8">
+                        <div id="pie8" class="echart-detail"></div>
+                      </Col>
+                      <Col :span="16">
+                        <div class="report-echarts-table report-echarts-right-table">
+                           <Table :columns="columnsRule" :data="tableData8" class="common-table report-table-detail" no-data-text="" :row-class-name="rowClassName">
+                            <template slot-scope="{ index }" slot="xAxis">
+                              <span class="table-legend" :style="'background:'+tableColumnColor8[index]" v-show="index>0"></span>
+                            </template>
+                            <template slot-scope="{row,index}" slot="paramDou01">
+                              <span :style="index==0 ? 'color:#ECCF0C': ''">{{row.paramDou01}}%</span>
+                            </template>
+                           </Table>
+                        </div>
+                      </Col>
+                    </Row>
+                  </div>
+               </Col>
+            </Row>
+            <Row :gutter="16" class-name="report-echarts-row">
+                <Col :span="24">
+                  <div class="report-echarts-main no-truncation">
+                    <div class="echarts-title">9. 分规则数据质量分析 - 完整性</div>
+                    <div class="echarts-sub-title">数据完整性检测异常,按来源应用区分数据如下:</div>
+                    <Row :gutter="16" align="middle">
+                      <Col :span="8">
+                        <div id="pie9" class="echart-detail"></div>
+                      </Col>
+                      <Col :span="16">
+                        <div class="report-echarts-table report-echarts-right-table">
+                          <Table :columns="columnsRule" :data="tableData9" class="common-table report-table-detail" no-data-text="" :row-class-name="rowClassName">
+                             <template slot-scope="{ index }" slot="xAxis">
+                              <span class="table-legend" :style="'background:'+tableColumnColor9[index]" v-show="index>0"></span>
+                            </template>
+                             <template slot-scope="{row,index}" slot="paramDou01">
+                                <span :style="index==0 ? 'color:#ECCF0C': ''">{{row.paramDou01}}%</span>
+                              </template>
+                           </Table>
+                        </div>
+                      </Col>
+                    </Row>
+                  </div>
+               </Col>
+            </Row>
+            <Row :gutter="16" class-name="report-echarts-row">
+                <Col :span="24">
+                  <div class="report-echarts-main no-truncation">
+                    <div class="echarts-title">10. 分规则数据质量分析 - 准确性</div>
+                    <div class="echarts-sub-title">数据准确性检测异常,按来源应用区分数据如下:</div>
+                    <Row :gutter="16" align="middle">
+                      <Col :span="8">
+                        <div id="pie10" class="echart-detail"></div>
+                      </Col>
+                      <Col :span="16">
+                        <div class="report-echarts-table report-echarts-right-table">
+                          <Table :columns="columnsRule" :data="tableData10" class="common-table report-table-detail" no-data-text="" :row-class-name="rowClassName">
+                             <template slot-scope="{ index }" slot="xAxis">
+                              <span class="table-legend" :style="'background:'+tableColumnColor10[index]" v-show="index>0"></span>
+                            </template>
+                             <template slot-scope="{row,index}" slot="paramDou01">
+                                <span :style="index==0 ? 'color:#ECCF0C': ''">{{row.paramDou01}}%</span>
+                              </template>
+                           </Table>
+                        </div>
+                      </Col>
+                    </Row>
+                  </div>
+               </Col>
+            </Row>
+            <Row :gutter="16" class-name="report-echarts-row">
+                <Col :span="24">
+                  <div class="report-echarts-main no-truncation">
+                    <div class="echarts-title">11. 分规则数据质量分析 - 及时性(数据采集)</div>
+                    <div class="echarts-sub-title">数据采集及时性检测异常,按来源应用区分数据如下:</div>
+                    <Row :gutter="16" align="middle">
+                      <Col :span="8">
+                        <div id="pie11" class="echart-detail"></div>
+                      </Col>
+                      <Col :span="16">
+                        <div class="report-echarts-table report-echarts-right-table">
+                          <Table :columns="columnsRule" :data="tableData11" class="common-table report-table-detail" no-data-text="" :row-class-name="rowClassName">
+                            <template slot-scope="{ index }" slot="xAxis">
+                              <span class="table-legend" :style="'background:'+tableColumnColor11[index]" v-show="index>0"></span>
+                            </template>
+                             <template slot-scope="{row,index}" slot="paramDou01">
+                                <span :style="index==0 ? 'color:#ECCF0C': ''">{{row.paramDou01}}%</span>
+                              </template>
+                           </Table>
+                        </div>
+                      </Col>
+                    </Row>
+                  </div>
+               </Col>
+            </Row>
+            <Row :gutter="16" class-name="report-echarts-row">
+                <Col :span="24">
+                  <div class="report-echarts-main no-truncation">
+                    <div class="echarts-title">12. 分规则数据质量分析 - 及时性(数据入库)</div>
+                    <div class="echarts-sub-title">数据入库及时性检测异常,按来源应用区分数据如下:</div>
+                    <Row :gutter="16" align="middle">
+                      <Col :span="8">
+                        <div id="pie12" class="echart-detail"></div>
+                      </Col>
+                      <Col :span="16">
+                        <div class="report-echarts-table report-echarts-right-table">
+                          <Table :columns="columnsRule" :data="tableData12" class="common-table report-table-detail" no-data-text="" :row-class-name="rowClassName">
+                             <template slot-scope="{ index }" slot="xAxis">
+                              <span class="table-legend" :style="'background:'+tableColumnColor12[index]" v-show="index>0"></span>
+                            </template>
+                             <template slot-scope="{row,index}" slot="paramDou01">
+                                <span :style="index==0 ? 'color:#ECCF0C': ''">{{row.paramDou01}}%</span>
+                              </template>
+                           </Table>
+                        </div>
+                      </Col>
+                    </Row>
+                  </div>
+               </Col>
+            </Row>
+          </div>
+        </div>
+         <div class="report-section">
+          <div class="title-content no-truncation">
+            <div class="title-line">
+              <span></span>数据质量排名统计
+            </div>
+          </div>
+          <div class="report-echarts">
+           <Row :gutter="16" class-name="report-echarts-row">
+                <Col :span="24">
+                  <div class="report-echarts-main no-truncation">
+                    <div class="echarts-title">13. 异常数来源 - 应用排名 TOP10</div>
+                    <div class="echarts-sub-title">数据质量检查错数按来源应用排名如下:</div>
+                    <Row :gutter="16">
+                      <Col :span="24">
+                        <div id="bar13" class="echart-detail"></div>
+                        <div class="report-echarts-table">
+                          <Table :columns="columnsQuality" :data="tableData13" class="common-table report-table-detail" no-data-text="" :row-class-name="rowClassName">
+                            <template slot-scope="{row,index}" slot="paramDou01">
+                              <span :style="index==0 ? 'color:#5EB6FC': ''">{{row.paramDou01+'%'}}</span>
+                            </template>
+                            <template slot-scope="{row,index}" slot="paramDou02">
+                              <span :style="index==0 ? 'color:#5EB6FC': ''">{{row.paramDou02+'%'}}</span>
+                            </template>
+                          </Table>
+                        </div>
+                      </Col>
+                    </Row>
+                  </div>
+               </Col>
+            </Row>
+            <Row :gutter="16" class-name="report-echarts-row">
+                <Col :span="24">
+                  <div class="report-echarts-main no-truncation">
+                    <div class="echarts-title">14. 异常数来源 - 质量规则 TOP10</div>
+                    <div class="echarts-sub-title">数据质量检查错数按规则排名如下:</div>
+                    <Row :gutter="16">
+                      <Col :span="24">
+                        <div id="bar14" class="echart-detail"></div>
+                         <div class="report-echarts-table">
+                          <Table :columns="columnsException" :data="tableData14" class="common-table report-table-detail" no-data-text="" :row-class-name="rowClassName">
+                            <template slot-scope="{row,index}" slot="paramDou01">
+                              <span :style="index==0 ? 'color:#5EB6FC': ''">{{row.paramDou01+'%'}}</span>
+                            </template>
+                            <template slot-scope="{row,index}" slot="paramDou02">
+                              <span :style="index==0 ? 'color:#5EB6FC': ''">{{row.paramDou02+'%'}}</span>
+                            </template>
+                          </Table>
+                        </div>
+                      </Col>
+                    </Row>
+                  </div>
+               </Col>
+            </Row>
+          </div>
+        </div>
+         <div class="report-section">
+          <div class="title-content no-truncation">
+            <div class="title-line">
+              <div class="num-title">
+                <span></span>规则配置状况
+              </div>
+            </div>
+          </div>
+          <div class="report-echarts">
+            <Row :gutter="16" class-name="report-echarts-row">
+                <Col :span="24">
+                  <div class="report-echarts-main no-truncation">
+                    <div class="echarts-title">15.规则配置状况</div>
+                    <div class="echarts-sub-title">规则配置数量级及占比</div>
+                    <Row :gutter="16" align="middle">
+                      <Col :span="8">
+                        <div id="pie15" class="echart-detail"></div>
+                      </Col>
+                      <Col :span="16">
+                        <div class="report-echarts-table report-echarts-right-table">
+                           <Table :columns="columnsConfig" :data="tableData15" class="common-table report-table-detail" no-data-text="" :row-class-name="rowClassName">
+                             <template slot-scope="{ index }" slot="xAxis">
+                              <span class="table-legend" :style="'background:'+tableColumnColor15[index]" v-show="index>0"></span>
+                            </template>
+                            <template slot-scope="{row,index}" slot="paramDou05">
+                              <span :style="index==0 ? 'color:#5EB6FC': ''">{{row.paramDou05+'%'}}</span>
+                            </template>
+                            <template slot-scope="{row}" slot="paramDou04">
+                              <Icon type="md-arrow-up" style="color: #09CB09;font-size:20px" v-show="row.paramDou04>0"/>
+                              <Icon type="md-arrow-down" style="color: #F32F2F;font-size:20px" v-show="row.paramDou04<0" />
+                              {{Math.abs(row.paramDou04)+'%'}}
+                            </template>
+                          </Table>
+                        </div>
+                      </Col>
+                    </Row>
+                  </div>
+               </Col>
+            </Row>
+          </div>
+        </div>
+      </div>
+      </div>
+    </div>
+  </div>
+</template>
+<script>
+import * as echarts from "echarts"
+import html2canvas from 'html2canvas';
+import JsPDF from 'jspdf'
+export default {
+  name: "DownQualityReport",
+  data() {
+    return {
+        scroll: '',
+        navList: ['综合数据质量分析', '数据异常分析', '分规则数据质量分析', '数据质量排名统计', '规则配置状况'],
+        currentIndex:0,
+        listBoxState: true,//点击导航栏时,暂时停止监听页面滚动
+        queryParams: {reportClassName:'',beginDate:'',endDate: ''},
+        columns4: [
+           {
+            title: '来源应用',
+            key: 'xAxis',
+            align: 'center',
+            ellipsis: true,
+            tooltip: true
+          },
+          {
+            title: '记录总数',
+            key: 'paramNum01',
+            align: 'center',
+            ellipsis: true,
+            tooltip: true
+          },
+          {
+            title: '本期质量',
+            slot: 'paramDou01',
+            align: 'center',
+          },
+          {
+            title: '上期质量',
+            slot: 'paramDou02',
+            align: 'center',
+          },
+          {
+            title: '趋势',
+            slot: 'paramDou04',
+            align: 'center',
+          },
+        ],
+        columns5: [
+           {
+            title: '来源应用',
+            key: 'xAxis',
+            align: 'center',
+            ellipsis: true,
+            tooltip: true
+          },
+          {
+            title: '记录总数',
+            key: 'paramLong01',
+            align: 'center',
+            ellipsis: true,
+            tooltip: true
+          },
+          {
+            title: '本期质量',
+            slot: 'paramDou01',
+            align: 'center',
+          },
+          {
+            title: '上期质量',
+            slot: 'paramDou02',
+            align: 'center',
+          },
+          {
+            title: '趋势',
+            slot: 'paramDou04',
+            align: 'center',
+          },
+        ],
+        tableData4: [],
+        tableData5: [],
+        tableData6: [],
+        tableData7: [],
+        tableData8: [],
+        tableData9: [],
+        tableData10: [],
+        tableData11: [],
+        tableData12: [],
+        tableData13: [],
+        tableData14: [],
+        tableData15: [],
+        columnsRule: [
+          {
+            title: '图例颜色',
+            slot: 'xAxis',
+            align: 'right',
+            width: 70,
+            className: 'table-legend-list',
+          },
+          {
+            title: '来源应用',
+            key: 'xAxis',
+            align: 'center',
+            ellipsis: true,
+            tooltip: true
+          },
+          {
+            title: '记录总数',
+            key: 'paramNum01',
+            align: 'center',
+            ellipsis: true,
+            tooltip: true
+          },
+          {
+            title: '异常总数',
+            key: 'paramNum02',
+            align: 'center',
+            ellipsis: true,
+            tooltip: true
+          },
+          {
+            title: '异常占比',
+            slot: 'paramDou01',
+            align: 'center',
+          }
+        ],
+        columnsQuality: [
+        {
+          title: '来源应用',
+          key: 'xAxis',
+          align: 'center',
+          ellipsis: true,
+          tooltip: true
+        },
+        {
+          title: '本期质量',
+          slot: 'paramDou01',
+          align: 'center',
+        },
+        {
+          title: '异常总数',
+          key: 'paramLong02',
+          align: 'center',
+          ellipsis: true,
+          tooltip: true
+        },
+        {
+          title: '异常数\n总体占比',
+          slot: 'paramDou02',
+          align: 'center',
+        },
+        {
+          title: '准确性策略\n异常总数',
+          key: 'paramNum01',
+          align: 'center',
+          ellipsis: true,
+          tooltip: true
+        },
+        {
+          title: '一致性策略\n异常总数',
+          key: 'paramNum02',
+          align: 'center',
+          ellipsis: true,
+          tooltip: true
+        },
+        {
+          title: '完整性策略\n异常总数',
+          key: 'paramNum03',
+          align: 'center',
+          ellipsis: true,
+          tooltip: true
+        },
+        {
+          title: '及时性\n(数据采集)异常',
+          key: 'paramNum04',
+          align: 'center',
+          ellipsis: true,
+          tooltip: true
+        },{
+          title: '及时性\n(数据入库)异常',
+          key: 'paramNum05',
+          align: 'center',
+          ellipsis: true,
+          tooltip: true
+        }],
+        columnsException: [
+          {
+          title: '来源规则名称',
+          key: 'xAxis',
+          align: 'center',
+          ellipsis: true,
+          tooltip: true
+        },
+        {
+          title: '记录总数',
+          key: 'paramLong01',
+          align: 'center',
+          ellipsis: true,
+          tooltip: true
+        },
+        {
+          title: '异常总数',
+          key: 'paramNum01',
+          align: 'center',
+          ellipsis: true,
+          tooltip: true
+        },
+        {
+          title: '本期质量',
+          slot: 'paramDou01',
+          align: 'center',
+        },
+        {
+          title: '异常数\n总体占比', // iview的table表头文字换行需要\n和.ivu-table-cell {white-space: pre;}
+          slot: 'paramDou02',
+          align: 'center',
+        },
+        ],
+        columnsConfig: [
+          {
+            title: '图例颜色',
+            slot: 'xAxis',
+            align: 'right',
+            width: 70,
+            className: 'table-legend-list',
+          },
+         {
+            title: '规则类型',
+            key: 'xAxis',
+            align: 'center',
+            ellipsis: true,
+            tooltip: true
+          },
+          {
+            title: '数量',
+            key: 'paramNum01',
+            align: 'center',
+            ellipsis: true,
+            tooltip: true
+          },
+          {
+            title: '占比',
+            slot: 'paramDou05',
+            align: 'center',
+          },
+          {
+            title: '趋势',
+            slot: 'paramDou04',
+            align: 'center',
+          },
+       ],
+        pieColumnColor6: ['#58D9F9','#4992FF','#7CFFB2','#FF6E76','#FDDD60','#646AD9'],
+        tableColumnColor6: ['','#58D9F9','#4992FF','#7CFFB2','#FF6E76','#FDDD60'],
+        pieColumnColor7: ['#646AD9','#FDDD60','#FF6E76','#7CFFB2','#4992FF','#58D9F9'],
+        tableColumnColor7: ['','#646AD9','#FDDD60','#FF6E76','#7CFFB2','#4992FF'],
+        pieColumnColor8: ['#FDDD60','#FF6E76','#7CFFB2','#4992FF','#58D9F9','#646AD9'],
+        tableColumnColor8: ['','#FDDD60','#FF6E76','#7CFFB2','#4992FF','#58D9F9'],
+        pieColumnColor9: ['#FF6E76','#7CFFB2','#4992FF','#58D9F9','#646AD9','#FDDD60'],
+        tableColumnColor9: ['','#FF6E76','#7CFFB2','#4992FF','#58D9F9','#646AD9'],
+        pieColumnColor10: ['#7CFFB2','#4992FF','#58D9F9','#646AD9','#FDDD60','#FF6E76'],
+        tableColumnColor10: ['','#7CFFB2','#4992FF','#58D9F9','#646AD9','#FDDD60'],
+        pieColumnColor11: ['#4992FF','#58D9F9','#646AD9','#FDDD60','#FF6E76','#7CFFB2'],
+        tableColumnColor11: ['','#4992FF','#58D9F9','#646AD9','#FDDD60','#FF6E76'],
+        pieColumnColor12: ['#4992FF','#7CFFB2','#FF6E76','#FDDD60','#646AD9','#58D9F9'],
+        tableColumnColor12: ['','#4992FF','#7CFFB2','#FF6E76','#FDDD60','#646AD9'],
+        pieColumnColor15: ['#FF6E76','#646AD9','#FDDD60','#7CFFB2','#4992FF','#58D9F9'],
+        tableColumnColor15: ['','#FF6E76','#646AD9','#FDDD60','#7CFFB2','#4992FF'],
+       downloadStatus: false,
+    };
+  },
+  watch: {
+      scroll: function () {
+        this.loadSroll()
+      },
+    },
+  created () {
+    if (this.$route.query.reportClassName) {
+      this.queryParams = this.$route.query
+      let parmasObj = {
+        beginDate: this.queryParams.beginDate,
+        endDate: this.queryParams.endDate
+      }
+      this.downloadStatus = false
+      // this.getEchartData(parmasObj)
+      this.getData(parmasObj)
+    }
+  },
+  mounted() {
+    //vue通过window.addEventListener('scroll', XXXX)无法监听屏幕滚动事件,上一个页面可以,换了一个页面,却不行了,后来百度,往后面加了一个true
+    window.addEventListener('scroll', this.dataScroll,true)
+  },
+  methods: {
+    // js 节流浏览器性能优化
+    dataScroll: function () {                           
+      this.scroll = document.documentElement.scrollTop || document.body.scrollTop;
+      // if (this.scroll >= 400) { //滚动条滚动的距离大于等于400时,显示BackTop组件
+      //   this.$refs.BackTop.backTop = true
+      // } else {
+      //   this.$refs.BackTop.backTop = false
+      // }
+    },
+    jump(index) {
+    let jump = document.getElementsByClassName('report-section');
+    // 获取需要滚动的距离
+    let total = jump[index].offsetTop;
+    // Chrome
+    document.body.scrollTop  = total;
+    // Firefox
+    document.documentElement.scrollTop = total;
+    // Safari
+    window.pageYOffset = total;
+    this.currentIndex = index
+    this.listBoxState = false
+    let timeId;
+    clearTimeout(timeId);
+    timeId = setTimeout(() => {
+      this.listBoxState = true
+    },100)
+    // $('html, body').animate({
+    // 'scrollheader': total
+    // }, 400);
+    },
+    loadSroll: function () {
+      var self = this;
+      var sections = document.getElementsByClassName('report-section');
+      if (this.listBoxState) {
+        for (var i = sections.length - 1; i >= 0; i--) {
+          if (self.scroll >= sections[i].offsetTop-100) {
+            this.currentIndex = i
+            break;
+          }
+        }
+      } 
+    },
+    rowClassName(row, index) {
+        if (index % 2 == 0) {
+          return "ivu-table-stripe-even";
+        } else {
+          return "ivu-table-stripe-odd";
+        }
+      },
+    creatGauge(gaugeData) {
+      let myChart = echarts.init(document.getElementById(gaugeData.id))
+      let option = {
+        series: [
+          {
+            type: 'gauge',
+            center: ['50%', '68%'],
+            radius:'90%',
+            startAngle: 200,
+            endAngle: -20,
+            min: 0,
+            max: 100,
+            splitNumber: 10,
+            itemStyle: {
+              color: '#FFAB91'
+            },
+            progress: {
+              show: true,
+              width: 15
+            },
+            pointer: {
+              show: false
+            },
+            axisLine: {
+              lineStyle: {
+                color:[[1, '#284677']],
+                width: 15
+              }
+            },
+            axisTick: {
+              distance: -35,
+              splitNumber: 5,
+              lineStyle: {
+                width: 2,
+                color: '#4D5F7D'
+              }
+            },
+            splitLine: {
+              distance: -52,
+              length: 14,
+              lineStyle: {
+                width: 3,
+                color: '#4D5F7D'
+              }
+            },
+            axisLabel: {
+              distance: -20,
+              color: '#5D6B82',
+              fontSize: 12
+            },
+            anchor: {
+              show: false
+            },
+            title: {
+              show: false
+            },
+            detail: {
+              valueAnimation: true,
+              width: '60%',
+              lineHeight: 40,
+              borderRadius: 8,
+              offsetCenter: [0, '-15%'],
+              fontSize: 30,
+              fontWeight: 'bolder',
+              formatter: '{value} %',
+              color: 'auto'
+            },
+            data: [
+              {
+                value: gaugeData.scores
+              }
+            ]
+          },
+          {
+            type: 'gauge',
+            center: ['50%', '68%'],
+            radius:'90%',
+            startAngle: 200,
+            endAngle: -20,
+            min: 0,
+            max: 100,
+            itemStyle: {
+              color: '#FD6636'
+            },
+            progress: {
+              show: true,
+              width: 5
+            },
+            pointer: {
+              show: false
+            },
+            axisLine: {
+              show: false
+            },
+            axisTick: {
+              show: false
+            },
+            splitLine: {
+              show: false
+            },
+            axisLabel: {
+              show: false
+            },
+            detail: {
+              show: false
+            },
+            data: [
+              {
+                value: gaugeData.scores
+              }
+            ]
+          }
+        ]
+      }
+      myChart.resize()
+      myChart.clear()
+      myChart.setOption(option)
+      window.addEventListener("resize", function() {
+        myChart.resize()
+      })
+    },
+    //雷达图显示文字
+    contains(arr, val) {
+      var i = arr.length;
+      while (i--) {
+          if (arr[i].name === val) {
+              return i;
+          }
+      }
+      return false;
+    },
+    creatSolidRadar (SolidRadarData) {
+        if (echarts.init(document.getElementById(SolidRadarData.id))) {
+          let  myChart = echarts.init(document.getElementById(SolidRadarData.id));
+          myChart.clear()
+          const createSvg = ({width, height, shadowColor, shadowBlur, points}) => {
+              const ret = [`M${points[0][0]} ${points[0][1]}`];
+              for (let i = 1; i < points.length; i++) {
+                  ret.push(`L${points[i][0]} ${points[i][1]}`);
+              }
+              ret.push('Z');
+              const rectPath = ret.join(' ');
+              return (`
+                  <svg version="1.1" xmlns="http://www.w3.org/2000/svg" 
+                      x="0px" y="0px" 
+                      width="${width}"
+                      height="${height}"
+                  >
+                      <style>
+                          .st1 {
+                              fill: transparent;
+                              stroke: ${shadowColor};
+                              stroke-width: ${shadowBlur}px;
+                              filter: url(#chart-inset-shadow);
+                              clip-path: url(#chart-clip);
+                          }
+
+                      </style>
+                      <defs>
+                      
+                          <clipPath id="chart-clip">
+                              <path d="${rectPath}" />
+                          </clipPath>
+                          
+                          <filter id="chart-inset-shadow" width="200%" height="200%" x="-50%" y="-50%">
+                              <feGaussianBlur in="SourceGraphic" result="gass" stdDeviation="${shadowBlur * 0.75}" />
+                              <feMerge>
+                                  <feMergeNode in="gass" />
+                              </feMerge>
+                          </filter>
+
+                      </defs>
+                      <g>
+                          <path class="st1" d="${rectPath}" />
+                      </g>
+                  </svg>
+              `);        
+            };
+          const cretateSvgUrl = (svgOption) => {
+              const svgString = createSvg(svgOption);
+              const svg = new Blob([svgString], {type: "image/svg+xml;charset=utf-8"});              
+              const DOMURL = window.URL || window.webkitURL || window;
+              const insetShadowUrl = DOMURL.createObjectURL(svg);               
+              return insetShadowUrl;
+          };
+          const dataSet = [], nameArr  = []
+          SolidRadarData.category[0].forEach((item,index)=> {
+           nameArr.push(item.name)
+          })
+          dataSet[0] = nameArr
+          dataSet[1] = [100,100,100,100,100]
+          dataSet[2] = SolidRadarData.data[0].value
+          const maxValue = [...dataSet[1], ...dataSet[2]].reduce((m, v) => Math.max(m, v), -Infinity);
+          const radius = 0.8;
+          const theta = Math.PI * 2 / dataSet[2].length
+          const getPoints = (R, ps, max) => ps.map((v, i) => {
+              const t = i * theta;
+              const d = v / max;
+              const x = R - Math.sin(t) * R * d;    
+              const y = R - Math.cos(t) * R * d;
+              return [x, y];
+          });
+          // let i = -1;
+          let option = {
+              polar: {
+                  radius: radius * 100 + '%',
+                  // center: ['50%', '58%'],
+                  center: ['50%', '50%'],
+              },
+              angleAxis: {
+                  type: 'category',
+                  clockwise: false,
+                  boundaryGap: false,
+                  splitLine: {
+                      show: false,
+                  },
+                  axisLine: {
+                      show: false
+                  }
+              },
+              radiusAxis: {
+                  type: 'value',
+                  min: 0,
+                  max: 100,
+                  splitLine: {
+                      show: false,
+                  },
+                  axisTick: {
+                      show: false,
+                  },
+                  axisLabel: {
+                      show: false,
+                      color:'#fff',
+                      formatter: '{value} %'
+                  },
+              },
+              radar: {
+                  indicator: SolidRadarData.category[0],
+                  radius: radius * 100 + '%',
+                  center: ['50%', '50%'],
+                  shape: 'polygon',
+                  splitNumber: 5,
+                  // nameGap : 1,
+                  name: {
+                    // rich: {
+                    //   a: {
+                    //       color: '#fff',
+                    //       lineHeight: 20,
+                    //   },
+                    //   b: {
+                    //       color: '#fff',
+                    //       align: 'center',
+                    //       padding: 2,
+                    //       borderRadius: 4
+                    //    }
+                    //   },
+                    //   formatter: (value)=>{
+                    //     let i = this.contains(SolidRadarData.category[0], value); // 处理对应要显示的样式
+                    //     return `{a|${value}}{b|${dataSet[2][i]}%}`
+                    //   },
+                      textStyle: {
+                          color: '#fff',
+                          fontSize: 12,
+                          padding: [-10, -10]
+                      }
+                  },
+                  splitArea: {
+                      areaStyle: {
+                          color: [
+                              'rgba(8,20,58,0.1)',
+                              'rgba(,20,58,0.03)',
+                              'rgba(,20,58,0.1)',
+                              'rgba(,20,58,0.03)',
+                          ]
+                      }
+                  },
+                  splitLine: {
+                      lineStyle: {
+                          color: [
+                              '#2A3A6E', '#2A3A6E',
+                              '#2A3A6E', '#2A3A6E',
+                              '#2A3A6E'
+                          ].reverse(),
+                          width: 3
+                      }
+                  },
+                  axisLine: {
+                      lineStyle: {
+                          color: '#264474'
+                      }
+                  }
+              },
+              animationDuration: 3000,
+              series: [
+                  {
+                      type: 'custom',
+                      name: 's1-inset-shadow',
+                      silent: true,
+                      coordinateSystem : 'polar', 
+                      // data: [0],
+                      renderItem: (params,api) => {
+                          const R = params.coordSys.r;
+                          const cx = params.coordSys.cx;
+                          const cy = params.coordSys.cy;
+                          const x = cx - R;
+                          const y = cy - R;
+                          const width = 2 * R;
+                          const height = 2 * R;                         
+                          return {
+                              type: 'image',
+                              style: {
+                                  image: cretateSvgUrl({
+                                      width, height,
+                                      shadowColor: '#00A0E9',
+                                      shadowBlur: 6, 
+                                      points: getPoints(R, dataSet[1], 100)
+                                  }),
+                                  x,
+                                  y,
+                                  width, 
+                                  height,
+                              },
+                          };
+                      },
+                  },
+                  {
+                      name: 's2',
+                      type: 'radar',
+                      data: [
+                          { value: dataSet[2] }
+                      ],
+                      // symbol: 'none',
+                      label: {
+                          show: true,
+                          formatter: function(params) {
+                              return params.value + '%';
+                          },
+                          color: '#fff',
+                          position: [-10, -10],
+                          // align: 'left',
+                          // distance: -25,
+                          
+                      },
+                      symbolSize: [6, 6],
+                      itemStyle: {
+                          shadowColor: 'rgba(0, 0, 0, 0.5)',
+                          shadowBlur: 20,
+                          normal: {
+                              color: 'rgba(87,201,255,0.8)',
+                              borderColor: 'rgba(87,201,255,0.2)',
+                              borderWidth: 12,
+                              
+                          }
+                      },
+                      areaStyle: {
+                          normal: {
+                              color: '#383F2F',
+                          }
+                      },
+                      lineStyle: {
+                          normal: {
+                              color: '#FAEC05',
+                              width: 2,
+                              
+                          }
+                      },
+                      z: 3,
+                  },
+              ]
+          };
+          myChart.resize()
+          myChart.setOption(option)
+          window.addEventListener("resize", function () {
+              myChart.resize()  
+            })
+        }
+    },
+    creatLine (lineData) {
+      let toplinechart = echarts.init(document.getElementById(lineData.id));
+      let seriesData = _.map(lineData.data, (item,index)=>({
+          name: lineData.legend[index], type: 'line', symbol: 'circle', symbolSize: 2,smooth: true, // 平滑曲线
+          lineStyle: { normal: { color: lineData.lineColor[index], width: 2 } },
+          itemStyle: { normal: { color: lineData.lineColor[index], borderColor: lineData.lineColor[index], borderWidth: 2 },
+          emphasis: { color: '#fff' }
+        },
+        areaStyle: { opacity:0.4,color: new echarts.graphic.LinearGradient(0, 0, 0, 1, [{ offset: 0.3, color: lineData.lineColor[index]}, { offset: 1, color: 'rgba(0,0,0,0)' }])},
+        data: item
+      }))
+      let toplineoption = {
+        // title: {
+        //   text: '单位:'+lineData.unit,
+        //   top: '5%',
+        //   right: 10,
+        //   textStyle: {
+        //     color: '#666666',
+        //     fontSize: 14
+        //   }
+        // },
+        legend: {
+          top: '5%', left: 'center', itemWidth: 10, itemHeight: 10, itemGap: 25,
+          textStyle: { color: '#fff', fontSize: 12 },
+          data: lineData.legend
+        },
+        tooltip: { trigger: "axis",
+          confine: true,
+          backgroundColor: '#011235',
+          borderWidth: 0,
+          extraCssText: 'opacity:0.8',
+          textStyle: {
+            color: '#fff'
+          },
+        formatter: function (params) {
+          let res = ''
+          params.forEach((item,i) => {
+            res += '<div style="display: flex;align-items:center;justify-content:space-between"><span>'+ item.marker + item.seriesName + ':</span><span>' +  item.value + lineData.unit+'</span></div> '
+          })
+          return params[0].name + res
+        }
+        },
+        grid: {
+          top: '18%', 
+          left: "4%",
+          right: "4%",
+          bottom: "4%",
+          containLabel: true
+        },
+        xAxis: [{
+          type: 'category',
+          data: lineData.category,
+          boundaryGap: false,
+          axisLine: {
+            lineStyle: {
+              color: '#00479D',
+              width: 1
+            }
+          },
+          axisLabel: {
+            color: '#fff',
+          },
+          axisTick: {
+            alignWithLabel: true
+          }
+        }],
+        yAxis: [{
+          type: 'value',
+          axisLine: {
+            show: true,
+            lineStyle: {
+              color: '#00479D',
+              width: 1
+            }
+          },
+          axisTick: {
+            show: true
+          },
+          splitLine: {
+            show: true,
+            lineStyle: {
+              type: "solid",
+              width: 1,
+              color: "#153068"
+            }
+          },
+          axisLabel: {
+            show: true,
+            color: '#fff'
+          }
+        }],
+        series: seriesData
+      }
+      toplinechart.resize()
+      toplinechart.clear()
+      toplinechart.setOption(toplineoption)
+      window.addEventListener("resize", function () { toplinechart.resize() })
+    },
+    creatBar(botmLeftBarData) {
+			let botmLeftChart = echarts.init(document.getElementById(botmLeftBarData.id))
+      let barseries = []
+      for (var i = 0; i < botmLeftBarData.legend.length; i++) {
+        let itemStyle = {}
+        if (botmLeftBarData.showStack) {
+          itemStyle = {
+            normal: {
+              color:botmLeftBarData.color[i]
+            }
+          }
+        } else {
+          itemStyle = {
+            normal: {
+              color: {
+                type: 'linear',
+                x: 0,
+                y: 0,
+                x2: 0,
+                y2: 1,
+                colorStops: [{
+                  offset: 0,
+                  color: botmLeftBarData.color[i][0]
+                }, {
+                  offset: 1,
+                  color: botmLeftBarData.color[i][1]
+                }],
+                globalCoord: false // 缺省为 false
+              },
+            }
+          }
+        }
+        barseries.push({
+          name: botmLeftBarData.legend[i],
+          type: 'bar',
+          stack: botmLeftBarData.showStack ? 'total' : false,
+          barMaxWidth: 28,
+          itemStyle: itemStyle,
+          data: botmLeftBarData.data[i]
+        })
+      }
+      let botmLeftOption = {
+        tooltip: {
+          trigger: botmLeftBarData.legend.length==1 ? 'item' : 'axis',
+          axisPointer: { type: 'shadow' },
+          confine: true,
+          backgroundColor: '#011235',
+          borderWidth: 0,
+          extraCssText: 'opacity:0.8',
+          textStyle: {
+            color: '#fff'
+          },
+          formatter: function(params) {
+            if (Array.isArray(params)) {
+             let res = ''
+              params.forEach((item,i) => {
+                res += '<div style="display: flex;align-items:center;justify-content:space-between"><span>'+ item.marker + item.seriesName + ':</span><span>' +  item.value + botmLeftBarData.unit+'</span></div> '
+              })
+              return params[0].name + res
+            } else {
+              return params.marker + params.name+':'+ params.value + botmLeftBarData.unit
+            }
+          }
+        },
+        legend: {
+          show: botmLeftBarData.legend.length>1 ? true : false,
+          orient: 'horizontal', left: 'center', top: 2, itemWidth: 10, itemHeight: 10,
+          textStyle: { color: '#ffffff', fontSize: 12 },
+          data: botmLeftBarData.legend
+        },
+        grid: {
+          top: '14%',
+          left: "4%",
+          right: "8%",
+          bottom: "2%",
+          containLabel: true
+        },
+        xAxis: [{
+          type: 'category',
+          axisLine: {
+            show: true,
+            lineStyle: {
+              color: '#00479D'
+            }
+          },
+          axisLabel: {
+            textStyle: {
+              color: '#ffffff',
+              fontSize: 12
+            },
+          },
+          axisTick: {
+            alignWithLabel: true
+          },
+          data: botmLeftBarData.category
+        }],
+        yAxis: [{
+          type: 'value',
+          splitLine: {
+            show: true,
+            lineStyle: {
+              type: "solid",
+              width: 1,
+              color: "#153068"
+            }
+          },
+          axisLine: {
+            show: true,
+            lineStyle: {
+              color: '#00479D',
+              width: 1
+            }
+          },
+          axisLabel: {
+            textStyle: {
+              color: '#ffffff',
+              fontSize: 12
+            }
+          },
+          axisTick: {
+            show: true
+          },
+        }],
+        series: barseries
+      }
+      botmLeftChart.resize()
+      botmLeftChart.clear()
+      botmLeftChart.setOption(botmLeftOption)
+      window.addEventListener("resize", function() {
+        botmLeftChart.resize()
+      })
+		},
+    creatPie(pieData) {
+      let sum = pieData.data.reduce((prev, current) => prev + current.value, 0) // 数组求和
+      pieData.data.forEach((item)=> {
+        if (item.name == '其他') {
+          item.labelLine = {
+            lineStyle: {
+              color: pieData.color[pieData.color.length-1]
+            }
+          }
+        } else {
+           item.labelLine = {
+            lineStyle: {
+              color: 'transparent'
+            }
+          }
+        }
+      })
+      let myChart = echarts.init(document.getElementById(pieData.id))
+      let option = {
+        title: {
+          text: '{a|' + sum + '}{c|条}',
+          x: 'center',
+          y: 'center',
+          textStyle: {
+            rich: {
+              a: {
+                padding: [10, 0],
+                color: '#1EAFF5',
+                fontSize: 20,
+                align: 'center',
+                fontWeight: 'bold'
+              },
+              c: {
+                color: "#fff",
+                fontSize: 12, 
+              }
+            }
+          },
+        },
+        // legend: {
+        //   orient: "horizontal",
+        //   top: '4%',
+        //   x: "center",
+        //   itemWidth: 10,
+        //   itemHeight: 10,
+        //   textStyle: {
+        //     color: "#ffffff",
+        //     fontSize: 12
+        //   },
+        //   data: pieData.legend
+        // },
+        tooltip: {
+          trigger: "item",
+          labelLine: false,
+          confine: true,
+          backgroundColor: '#011235',
+          borderWidth: 0,
+          extraCssText: 'opacity:0.8',
+          textStyle: {
+            color: '#fff'
+          },
+          formatter: function(params) {
+            return params.name + ':' + params.percent + '% (' + params.value + pieData.unit + ')'
+          }
+        },
+        series: [{
+          color: pieData.color,
+          type: 'pie',
+          radius: ['50%', '70%'],
+          center: ['50%', '50%'],
+          label: {
+              position: 'outer',
+              alignTo: 'none',
+              bleedMargin: 0,
+              color: '#FFFFFF',
+              fontSize: 12,
+              formatter: function(params) {
+                if (params.data.name == '其他') {
+                  return params.name + ':' + params.percent + '% (' + params.value + pieData.unit + ')'
+                } else {
+                  return ''
+                }
+              }
+            },
+          data: pieData.data,
+        }, ]
+      };
+      myChart.resize();
+      myChart.clear();
+      myChart.setOption(option);
+      window.addEventListener("resize", function() {
+        myChart.resize();
+      })
+    },
+    getEchartData (params) {
+      this.$get('metroapi/dataQuality/report/comScores',params).then(res => {
+        if (res.httpCode == 1) {
+          let obj = res.data
+          obj.id = 'guage'
+          this.$nextTick(() => this.creatGauge(obj))
+        }
+      })
+      this.$get('metroapi/dataQuality/report/difDimScores',params).then(res => {
+        if (res.httpCode == 1) {
+          let obj2 = res.data
+          obj2.id = 'radar'
+          this.$nextTick(() => this.creatSolidRadar(obj2))
+        }
+      })
+      this.$get('metroapi/dataQuality/report/comScoresTrend',params).then(res => {
+        if (res.httpCode == 1) {
+          let obj3 = res.data
+          obj3.id = 'line3'
+          obj3.unit = '%'
+          obj3.lineColor = ['#31A4FD', '#86BE73']
+          this.$nextTick(() => this.creatLine(obj3))
+        }
+      })
+      this.$get('metroapi/dataQuality/report/comScores/appType/bar',params).then(res => {
+        if (res.httpCode == 1) {
+          let obj4 = res.data
+          obj4.id = 'bar4'
+          obj4.unit = '%'
+          obj4.color = [['#0874E2','#62BAFD'], ['#86BE73', '#42A76D']]
+          this.$nextTick(() => this.creatBar(obj4))
+        }
+      })
+      this.$get('metroapi/dataQuality/report/comScores/appType/list',params).then(res => {
+        if (res.httpCode == 1) {
+          this.tableData4 = res[4].data.data
+          this.tableData4.forEach((item,index)=> {
+            if (index == 0) {
+              item.cellClassName = {
+                paramNum01: 'total-records-table-cell',
+                paramDou01: 'quality-table-cell',
+                paramDou02: 'quality-table-cell',
+              }
+            }
+          })
+        }
+      })
+      this.$get('metroapi/dataQuality/report/comScores/model/bar',params).then(res => {
+        if (res.httpCode == 1) {
+          let obj5 = res.data
+          obj5.id = 'bar5'
+          obj5.unit = '%'
+          obj5.color = [['#0874E2','#62BAFD'], ['#86BE73', '#42A76D']]
+          this.$nextTick(() => this.creatBar(obj5))
+        }
+      })
+     
+    },
+    downReport(row) {
+      this.downloadStatus = true
+      this.queryParams = row
+      let paramsObj = {
+        beginDate: row.beginDate,
+        endDate: row.endDate
+      }
+      this.getData(paramsObj)
+    },
+    async getEchartData1(url,params) { //async 函数返回的是一个 Promise 对象,所以在最外层不能用 await 获取其返回值的情况下,我们当然应该用原来的方式:then() 链来处理这个 Promise 对象
+      let rtnData 
+      await this.$get( url, params).then(res=>{ //await让被调用的函数都完成后并返回结果 (await只在 async 函数中有效)
+        rtnData = res         
+      })
+      return rtnData
+    },
+    getData(params){
+      let interface1 = this.getEchartData1('metroapi/dataQuality/report/comScores',params)
+      let interface2 = this.getEchartData1('metroapi/dataQuality/report/difDimScores',params)
+      let interface3 = this.getEchartData1('metroapi/dataQuality/report/comScoresTrend',params)
+      let interface4 = this.getEchartData1('metroapi/dataQuality/report/comScores/appType/bar',params)
+      let interfaceTable4 = this.getEchartData1('metroapi/dataQuality/report/comScores/appType/list',params)
+      let interface5 = this.getEchartData1('metroapi/dataQuality/report/comScores/model/bar',params)
+      let interfaceTable5 = this.getEchartData1('metroapi/dataQuality/report/comScores/model/list',params)
+      let interface6 = this.getEchartData1('metroapi/dataQuality/report/abnDataAnalysis/appType/pie',params)
+      let interfaceTable6 = this.getEchartData1('metroapi/dataQuality/report/abnDataAnalysis/appType/list',params)
+      let interface7 = this.getEchartData1('metroapi/dataQuality/report/abnDataAnalysis/model/pie',params)
+      let interfaceTable7 = this.getEchartData1('metroapi/dataQuality/report/abnDataAnalysis/model/list',params)
+      let params8 = params
+      params8.modelType = '一致性'
+      let interface8 = this.getEchartData1('metroapi/dataQuality/report/abnDataAnalysis/appType/model/pie',params8)
+      let interfaceTable8 = this.getEchartData1('metroapi/dataQuality/report/abnDataAnalysis/appType/model/list',params8)
+      let params9 = params
+      params9.modelType = '完整性'
+      let interface9 = this.getEchartData1('metroapi/dataQuality/report/abnDataAnalysis/appType/model/pie',params9)
+      let interfaceTable9 = this.getEchartData1('metroapi/dataQuality/report/abnDataAnalysis/appType/model/list',params9)
+      let params10 = params
+      params10.modelType = '准确性'
+      let interface10 = this.getEchartData1('metroapi/dataQuality/report/abnDataAnalysis/appType/model/pie',params10)
+      let interfaceTable10 = this.getEchartData1('metroapi/dataQuality/report/abnDataAnalysis/appType/model/list',params10)
+      let params11 = params
+      params11.modelType = '及时性(数据采集)'
+      let interface11 = this.getEchartData1('metroapi/dataQuality/report/abnDataAnalysis/appType/model/pie',params11)
+      let interfaceTable11 = this.getEchartData1('metroapi/dataQuality/report/abnDataAnalysis/appType/model/list',params11)
+      let params12 = params
+      params12.modelType = '及时性(数据入库)'
+      let interface12 = this.getEchartData1('metroapi/dataQuality/report/abnDataAnalysis/appType/model/pie',params12)
+      let interfaceTable12 = this.getEchartData1('metroapi/dataQuality/report/abnDataAnalysis/appType/model/list',params12)
+      let interface13 = this.getEchartData1('metroapi/dataQuality/report/abnSource/appType/bar',params)
+      let interfaceTable13 = this.getEchartData1('metroapi/dataQuality/report/abnSource/appType/list',params)
+      let interface14 = this.getEchartData1('metroapi/dataQuality/report/abnSource/rule/bar',params)
+      let interfaceTable14 = this.getEchartData1('metroapi/dataQuality/report/abnSource/rule/list',params)
+      let interface15 = this.getEchartData1('metroapi/dataQuality/report/ruleConf/pie',params)
+      let interfaceTable15 = this.getEchartData1('metroapi/dataQuality/report/ruleConf/list',params)
+      this.$axiosAll([interface1,interface2,interface3,interface4,interfaceTable4,interface5,interfaceTable5,interface6,interfaceTable6,interface7,interfaceTable7,interface8,interfaceTable8,interface9,interfaceTable9,interface10,interfaceTable10,interface11,interfaceTable11,interface12,interfaceTable12,interface13,interfaceTable13,interface14,interfaceTable14,interface15,interfaceTable15]).then(res=> {
+        if (res[0].httpCode == 1) {
+          let obj = res[0].data
+          obj.id = 'guage'
+          this.$nextTick(() => this.creatGauge(obj))
+        }
+        if (res[1].httpCode == 1) {
+          let obj2 = res[1].data
+          obj2.id = 'radar'
+          this.$nextTick(() => this.creatSolidRadar(obj2))
+        }
+        if (res[2].httpCode == 1) {
+          let obj3 = res[2].data
+          obj3.id = 'line3'
+          obj3.unit = '%'
+          obj3.lineColor = ['#31A4FD', '#86BE73']
+          this.$nextTick(() => this.creatLine(obj3))
+        }
+        if (res[3].httpCode == 1) {
+          let obj4 = res[3].data
+          obj4.id = 'bar4'
+          obj4.unit = '%'
+          obj4.color = [['#0874E2','#62BAFD'], ['#86BE73', '#42A76D']]
+          this.$nextTick(() => this.creatBar(obj4))
+        }
+        if (res[4].httpCode == 1) {
+          this.tableData4 = res[4].data.data
+          this.tableData4.forEach((item,index)=> {
+            if (index == 0) {
+              item.cellClassName = {
+                paramNum01: 'total-records-table-cell',
+                paramDou01: 'quality-table-cell',
+                paramDou02: 'quality-table-cell',
+              }
+            }
+          })
+        }
+        if (res[5].httpCode == 1) {
+          let obj5 = res[5].data
+          obj5.id = 'bar5'
+          obj5.unit = '%'
+          obj5.color = [['#0874E2','#62BAFD'], ['#86BE73', '#42A76D']]
+          this.$nextTick(() => this.creatBar(obj5))
+        }
+        if (res[6].httpCode == 1) {
+          this.tableData5 = res[6].data.data
+          this.tableData5.forEach((item,index)=> {
+            if (index == 0) {
+              item.cellClassName = {
+                paramLong01: 'total-records-table-cell',
+                paramDou01: 'quality-table-cell',
+                paramDou02: 'quality-table-cell',
+              }
+            }
+          })
+        }
+        if (res[7].httpCode == 1) {
+          let obj6 = res[7].data
+          obj6.id = 'pie6'
+          obj6.unit = '条'
+          obj6.color = this.pieColumnColor6
+          this.$nextTick(() => this.creatPie(obj6))
+        }
+        if (res[8].httpCode == 1) {
+          this.tableData6 = res[8].data.data
+          this.tableData6.forEach((item,index)=> {
+            if (index == 0) {
+              item.cellClassName = {
+                paramNum01: 'total-records-table-cell',
+                paramNum02: 'total-exceptions-table-cell',
+              }
+            }
+          })
+        }
+        if (res[9].httpCode == 1) {
+          let obj7 = res[9].data
+          obj7.id = 'pie7'
+          obj7.unit = '条'
+          obj7.color = this.pieColumnColor7
+          this.$nextTick(() => this.creatPie(obj7))
+        }
+         if (res[10].httpCode == 1) {
+          this.tableData7 = res[10].data.data
+          this.tableData7.forEach((item,index)=> {
+            if (index == 0) {
+              item.cellClassName = {
+                paramNum01: 'total-records-table-cell',
+                paramNum02: 'total-exceptions-table-cell',
+              }
+            }
+          })
+        }
+        if (res[11].httpCode == 1) {
+          let obj8 = res[11].data
+          obj8.id = 'pie8'
+          obj8.unit = '条'
+          obj8.color = this.pieColumnColor8
+          this.$nextTick(() => this.creatPie(obj8))
+        }
+         if (res[12].httpCode == 1) {
+          this.tableData8 = res[12].data.data
+          this.tableData8.forEach((item,index)=> {
+            if (index == 0) {
+              item.cellClassName = {
+                paramNum01: 'total-records-table-cell',
+                paramNum02: 'total-exceptions-table-cell',
+              }
+            }
+          })
+        }
+        if (res[13].httpCode == 1) {
+          let obj9 = res[13].data
+          obj9.id = 'pie9'
+          obj9.unit = '条'
+          obj9.color = this.pieColumnColor9
+          this.$nextTick(() => this.creatPie(obj9))
+        }
+         if (res[14].httpCode == 1) {
+          this.tableData9 = res[14].data.data
+          this.tableData9.forEach((item,index)=> {
+            if (index == 0) {
+              item.cellClassName = {
+                paramNum01: 'total-records-table-cell',
+                paramNum02: 'total-exceptions-table-cell',
+              }
+            }
+          })
+        }
+        if (res[15].httpCode == 1) {
+          let obj10 = res[15].data
+          obj10.id = 'pie10'
+          obj10.unit = '条'
+          obj10.color = this.pieColumnColor10
+          this.$nextTick(() => this.creatPie(obj10))
+        }
+         if (res[16].httpCode == 1) {
+          this.tableData10 = res[16].data.data
+          this.tableData10.forEach((item,index)=> {
+            if (index == 0) {
+              item.cellClassName = {
+                paramNum01: 'total-records-table-cell',
+                paramNum02: 'total-exceptions-table-cell',
+              }
+            }
+          })
+        }
+        if (res[17].httpCode == 1) {
+          let obj11 = res[17].data
+          obj11.id = 'pie11'
+          obj11.unit = '条'
+          obj11.color = this.pieColumnColor11
+          this.$nextTick(() => this.creatPie(obj11))
+        }
+         if (res[18].httpCode == 1) {
+          this.tableData11 = res[18].data.data
+          this.tableData11.forEach((item,index)=> {
+            if (index == 0) {
+              item.cellClassName = {
+                paramNum01: 'total-records-table-cell',
+                paramNum02: 'total-exceptions-table-cell',
+              }
+            }
+          })
+        }
+        if (res[19].httpCode == 1) {
+          let obj12 = res[19].data
+          obj12.id = 'pie12'
+          obj12.unit = '条'
+          obj12.color = this.pieColumnColor12
+          this.$nextTick(() => this.creatPie(obj12))
+        }
+        if (res[20].httpCode == 1) {
+          this.tableData12 = res[20].data.data
+          this.tableData12.forEach((item,index)=> {
+            if (index == 0) {
+              item.cellClassName = {
+                paramNum01: 'total-records-table-cell',
+                paramNum02: 'total-exceptions-table-cell',
+              }
+            }
+          })
+        }
+        if (res[21].httpCode == 1) {
+          let obj13 = res[21].data
+          obj13.id = 'bar13'
+          obj13.unit = '条'
+          obj13.showStack = true
+          obj13.color = ['#31A4FD','#62BAFD','#646AD9', '#58D9F9','#d5affb']
+          this.$nextTick(() => this.creatBar(obj13))
+        }
+        if (res[22].httpCode == 1) {
+          this.tableData13 = res[22].data.data
+          this.tableData13.forEach((item,index)=> {
+            if (index == 0) {
+              item.cellClassName = {
+                paramNum01: 'quality-table-cell',
+                paramNum02: 'quality-table-cell',
+                paramNum03: 'quality-table-cell',
+                paramNum04: 'quality-table-cell',
+                paramNum05: 'quality-table-cell',
+                paramLong02: 'quality-table-cell',
+              }
+            }
+          })
+        }
+        if (res[23].httpCode == 1) {
+          let obj14 = res[23].data
+          obj14.id = 'bar14'
+          obj14.unit = '条'
+          obj14.legend = ['']
+          obj14.color = [['#0874E2','#62BAFD']]
+          this.$nextTick(() => this.creatBar(obj14))
+        }
+        if (res[24].httpCode == 1) {
+          this.tableData14 = res[24].data.data
+          this.tableData14.forEach((item,index)=> {
+          if (index == 0) {
+            item.cellClassName = {
+              paramLong01: 'total-records-table-cell',
+              paramNum01: 'total-exceptions-table-cell'  
+            }
+          }
+         })
+        }
+        if (res[25].httpCode == 1) {
+          let obj15 = res[25].data
+          obj15.id = 'pie15'
+          obj15.unit = '条'
+          obj15.color = this.pieColumnColor15
+          this.$nextTick(() => this.creatPie(obj15))
+        }
+         if (res[26].httpCode == 1) {
+          this.tableData15 = res[26].data.data
+          this.tableData15.forEach((item,index)=> {
+            if (index == 0) {
+              item.cellClassName = {
+                paramNum01: 'quality-table-cell',
+              }
+            }
+          })
+        }
+        this.$nextTick(()=> {
+          if (this.downloadStatus) {
+            setTimeout(() => {
+            this.downPdf()
+            }, 1000)
+          }
+        })
+      })
+    },
+    downPdf () {
+      this.$nextTick(()=> {
+        let title = this.queryParams.reportName+'-'+this.queryParams.appName
+        // 如果这个页面有左右移动,canvas 也要做响应的移动,不然会出现canvas 内容不全
+        const xOffset = window.pageXOffset
+        // 避免笔下误 灯下黑 统一写
+        const A4_WIDTH = 592.28
+        // const A4_HEIGHT = 841.89
+        const A4_HEIGHT = 841.89
+        let printDom = this.$refs.downReport
+        // 根据A4的宽高计算DOM页面一页应该对应的高度
+        let pageHeight = printDom.offsetWidth / A4_WIDTH * A4_HEIGHT
+        // 将所有不允许被截断的元素进行处理
+        let wholeNodes = document.querySelectorAll('.no-truncation') //pdf加分页防止内容截断
+        for (let i = 0; i < wholeNodes.length; i++) {
+          //1、 判断当前的不可分页元素是否在两页显示
+          const topPageNum = Math.ceil((wholeNodes[i].offsetTop) / pageHeight) // wholeNodes[i].offsetTop 它返回当前元素相对于其 offsetParent 元素的顶部内边距的距离 如果算距离对顶部的距离它的父级不能设置定位,,否则结果为0
+          const bottomPageNum = Math.ceil((wholeNodes[i].offsetTop + wholeNodes[i].offsetHeight) / pageHeight)
+          if (topPageNum !== bottomPageNum) {
+            //说明该dom会被截断
+            // 2、插入空白块使被截断元素下移
+            let divParent = wholeNodes[i].parentNode
+            let newBlock = document.createElement('div')
+            newBlock.className = 'emptyDiv'
+            newBlock.style.background = '#06214d'
+            // 3、计算插入空白块的高度 可以适当流出空间使得内容太靠边,根据自己需求而定
+            let _H = topPageNum * pageHeight - wholeNodes[i].offsetTop
+            newBlock.style.height = _H + 30 + 'px'
+            divParent.insertBefore(newBlock, wholeNodes[i])
+          }
+        }
+          // 以上完成dom层面的分页 可以转为图片进一步处理了
+          html2canvas(printDom, { height: printDom.offsetHeight, width: printDom.offsetWidth, scrollX: -xOffset,backgroundColor: "#fff",allowTaint: true ,}).then(canvas => {
+            //dom 已经转换为canvas 对象,可以将插入的空白块删除了
+            let emptyDivs = document.querySelectorAll('.emptyDiv')
+            for (let i = 0; i < emptyDivs.length; i++) {
+              emptyDivs[i].parentNode.removeChild(emptyDivs[i])
+            }
+            // 有一点重复的代码
+            let contentWidth = canvas.width
+            let contentHeight = canvas.height
+            let pageHeight = contentWidth / A4_WIDTH * A4_HEIGHT
+            let leftHeight = contentHeight
+            let position = 0
+  
+            let imgWidth = A4_WIDTH
+            let imgHeight = A4_WIDTH / contentWidth * contentHeight
+            let pageData = canvas.toDataURL('image/jpeg', 1.0)
+            // if (isPrint) {
+            //   //如果是打印,可以拿着分号页的数据 直接使用
+            //   printJs({ printable: pageData, type: 'image', base64: true, documentTitle: '\u200E' })
+            //   return
+            // }
+            //计算分页的pdf 
+            let PDF = new JsPDF('', 'pt', 'a4')
+            if (leftHeight <= pageHeight) {
+              PDF.addImage(pageData, 'JPEG', 0, 0, imgWidth, imgHeight)
+            } else {
+              while (leftHeight > 0) {
+                PDF.addImage(pageData, 'JPEG', 0, position, imgWidth, imgHeight)
+                leftHeight -= pageHeight
+                position -= A4_HEIGHT
+                if (leftHeight > 0) {
+                  PDF.addPage()
+                }
+              }
+            }
+            this.downloadStatus = false
+            PDF.save(title + '.pdf')
+          })
+       })
+    },
+  }
+};
+</script>
+<style lang="stylus">
+* {
+  margin: 0;
+  padding: 0;
+}
+.quality-report {
+  // z-index:9999;
+  width: 100%;
+  position: relative;
+  display: flex;
+  justify-content: center;
+  background: #06214D;
+}
+</style>
+<style lang="stylus" scoped>
+.nav-content {
+  position:fixed;
+  right: 10PX;
+  top: 164px;
+  display: flex;
+  flex-direction: column;
+  z-index: 99;
+  // width: 108px;
+  /* height: 44px; */
+  // background: #214388;
+  // header:300px;
+} 
+.nav-list {
+  height: 48px;
+  line-height: 48px;
+  text-align: center;
+  color: #FFFFFF;
+  font-size: 16px;
+  font-weight: bold;
+  margin-bottom: 20px;
+  background: linear-gradient(-79deg, #062D6F, #0185EA);
+  opacity: 0.6;
+  padding: 0 10px;
+}
+.report-container {
+  width: 70%;
+  margin-bottom: 20px;
+  position: relative;
+}
+.report-header {
+  text-align: center;
+  background: url('../assets/images/reportBg.png') no-repeat center;
+  background-size: 100% 100%;
+  height: 132px;
+}
+.header-title {
+  font-size: 36px;
+  font-weight: bold;
+  color: #FFFFFF;
+  padding-top: 32px;
+  line-height: 38px;
+}
+.header-subtitle {
+  font-size: 14px;
+  font-weight: 400;
+  color: #FFFFFF;
+  margin: 28px 0 22px;
+  line-height: 14px;
+  display: flex;
+  justify-content: space-around;
+}
+.report-content {
+  background: #0F2D5E;
+  padding: 0 16px;
+}
+.report-section {
+  margin: 18px 0;
+}
+.report-section:first-child {
+  margin-top: 0;
+  padding-top: 18px;
+}
+.title-content{
+  width: 100%;
+  height: 33px;
+  padding-bottom: 20px;
+  border-bottom: 2px solid #E5E5E5;
+  margin-bottom: 24px;
+}
+.title-line {
+  background: #1E58B8;
+  border-radius: 4px;
+  height: 45px;
+  padding-left: 20px;
+  display: flex;
+  align-items: center;
+  font-size: 14px;
+  color: #FFFFFF;
+  span {
+    height: 18px;
+    border-left: 1PX solid #FFFFFF;
+    padding-left: 10px;
+  }
+}
+.report-echarts {
+  .report-echarts-row {
+    margin-top: 10px;
+    margin-bottom: 10px;
+  }
+  .report-echarts-main {
+    // height: 310px;
+    border: 1px solid #2259B3;
+    border-radius: 4px;
+  }
+  .echarts-title {
+    font-size: 16px;
+    font-weight: 400;
+    color: #31A4FD;
+    line-height: 16px;
+    padding: 18px 18px 0 18px;
+  }
+  .echarts-sub-title {
+    font-size: 12px;
+    color: #fff;
+    padding: 20px 18px 0 18px;
+  }
+}
+.echart-detail {
+  width: 100%;
+  height: 290px;
+  // height: 100%;
+}
+// .echart-pie {
+//   width: 100%;
+//   height: 350px;
+// }
+.current-item {
+  background: linear-gradient(-79deg, #0185EA, #9FD0F5);
+}
+>>> .table-legend-list .ivu-table-cell{
+    display: flex;
+    align-items: center;
+    justify-content: center;
+}
+.table-legend {
+  width: 12px;
+  height: 12px;
+  border-radius: 4px;
+  display:inline-block;
+}
+.report-echarts-table {
+  padding: 20px 40px;
+}
+.report-echarts-right-table {
+  padding-top: 0;
+  padding-left: 0;
+}
+>>> .report-table-detail .ivu-table-stripe-even td {
+  background-color: #0F2D5E;
+  height: 40px;
+}
+>>> .report-table-detail .ivu-table-stripe-odd td {
+  background-color: #15376F;
+  height: 40px;
+}
+>>> .report-echarts-table .ivu-table .ivu-table-header .ivu-table-cell {
+ white-space: pre;
+}
+>>> .ivu-row .ivu-col {
+ position: static;
+}
+>>> .quality-table-cell span{
+  color:#5EB6FC;
+}
+>>> .total-records-table-cell span {
+  color: #42C151;
+}
+>>> .total-exceptions-table-cell span {
+  color: #D70101;
+}
+</style>

+ 1469 - 0
src/login/DownAppQualityReport.vue

@@ -0,0 +1,1469 @@
+<template>
+  <div class="quality-report">
+    <nav style="" class="nav-content">
+      <a class="nav-list" v-for="(item, index) in navList" :key="index" @click="jump(index)" :class="index==currentIndex?'current-item':''">{{item}}</a>
+    </nav>
+    <div class="report-container" id="report" ref="downReport">
+      <div class="report-header">
+        <div class="header-title">数据质量报告</div>
+        <div class="header-subtitle">
+          <span>数据范围:{{queryParams.appName}}</span>
+          <span>报告类型:{{queryParams.reportClassName}}</span>
+          <span v-if="queryParams.reportClassName == '日报'">时间范围:{{queryParams.beginDate}}</span>
+          <span v-else>时间范围:{{queryParams.beginDate}}~{{queryParams.endDate}}</span>
+        </div>
+      </div>
+      <div class="report-content">
+        <div class="report-section">
+          <div class="title-content">
+            <div class="title-line">
+              <span></span>综合数据质量分析
+            </div>
+          </div>
+          <div class="report-echarts">
+            <Row :gutter="16" class-name="report-echarts-row">
+              <Col :span="12">
+                <div class="report-echarts-main">
+                  <div class="echarts-title">1. 综合得分</div>
+                  <div id="appGuage" class="echart-detail"></div>
+                </div>
+             </Col>
+              <Col :span="12">
+                <div class="report-echarts-main">
+                  <div class="echarts-title">2. 评估维度</div>
+                  <div id="appRadar" class="echart-detail"></div>
+                </div>
+              </Col>
+            </Row>
+            <Row :gutter="16" class-name="report-echarts-row">
+              <Col :span="24">
+                <div class="report-echarts-main">
+                  <div class="echarts-title">3. 综合数据质量趋势</div>
+                  <div id="appLine3" class="echart-detail"></div>
+                </div>
+             </Col>
+            </Row>
+             <Row :gutter="16" class-name="report-echarts-row">
+              <Col :span="24">
+                <div class="report-echarts-main no-truncation">
+                  <div class="echarts-title">4. 综合数据质量分析-按规则类型</div>
+                  <div id="appLBar4" class="echart-detail"></div>
+                  <div class="report-echarts-table">
+                    <Table :columns="columns4" :data="tableData4" class="common-table report-table-detail" no-data-text="" :row-class-name="rowClassName">
+                      <template slot-scope="{row,index}" slot="paramDou01">
+                        <span :style="index==0 ? 'color:#5EB6FC': ''">{{row.paramDou01+'%'}}</span>
+                      </template>
+                      <template slot-scope="{row,index}" slot="paramDou02">
+                        <span :style="index==0 ? 'color:#5EB6FC': ''">{{row.paramDou02+'%'}}</span>
+                      </template>
+                      <template slot-scope="{row}" slot="paramDou04">
+                        <Icon type="md-arrow-up" style="color: #09CB09;font-size:20px" v-show="row.paramDou04>0"/>
+                        <Icon type="md-arrow-down" style="color: #F32F2F;font-size:20px" v-show="row.paramDou04<0" />
+                        {{Math.abs(row.paramDou04)+'%'}}
+                      </template>
+                    </Table>
+                  </div>
+                </div>
+             </Col>
+            </Row>
+          </div>
+        </div>
+         <div class="report-section">
+          <div class="title-content no-truncation">
+            <div class="title-line">
+              <span></span>数据异常分析
+            </div>
+          </div>
+          <div class="report-echarts">
+            <Row :gutter="16" class-name="report-echarts-row">
+                <Col :span="24">
+                  <div class="report-echarts-main no-truncation">
+                    <div class="echarts-title">5. 数据异常分析 - 按规则类型</div>
+                    <div class="echarts-sub-title">数据质量检测异常,按来源规则类型区分数据如下:</div>
+                    <Row :gutter="16" align="middle">
+                      <Col :span="8">
+                        <div id="appPie5" class="echart-detail"></div>
+                      </Col>
+                      <Col :span="16">
+                         <div class="report-echarts-table report-echarts-right-table">
+                           <Table :columns="columnsRule" :data="tableData5" class="common-table report-table-detail" no-data-text="" :row-class-name="rowClassName" ref="appTable5">
+                            <template slot-scope="{ index }" slot="xAxis">
+                              <span class="table-legend" :style="'background:'+tableColumnColor5[index]" v-show="index>0"></span>
+                            </template>
+                             <template slot-scope="{row,index}" slot="paramDou01">
+                                <span :style="index==0 ? 'color:#ECCF0C': ''">{{row.paramDou01}}%</span>
+                              </template>
+                           </Table>
+                        </div>
+                      </Col>
+                    </Row>
+                  </div>
+               </Col>
+            </Row>
+            <Row :gutter="16" class-name="report-echarts-row">
+                <Col :span="24">
+                  <div class="report-echarts-main no-truncation">
+                    <div class="echarts-title">6. 异常数来源 - 质量规则 TOP10</div>
+                    <div class="echarts-sub-title">数据质量检查错数按规则排名如下:</div>
+                    <Row :gutter="16">
+                      <Col :span="24">
+                         <div id="appBar6" class="echart-detail"></div>
+                         <div class="report-echarts-table">
+                          <Table :columns="columnsException" :data="tableData6" class="common-table report-table-detail" no-data-text="" :row-class-name="rowClassName">
+                            <template slot-scope="{row,index}" slot="paramDou01">
+                              <span :style="index==0 ? 'color:#5EB6FC': ''">{{row.paramDou01+'%'}}</span>
+                            </template>
+                            <template slot-scope="{row,index}" slot="paramDou02">
+                              <span :style="index==0 ? 'color:#5EB6FC': ''">{{row.paramDou02+'%'}}</span>
+                            </template>
+                          </Table>
+                        </div>
+                      </Col>
+                    </Row>
+                  </div>
+               </Col>
+            </Row>
+          </div>
+         <div class="report-section">
+          <div class="title-content no-truncation">
+            <div class="title-line">
+              <div class="num-title">
+                <span></span>规则配置状况
+              </div>
+            </div>
+          </div>
+          <div class="report-echarts">
+            <Row :gutter="16" class-name="report-echarts-row">
+                <Col :span="24">
+                  <div class="report-echarts-main no-truncation">
+                    <div class="echarts-title">7.规则配置状况</div>
+                    <div class="echarts-sub-title">规则配置数量级及占比</div>
+                    <Row :gutter="16" align="middle">
+                      <Col :span="8">
+                        <div id="appPie7" class="echart-detail"></div>
+                      </Col>
+                      <Col :span="16">
+                        <div class="report-echarts-table report-echarts-right-table">
+                           <Table :columns="columnsConfig" :data="tableData7" class="common-table report-table-detail" no-data-text="" :row-class-name="rowClassName">
+                             <template slot-scope="{ index }" slot="xAxis">
+                              <span class="table-legend" :style="'background:'+tableColumnColor7[index]" v-show="index>0"></span>
+                            </template>
+                            <template slot-scope="{row,index}" slot="paramDou05">
+                              <span :style="index==0 ? 'color:#5EB6FC': ''">{{row.paramDou05+'%'}}</span>
+                            </template>
+                            <template slot-scope="{row}" slot="paramDou04">
+                              <Icon type="md-arrow-up" style="color: #09CB09;font-size:20px" v-show="row.paramDou04>0"/>
+                              <Icon type="md-arrow-down" style="color: #F32F2F;font-size:20px" v-show="row.paramDou04<0" />
+                              {{Math.abs(row.paramDou04)+'%'}}
+                            </template>
+                          </Table>
+                        </div>
+                      </Col>
+                    </Row>
+                  </div>
+               </Col>
+            </Row>
+          </div>
+        </div>
+      </div>
+      </div>
+    </div>
+  </div>
+</template>
+<script>
+import * as echarts from "echarts"
+import html2canvas from 'html2canvas';
+import JsPDF from 'jspdf'
+export default {
+  name: "DownAppQualityReport",
+  data() {
+    return {
+        scroll: '',
+        navList: ['综合数据质量分析', '数据异常分析','规则配置状况'],
+        currentIndex:0,
+        listBoxState: true,//点击导航栏时,暂时停止监听页面滚动
+        queryParams: {reportClassName:'',beginDate:'',endDate: '',appId:0,appName: ''},
+        columns4: [
+           {
+            title: '来源应用',
+            key: 'xAxis',
+            align: 'center',
+            ellipsis: true,
+            tooltip: true
+          },
+          {
+            title: '记录总数',
+            key: 'paramLong01',
+            align: 'center',
+            ellipsis: true,
+            tooltip: true
+          },
+          {
+            title: '本期质量',
+            slot: 'paramDou01',
+            align: 'center',
+          },
+          {
+            title: '上期质量',
+            slot: 'paramDou02',
+            align: 'center',
+          },
+          {
+            title: '趋势',
+            slot: 'paramDou04',
+            align: 'center',
+          },
+        ],
+        tableData4: [],
+        tableData5: [],
+        tableData6: [],
+        tableData7: [],
+        pieColumnColor5: ['#646AD9','#FDDD60','#FF6E76','#7CFFB2','#4992FF','#58D9F9'],
+        tableColumnColor5: ['','#646AD9','#FDDD60','#FF6E76','#7CFFB2','#4992FF'],
+        pieColumnColor7: ['#FF6E76','#646AD9','#FDDD60','#7CFFB2','#4992FF','#58D9F9'],
+        tableColumnColor7: ['','#FF6E76','#646AD9','#FDDD60','#7CFFB2','#4992FF'],
+        columnsRule: [
+        {
+          title: '图例颜色',
+          slot: 'xAxis',
+          align: 'right',
+          width: 70,
+          className: 'table-legend-list',
+        },
+        {
+          title: '来源应用',
+          key: 'xAxis',
+          align: 'center',
+          ellipsis: true,
+          tooltip: true
+        },
+        {
+          title: '记录总数',
+          key: 'paramNum01',
+          align: 'center',
+          ellipsis: true,
+          tooltip: true
+        },
+        {
+          title: '异常总数',
+          key: 'paramNum02',
+          align: 'center',
+          ellipsis: true,
+          tooltip: true
+        },
+        {
+          title: '异常占比',
+          slot: 'paramDou01',
+          align: 'center',
+        }],
+        columnsException: [
+          {
+          title: '来源规则名称',
+          key: 'xAxis',
+          align: 'center',
+          ellipsis: true,
+          tooltip: true
+        },
+        {
+          title: '记录总数',
+          key: 'paramLong01',
+          align: 'center',
+          ellipsis: true,
+          tooltip: true
+        },
+        {
+          title: '异常总数',
+          key: 'paramNum01',
+          align: 'center',
+          ellipsis: true,
+          tooltip: true
+        },
+        {
+          title: '本期质量',
+          slot: 'paramDou01',
+          align: 'center',
+        },
+        {
+          title: '异常数\n总体占比', // iview的table表头文字换行需要\n和.ivu-table-cell {white-space: pre;}
+          slot: 'paramDou02',
+          align: 'center',
+        },
+       ],
+        columnsConfig: [
+          {
+            title: '图例颜色',
+            slot: 'xAxis',
+            align: 'right',
+            width: 70,
+            className: 'table-legend-list',
+          },
+         {
+            title: '规则类型',
+            key: 'xAxis',
+            align: 'center',
+            ellipsis: true,
+            tooltip: true
+          },
+          {
+            title: '数量',
+            key: 'paramNum01',
+            align: 'center',
+            ellipsis: true,
+            tooltip: true
+          },
+          {
+            title: '占比',
+            slot: 'paramDou05',
+            align: 'center',
+          },
+          {
+            title: '趋势',
+            slot: 'paramDou04',
+            align: 'center',
+          },
+        ],
+        downloadStatus: false,
+    };
+  },
+  watch: {
+      scroll: function () {
+        this.loadSroll()
+      }
+    },
+  created () {
+    if (this.$route.query.reportClassName) {
+      this.queryParams = this.$route.query
+      let parmasObj = {
+        beginDate: this.queryParams.beginDate,
+        endDate: this.queryParams.endDate,
+        appId: this.queryParams.appId
+      }
+      this.downloadStatus = false
+      this.getData(parmasObj)
+    }
+  },
+  mounted() {
+    //vue通过window.addEventListener('scroll', XXXX)无法监听屏幕滚动事件,上一个页面可以,换了一个页面,却不行了,后来百度,往后面加了一个true
+    window.addEventListener('scroll', this.dataScroll,true)
+  },
+  methods: {
+    // js 节流浏览器性能优化
+    dataScroll: function () {                           
+      this.scroll = document.documentElement.scrollTop || document.body.scrollTop;
+    },
+    jump(index) {
+    let jump = document.getElementsByClassName('report-section');
+    // 获取需要滚动的距离
+    let total = jump[index].offsetTop;
+    // Chrome
+    document.body.scrollTop  = total;
+    // Firefox
+    document.documentElement.scrollTop = total;
+    // Safari
+    window.pageYOffset = total;
+    this.currentIndex = index
+    this.listBoxState = false
+    let timeId;
+    clearTimeout(timeId);
+    timeId = setTimeout(() => {
+      this.listBoxState = true
+    },100)
+    // $('html, body').animate({
+    // 'scrollheader': total
+    // }, 400);
+    },
+    loadSroll: function () {
+      var self = this;
+      var sections = document.getElementsByClassName('report-section');
+      if (this.listBoxState) {
+        for (var i = sections.length - 1; i >= 0; i--) {
+          if (self.scroll >= sections[i].offsetTop-100) {
+            this.currentIndex = i
+            break;
+          }
+        }
+      } 
+    },
+    rowClassName(row, index) {
+      if (index % 2 == 0) {
+        return "ivu-table-stripe-even";
+      } else {
+        return "ivu-table-stripe-odd";
+      }
+    },
+    creatGauge(gaugeData) {
+      let myChart = echarts.init(document.getElementById(gaugeData.id))
+      let option = {
+        series: [
+          {
+            type: 'gauge',
+            center: ['50%', '68%'],
+            radius:'90%',
+            startAngle: 200,
+            endAngle: -20,
+            min: 0,
+            max: 100,
+            splitNumber: 10,
+            itemStyle: {
+              color: '#FFAB91'
+            },
+            progress: {
+              show: true,
+              width: 15
+            },
+            pointer: {
+              show: false
+            },
+            axisLine: {
+              lineStyle: {
+                color:[[1, '#284677']],
+                width: 15
+              }
+            },
+            axisTick: {
+              distance: -35,
+              splitNumber: 5,
+              lineStyle: {
+                width: 2,
+                color: '#4D5F7D'
+              }
+            },
+            splitLine: {
+              distance: -52,
+              length: 14,
+              lineStyle: {
+                width: 3,
+                color: '#4D5F7D'
+              }
+            },
+            axisLabel: {
+              distance: -20,
+              color: '#5D6B82',
+              fontSize: 12
+            },
+            anchor: {
+              show: false
+            },
+            title: {
+              show: false
+            },
+            detail: {
+              valueAnimation: true,
+              width: '60%',
+              lineHeight: 40,
+              borderRadius: 8,
+              offsetCenter: [0, '-15%'],
+              fontSize: 30,
+              fontWeight: 'bolder',
+              formatter: '{value} %',
+              color: 'auto'
+            },
+            data: [
+              {
+                value: gaugeData.scores
+              }
+            ]
+          },
+          {
+            type: 'gauge',
+            center: ['50%', '68%'],
+            radius:'90%',
+            startAngle: 200,
+            endAngle: -20,
+            min: 0,
+            max: 100,
+            itemStyle: {
+              color: '#FD6636'
+            },
+            progress: {
+              show: true,
+              width: 5
+            },
+            pointer: {
+              show: false
+            },
+            axisLine: {
+              show: false
+            },
+            axisTick: {
+              show: false
+            },
+            splitLine: {
+              show: false
+            },
+            axisLabel: {
+              show: false
+            },
+            detail: {
+              show: false
+            },
+            data: [
+              {
+                value: gaugeData.scores
+              }
+            ]
+          }
+        ]
+      }
+      myChart.resize()
+      myChart.clear()
+      myChart.setOption(option)
+      window.addEventListener("resize", function() {
+        myChart.resize()
+      })
+    },
+    //雷达图显示文字
+    contains(arr, val) {
+      var i = arr.length;
+      while (i--) {
+          if (arr[i].name === val) {
+              return i;
+          }
+      }
+      return false;
+    },
+    creatSolidRadar (SolidRadarData) {
+        if (echarts.init(document.getElementById(SolidRadarData.id))) {
+          let  myChart = echarts.init(document.getElementById(SolidRadarData.id));
+          myChart.clear()
+          const createSvg = ({width, height, shadowColor, shadowBlur, points}) => {
+              const ret = [`M${points[0][0]} ${points[0][1]}`];
+              for (let i = 1; i < points.length; i++) {
+                  ret.push(`L${points[i][0]} ${points[i][1]}`);
+              }
+              ret.push('Z');
+              const rectPath = ret.join(' ');
+              return (`
+                  <svg version="1.1" xmlns="http://www.w3.org/2000/svg" 
+                      x="0px" y="0px" 
+                      width="${width}"
+                      height="${height}"
+                  >
+                      <style>
+                          .st1 {
+                              fill: transparent;
+                              stroke: ${shadowColor};
+                              stroke-width: ${shadowBlur}px;
+                              filter: url(#chart-inset-shadow);
+                              clip-path: url(#chart-clip);
+                          }
+
+                      </style>
+                      <defs>
+                      
+                          <clipPath id="chart-clip">
+                              <path d="${rectPath}" />
+                          </clipPath>
+                          
+                          <filter id="chart-inset-shadow" width="200%" height="200%" x="-50%" y="-50%">
+                              <feGaussianBlur in="SourceGraphic" result="gass" stdDeviation="${shadowBlur * 0.75}" />
+                              <feMerge>
+                                  <feMergeNode in="gass" />
+                              </feMerge>
+                          </filter>
+
+                      </defs>
+                      <g>
+                          <path class="st1" d="${rectPath}" />
+                      </g>
+                  </svg>
+              `);        
+            };
+          const cretateSvgUrl = (svgOption) => {
+              const svgString = createSvg(svgOption);
+              const svg = new Blob([svgString], {type: "image/svg+xml;charset=utf-8"});              
+              const DOMURL = window.URL || window.webkitURL || window;
+              const insetShadowUrl = DOMURL.createObjectURL(svg);               
+              return insetShadowUrl;
+          };
+          const dataSet = [], nameArr  = []
+          SolidRadarData.category[0].forEach((item,index)=> {
+           nameArr.push(item.name)
+          })
+          dataSet[0] = nameArr
+          dataSet[1] = [100,100,100,100,100]
+          dataSet[2] = SolidRadarData.data[0].value
+          const maxValue = [...dataSet[1], ...dataSet[2]].reduce((m, v) => Math.max(m, v), -Infinity);
+          const radius = 0.8;
+          const theta = Math.PI * 2 / dataSet[2].length
+          const getPoints = (R, ps, max) => ps.map((v, i) => {
+              const t = i * theta;
+              const d = v / max;
+              const x = R - Math.sin(t) * R * d;    
+              const y = R - Math.cos(t) * R * d;
+              return [x, y];
+          });
+          // let i = -1;
+          let option = {
+              polar: {
+                  radius: radius * 100 + '%',
+                  // center: ['50%', '58%'],
+                  center: ['50%', '50%'],
+              },
+              angleAxis: {
+                  type: 'category',
+                  clockwise: false,
+                  boundaryGap: false,
+                  splitLine: {
+                      show: false,
+                  },
+                  axisLine: {
+                      show: false
+                  }
+              },
+              radiusAxis: {
+                  type: 'value',
+                  min: 0,
+                  max: 100,
+                  splitLine: {
+                      show: false,
+                  },
+                  axisTick: {
+                      show: false,
+                  },
+                  axisLabel: {
+                      show: false,
+                      color:'#fff',
+                      formatter: '{value} %'
+                  },
+              },
+              radar: {
+                  indicator: SolidRadarData.category[0],
+                  radius: radius * 100 + '%',
+                  center: ['50%', '50%'],
+                  shape: 'polygon',
+                  splitNumber: 5,
+                  // nameGap : 1,
+                  name: {
+                    // rich: {
+                    //   a: {
+                    //       color: '#fff',
+                    //       lineHeight: 20,
+                    //   },
+                    //   b: {
+                    //       color: '#fff',
+                    //       align: 'center',
+                    //       padding: 2,
+                    //       borderRadius: 4
+                    //    }
+                    //   },
+                    //   formatter: (value)=>{
+                    //     let i = this.contains(SolidRadarData.category[0], value); // 处理对应要显示的样式
+                    //     return `{a|${value}}{b|${dataSet[2][i]}%}`
+                    //   },
+                      textStyle: {
+                          color: '#fff',
+                          fontSize: 12,
+                          padding: [-10, -10]
+                      }
+                  },
+                  splitArea: {
+                      areaStyle: {
+                          color: [
+                              'rgba(8,20,58,0.1)',
+                              'rgba(,20,58,0.03)',
+                              'rgba(,20,58,0.1)',
+                              'rgba(,20,58,0.03)',
+                          ]
+                      }
+                  },
+                  splitLine: {
+                      lineStyle: {
+                          color: [
+                              '#2A3A6E', '#2A3A6E',
+                              '#2A3A6E', '#2A3A6E',
+                              '#2A3A6E'
+                          ].reverse(),
+                          width: 3
+                      }
+                  },
+                  axisLine: {
+                      lineStyle: {
+                          color: '#264474'
+                      }
+                  }
+              },
+              animationDuration: 3000,
+              series: [
+                  {
+                      type: 'custom',
+                      name: 's1-inset-shadow',
+                      silent: true,
+                      coordinateSystem : 'polar', 
+                      // data: [0],
+                      renderItem: (params,api) => {
+                          const R = params.coordSys.r;
+                          const cx = params.coordSys.cx;
+                          const cy = params.coordSys.cy;
+                          const x = cx - R;
+                          const y = cy - R;
+                          const width = 2 * R;
+                          const height = 2 * R;                         
+                          return {
+                              type: 'image',
+                              style: {
+                                  image: cretateSvgUrl({
+                                      width, height,
+                                      shadowColor: '#00A0E9',
+                                      shadowBlur: 6, 
+                                      points: getPoints(R, dataSet[1], 100)
+                                  }),
+                                  x,
+                                  y,
+                                  width, 
+                                  height,
+                              },
+                          };
+                      },
+                  },
+                  {
+                      name: 's2',
+                      type: 'radar',
+                      data: [
+                          { value: dataSet[2] }
+                      ],
+                      // symbol: 'none',
+                      label: {
+                          show: true,
+                          formatter: function(params) {
+                              return params.value + '%';
+                          },
+                          color: '#fff',
+                          position: [-10, -10],
+                          // align: 'left',
+                          // distance: -25,
+                          
+                      },
+                      symbolSize: [6, 6],
+                      itemStyle: {
+                          shadowColor: 'rgba(0, 0, 0, 0.5)',
+                          shadowBlur: 20,
+                          normal: {
+                              color: 'rgba(87,201,255,0.8)',
+                              borderColor: 'rgba(87,201,255,0.2)',
+                              borderWidth: 12,
+                              
+                          }
+                      },
+                      areaStyle: {
+                          normal: {
+                              color: '#383F2F',
+                          }
+                      },
+                      lineStyle: {
+                          normal: {
+                              color: '#FAEC05',
+                              width: 2,
+                              
+                          }
+                      },
+                      z: 3,
+                  },
+              ]
+          };
+          myChart.resize()
+          myChart.setOption(option)
+          window.addEventListener("resize", function () {
+              myChart.resize()  
+            })
+        }
+    },
+    creatLine (lineData) {
+      let toplinechart = echarts.init(document.getElementById(lineData.id));
+      let seriesData = _.map(lineData.data, (item,index)=>({
+          name: lineData.legend[index], type: 'line', symbol: 'circle', symbolSize: 2,smooth: true, // 平滑曲线
+          lineStyle: { normal: { color: lineData.lineColor[index], width: 2 } },
+          itemStyle: { normal: { color: lineData.lineColor[index], borderColor: lineData.lineColor[index], borderWidth: 2 },
+          emphasis: { color: '#fff' }
+        },
+        areaStyle: { opacity:0.4,color: new echarts.graphic.LinearGradient(0, 0, 0, 1, [{ offset: 0.3, color: lineData.lineColor[index]}, { offset: 1, color: 'rgba(0,0,0,0)' }])},
+        data: item
+      }))
+      let toplineoption = {
+        legend: {
+          top: '5%', left: 'center', itemWidth: 10, itemHeight: 10, itemGap: 25,
+          textStyle: { color: '#fff', fontSize: 12 },
+          data: lineData.legend
+        },
+        tooltip: { trigger: "axis",
+          confine: true,
+          backgroundColor: '#011235',
+          borderWidth: 0,
+          extraCssText: 'opacity:0.8',
+          textStyle: {
+            color: '#fff'
+          },
+        formatter: function (params) {
+          let res = ''
+          params.forEach((item,i) => {
+            res += '<div style="display: flex;align-items:center;justify-content:space-between"><span>'+ item.marker + item.seriesName + ':</span><span>' +  item.value + lineData.unit+'</span></div> '
+          })
+          return params[0].name + res
+        }
+        },
+        grid: {
+          top: '18%', 
+          left: "4%",
+          right: "4%",
+          bottom: "4%",
+          containLabel: true
+        },
+        xAxis: [{
+          type: 'category',
+          data: lineData.category,
+          boundaryGap: false,
+          axisLine: {
+            lineStyle: {
+              color: '#00479D',
+              width: 1
+            }
+          },
+          axisLabel: {
+            color: '#fff',
+          },
+          axisTick: {
+            alignWithLabel: true
+          }
+        }],
+        yAxis: [{
+          type: 'value',
+          axisLine: {
+            show: true,
+            lineStyle: {
+              color: '#00479D',
+              width: 1
+            }
+          },
+          axisTick: {
+            show: true
+          },
+          splitLine: {
+            show: true,
+            lineStyle: {
+              type: "solid",
+              width: 1,
+              color: "#153068"
+            }
+          },
+          axisLabel: {
+            show: true,
+            color: '#fff'
+          }
+        }],
+        series: seriesData
+      }
+      toplinechart.resize()
+      toplinechart.clear()
+      toplinechart.setOption(toplineoption)
+      console.log('line')
+      window.addEventListener("resize", function () { toplinechart.resize() })
+    },
+    creatBar(botmLeftBarData) {
+			let botmLeftChart = echarts.init(document.getElementById(botmLeftBarData.id))
+      let barseries = []
+      for (var i = 0; i < botmLeftBarData.legend.length; i++) {
+        let itemStyle = {}
+        if (botmLeftBarData.showStack) {
+          itemStyle = {
+            normal: {
+              color:botmLeftBarData.color[i]
+            }
+          }
+        } else {
+          itemStyle = {
+            normal: {
+              color: {
+                type: 'linear',
+                x: 0,
+                y: 0,
+                x2: 0,
+                y2: 1,
+                colorStops: [{
+                  offset: 0,
+                  color: botmLeftBarData.color[i][0]
+                }, {
+                  offset: 1,
+                  color: botmLeftBarData.color[i][1]
+                }],
+                globalCoord: false // 缺省为 false
+              },
+            }
+          }
+        }
+        barseries.push({
+          name: botmLeftBarData.legend[i],
+          type: 'bar',
+          stack: botmLeftBarData.showStack ? 'total' : false,
+          barMaxWidth: 28,
+          itemStyle: itemStyle,
+          data: botmLeftBarData.data[i]
+        })
+      }
+      let botmLeftOption = {
+        tooltip: {
+          trigger: botmLeftBarData.legend.length==1 ? 'item' : 'axis',
+          axisPointer: { type: 'shadow' },
+          confine: true,
+          backgroundColor: '#011235',
+          borderWidth: 0,
+          extraCssText: 'opacity:0.8',
+          textStyle: {
+            color: '#fff'
+          },
+          formatter: function(params) {
+            if (Array.isArray(params)) {
+             let res = ''
+              params.forEach((item,i) => {
+                res += '<div style="display: flex;align-items:center;justify-content:space-between"><span>'+ item.marker + item.seriesName + ':</span><span>' +  item.value + botmLeftBarData.unit+'</span></div> '
+              })
+              return params[0].name + res
+            } else {
+              return params.marker + params.name+':'+ params.value + botmLeftBarData.unit
+            }
+          }
+        },
+        legend: {
+          show: botmLeftBarData.legend.length>1 ? true : false,
+          orient: 'horizontal', left: 'center', top: 2, itemWidth: 10, itemHeight: 10,
+          textStyle: { color: '#ffffff', fontSize: 12 },
+          data: botmLeftBarData.legend
+        },
+        grid: {
+          top: '14%',
+          left: "4%",
+          right: "8%",
+          bottom: "2%",
+          containLabel: true
+        },
+        xAxis: [{
+          type: 'category',
+          axisLine: {
+            show: true,
+            lineStyle: {
+              color: '#00479D'
+            }
+          },
+          axisLabel: {
+            textStyle: {
+              color: '#ffffff',
+              fontSize: 12
+            },
+          },
+          axisTick: {
+            alignWithLabel: true
+          },
+          data: botmLeftBarData.category
+        }],
+        yAxis: [{
+          type: 'value',
+          splitLine: {
+            show: true,
+            lineStyle: {
+              type: "solid",
+              width: 1,
+              color: "#153068"
+            }
+          },
+          axisLine: {
+            show: true,
+            lineStyle: {
+              color: '#00479D',
+              width: 1
+            }
+          },
+          axisLabel: {
+            textStyle: {
+              color: '#ffffff',
+              fontSize: 12
+            }
+          },
+          axisTick: {
+            show: true
+          },
+        }],
+        series: barseries
+      }
+      botmLeftChart.resize()
+      botmLeftChart.clear()
+      botmLeftChart.setOption(botmLeftOption)
+      window.addEventListener("resize", function() {
+        botmLeftChart.resize()
+      })
+		},
+    creatPie(pieData) {
+      let sum = pieData.data.reduce((prev, current) => prev + current.value, 0) // 数组求和
+      pieData.data.forEach((item)=> {
+        if (item.name == '其他') {
+          item.labelLine = {
+            lineStyle: {
+              color: pieData.color[pieData.color.length-1]
+            }
+          }
+        } else {
+           item.labelLine = {
+            lineStyle: {
+              color: 'transparent'
+            }
+          }
+        }
+      })
+      let myChart = echarts.init(document.getElementById(pieData.id))
+      let option = {
+        title: {
+          text: '{a|' + sum + '}{c|条}',
+          x: 'center',
+          y: 'center',
+          textStyle: {
+            rich: {
+              a: {
+                padding: [10, 0],
+                color: '#1EAFF5',
+                fontSize: 20,
+                align: 'center',
+                fontWeight: 'bold'
+              },
+              c: {
+                color: "#fff",
+                fontSize: 12, 
+              }
+            }
+          },
+        },
+        tooltip: {
+          trigger: "item",
+          labelLine: false,
+          confine: true,
+          backgroundColor: '#011235',
+          borderWidth: 0,
+          extraCssText: 'opacity:0.8',
+          textStyle: {
+            color: '#fff'
+          },
+          formatter: function(params) {
+            return params.name + ':' + params.percent + '% (' + params.value + pieData.unit + ')'
+          }
+        },
+        series: [{
+          color: pieData.color,
+          type: 'pie',
+          radius: ['50%', '70%'],
+          center: ['50%', '50%'],
+          label: {
+              position: 'outer',
+              alignTo: 'none',
+              bleedMargin: 0,
+              color: '#FFFFFF',
+              fontSize: 12,
+              formatter: function(params) {
+                if (params.data.name == '其他') {
+                  return params.name + ':' + params.percent + '% (' + params.value + pieData.unit + ')'
+                } else {
+                  return ''
+                }
+              }
+            },
+          data: pieData.data,
+        }, ]
+      };
+      myChart.resize();
+      myChart.clear();
+      myChart.setOption(option);
+      window.addEventListener("resize", function() {
+        myChart.resize();
+      })
+    },
+    // getEchartData (params) {
+    //   this.$get('metroapi/dataQuality/report/comScores',params).then(res => {
+    //     if (res.httpCode == 1) {
+    //       let obj = res.data
+    //       obj.id = 'appGuage'
+    //       this.$nextTick(() => this.creatGauge(obj))
+    //     }
+    //   })
+    //   this.$get('metroapi/dataQuality/report/difDimScores',params).then(res => {
+    //     if (res.httpCode == 1) {
+    //       let obj2 = res.data
+    //       obj2.id = 'appRadar'
+    //       this.$nextTick(() => this.creatSolidRadar(obj2))
+    //     }
+    //   })
+    // },
+    async getEchartData1(url,params) {
+      let rtnData 
+      await this.$get( url, params).then(res=>{
+        rtnData = res         
+      })
+      return rtnData
+    },
+    downReport(row) {
+      this.downloadStatus = true
+      this.queryParams = row
+      let paramsObj = {
+        beginDate: row.beginDate,
+        endDate: row.endDate,
+        appId: row.appId
+      }
+      this.getData(paramsObj)
+    },
+    downPdf () {
+     this.$nextTick(()=> {
+        let title = this.queryParams.reportName+'-'+this.queryParams.appName
+        // 如果这个页面有左右移动,canvas 也要做响应的移动,不然会出现canvas 内容不全
+        const xOffset = window.pageXOffset
+        // 避免笔下误 灯下黑 统一写
+        const A4_WIDTH = 592.28
+        // const A4_HEIGHT = 841.89
+        const A4_HEIGHT = 841.89
+        let printDom = this.$refs.downReport
+        // 根据A4的宽高计算DOM页面一页应该对应的高度
+        let pageHeight = printDom.offsetWidth / A4_WIDTH * A4_HEIGHT
+        // 将所有不允许被截断的元素进行处理
+        let wholeNodes = document.querySelectorAll('.no-truncation') //pdf加分页防止内容截断
+        for (let i = 0; i < wholeNodes.length; i++) {
+          //1、 判断当前的不可分页元素是否在两页显示
+          const topPageNum = Math.ceil((wholeNodes[i].offsetTop) / pageHeight) // wholeNodes[i].offsetTop 它返回当前元素相对于其 offsetParent 元素的顶部内边距的距离 如果算距离对顶部的距离它的父级不能设置定位,,否则结果为0
+          const bottomPageNum = Math.ceil((wholeNodes[i].offsetTop + wholeNodes[i].offsetHeight) / pageHeight)
+          if (topPageNum !== bottomPageNum) {
+            //说明该dom会被截断
+            // 2、插入空白块使被截断元素下移
+            let divParent = wholeNodes[i].parentNode
+            let newBlock = document.createElement('div')
+            newBlock.className = 'emptyDiv'
+            newBlock.style.background = '#06214d'
+            // 3、计算插入空白块的高度 可以适当流出空间使得内容太靠边,根据自己需求而定
+            let _H = topPageNum * pageHeight - wholeNodes[i].offsetTop
+            newBlock.style.height = _H + 30 + 'px'
+            divParent.insertBefore(newBlock, wholeNodes[i])
+          }
+        }
+          // 以上完成dom层面的分页 可以转为图片进一步处理了
+          html2canvas(printDom, { height: printDom.offsetHeight, width: printDom.offsetWidth, scrollX: -xOffset,backgroundColor: "#fff",allowTaint: true ,}).then(canvas => {
+            //dom 已经转换为canvas 对象,可以将插入的空白块删除了
+            let emptyDivs = document.querySelectorAll('.emptyDiv')
+            for (let i = 0; i < emptyDivs.length; i++) {
+              emptyDivs[i].parentNode.removeChild(emptyDivs[i])
+            }
+            // 有一点重复的代码
+            let contentWidth = canvas.width
+            let contentHeight = canvas.height
+            let pageHeight = contentWidth / A4_WIDTH * A4_HEIGHT
+            let leftHeight = contentHeight
+            let position = 0
+  
+            let imgWidth = A4_WIDTH
+            let imgHeight = A4_WIDTH / contentWidth * contentHeight
+            let pageData = canvas.toDataURL('image/jpeg', 1.0)
+            // if (isPrint) {
+            //   //如果是打印,可以拿着分号页的数据 直接使用
+            //   printJs({ printable: pageData, type: 'image', base64: true, documentTitle: '\u200E' })
+            //   return
+            // }
+            //计算分页的pdf 
+            let PDF = new JsPDF('', 'pt', 'a4')
+            if (leftHeight <= pageHeight) {
+              PDF.addImage(pageData, 'JPEG', 0, 0, imgWidth, imgHeight)
+            } else {
+              while (leftHeight > 0) {
+                PDF.addImage(pageData, 'JPEG', 0, position, imgWidth, imgHeight)
+                leftHeight -= pageHeight
+                position -= A4_HEIGHT
+                if (leftHeight > 0) {
+                  PDF.addPage()
+                }
+              }
+            }
+            this.downloadStatus = false
+            PDF.save(title + '.pdf')
+          })
+       })
+    },
+    getData(params){
+      let interface1 = this.getEchartData1('metroapi/dataQuality/report/comScores',params)
+      let interface2 = this.getEchartData1('metroapi/dataQuality/report/difDimScores',params)
+      let interface3 = this.getEchartData1('metroapi/dataQuality/report/comScoresTrend',params)
+      let interface4 = this.getEchartData1('metroapi/dataQuality/report/comScores/model/bar',params)
+      let interfaceTable4 = this.getEchartData1('metroapi/dataQuality/report/comScores/model/list',params)
+      let interface5 = this.getEchartData1('metroapi/dataQuality/report/abnDataAnalysis/model/pie',params)
+      let interfaceTable5 = this.getEchartData1('metroapi/dataQuality/report/abnDataAnalysis/model/list',params)
+      let interface6 = this.getEchartData1('metroapi/dataQuality/report/abnSource/rule/bar',params)
+      let interfaceTable6 = this.getEchartData1('metroapi/dataQuality/report/abnSource/rule/list',params)
+      let interface7 = this.getEchartData1('metroapi/dataQuality/report/ruleConf/pie',params)
+      let interfaceTable7 = this.getEchartData1('metroapi/dataQuality/report/ruleConf/list',params)
+      this.$axiosAll([interface1,interface2,interface3,interface4,interfaceTable4,interface5,interfaceTable5,interface6,interfaceTable6,interface7,interfaceTable7]).then(res=> {
+        if (res[0].httpCode == 1) {
+          let obj = res[0].data
+          obj.id = 'appGuage'
+          this.$nextTick(() => this.creatGauge(obj))
+        }
+        if (res[1].httpCode == 1) {
+          let obj2 = res[1].data
+          obj2.id = 'appRadar'
+          this.$nextTick(() => this.creatSolidRadar(obj2))
+        }
+        if (res[2].httpCode == 1) {
+          let obj3 = res[2].data
+          obj3.id = 'appLine3'
+          obj3.unit = '%'
+          obj3.lineColor = ['#31A4FD', '#86BE73']
+          this.$nextTick(() => this.creatLine(obj3))
+        }
+        if (res[3].httpCode == 1) {
+          let obj4 = res[3].data
+          obj4.id = 'appLBar4'
+          obj4.unit = '%'
+          obj4.color = [['#0874E2','#62BAFD'], ['#86BE73', '#42A76D']]
+          this.$nextTick(() => this.creatBar(obj4))
+        }
+        if (res[4].httpCode == 1) {
+          this.tableData4 = res[4].data.data
+          this.tableData4.forEach((item,index)=> {
+            if (index == 0) {
+              item.cellClassName = {
+                paramLong01: 'total-records-table-cell',
+                paramDou01: 'quality-table-cell',
+                paramDou02: 'quality-table-cell',
+              }
+            }
+          })
+        }
+         if (res[5].httpCode == 1) {
+          let obj5 = res[5].data
+          obj5.id = 'appPie5'
+          obj5.unit = '条'
+          obj5.color = this.pieColumnColor5
+          this.$nextTick(() => this.creatPie(obj5))
+        }
+        if (res[6].httpCode == 1) {
+          this.tableData5 = res[6].data.data
+          this.tableData5.forEach((item,index)=> {
+            if (index == 0) {
+              item.cellClassName = {
+                paramNum01: 'total-records-table-cell',
+                paramNum02: 'total-exceptions-table-cell',
+              }
+            }
+          })
+        }
+        if (res[7].httpCode == 1) {
+          let obj6 = res[7].data
+          obj6.id = 'appBar6'
+          obj6.unit = '条'
+          obj6.legend = ['']
+          obj6.color = [['#0874E2','#62BAFD']]
+          this.$nextTick(() => this.creatBar(obj6))
+        }
+        if (res[8].httpCode == 1) {
+          this.tableData6 = res[8].data.data
+          this.tableData6.forEach((item,index)=> {
+          if (index == 0) {
+            item.cellClassName = {
+              paramLong01: 'total-records-table-cell',
+              paramNum01: 'total-exceptions-table-cell'  
+            }
+          }
+         })
+        }
+        if (res[9].httpCode == 1) {
+          let obj7 = res[9].data
+          obj7.id = 'appPie7'
+          obj7.unit = '条'
+          obj7.color = this.pieColumnColor7
+          this.$nextTick(() => this.creatPie(obj7))
+        }
+         if (res[10].httpCode == 1) {
+          this.tableData7 = res[10].data.data
+          this.tableData7.forEach((item,index)=> {
+            if (index == 0) {
+              item.cellClassName = {
+                paramNum01: 'quality-table-cell',
+              }
+            }
+          })
+        }
+        this.$nextTick(()=> {
+          if (this.downloadStatus) {
+            setTimeout(() => {
+              this.downPdf()
+            }, 1000)
+          }
+        })
+      })
+    }
+  }
+};
+</script>
+<style lang="stylus">
+* {
+  margin: 0;
+  padding: 0;
+}
+.quality-report {
+  // z-index:9999;
+  width: 100%;
+  position: relative;
+  display: flex;
+  justify-content: center;
+  background: #06214D;
+}
+</style>
+<style lang="stylus" scoped>
+.nav-content {
+  position:fixed;
+  right: 10PX;
+  top: 164px;
+  display: flex;
+  flex-direction: column;
+  z-index: 99;
+  // width: 108px;
+  /* height: 44px; */
+  // background: #214388;
+  // header:300px;
+} 
+.nav-list {
+  height: 48px;
+  line-height: 48px;
+  text-align: center;
+  color: #FFFFFF;
+  font-size: 16px;
+  font-weight: bold;
+  margin-bottom: 20px;
+  background: linear-gradient(-79deg, #062D6F, #0185EA);
+  opacity: 0.6;
+  padding: 0 10px;
+}
+.report-container {
+  width: 70%;
+  margin-bottom: 20px;
+  position: relative;
+}
+.report-header {
+  text-align: center;
+  background: url('../assets/images/reportBg.png') no-repeat center;
+  background-size: 100% 100%;
+  height: 132px;
+}
+.header-title {
+  font-size: 36px;
+  font-weight: bold;
+  color: #FFFFFF;
+  padding-top: 32px;
+  line-height: 38px;
+}
+.header-subtitle {
+  font-size: 14px;
+  font-weight: 400;
+  color: #FFFFFF;
+  margin: 28px 0 22px;
+  line-height: 14px;
+  display: flex;
+  justify-content: space-around;
+}
+.report-content {
+  background: #0F2D5E;
+  padding: 0 16px;
+}
+.report-section {
+  margin: 18px 0;
+}
+.report-section:first-child {
+  margin-top: 0;
+  padding-top: 18px;
+}
+.title-content{
+  width: 100%;
+  height: 33px;
+  padding-bottom: 20px;
+  border-bottom: 2px solid #E5E5E5;
+  margin-bottom: 24px;
+}
+.title-line {
+  background: #1E58B8;
+  border-radius: 4px;
+  height: 45px;
+  padding-left: 20px;
+  display: flex;
+  align-items: center;
+  font-size: 14px;
+  color: #FFFFFF;
+  span {
+    height: 18px;
+    border-left: 1PX solid #FFFFFF;
+    padding-left: 10px;
+  }
+}
+.report-echarts {
+  .report-echarts-row {
+    margin-top: 10px;
+    margin-bottom: 10px;
+  }
+  .report-echarts-main {
+    // height: 310px;
+    border: 1px solid #2259B3;
+    border-radius: 4px;
+  }
+  .echarts-title {
+    font-size: 16px;
+    font-weight: 400;
+    color: #31A4FD;
+    line-height: 16px;
+    padding: 18px 18px 0 18px;
+  }
+  .echarts-sub-title {
+    font-size: 12px;
+    color: #fff;
+    padding: 20px 18px 0 18px;
+  }
+}
+.echart-detail {
+  width: 100%;
+  height: 290px;
+}
+// .echart-pie {
+//   width: 100%;
+//   height: 350px;
+// }
+.current-item {
+  background: linear-gradient(-79deg, #0185EA, #9FD0F5);
+}
+>>> .table-legend-list .ivu-table-cell{
+    display: flex;
+    align-items: center;
+    justify-content: center;
+}
+.table-legend {
+  width: 12px;
+  height: 12px;
+  border-radius: 4px;
+  display:inline-block;
+}
+.report-echarts-table {
+  padding: 20px 40px;
+}
+.report-echarts-right-table {
+  padding-top: 0;
+  padding-left: 0;
+}
+>>> .report-table-detail .ivu-table-stripe-even td {
+  background-color: #0F2D5E;
+  height: 40px;
+}
+>>> .report-table-detail .ivu-table-stripe-odd td {
+  background-color: #15376F;
+  height: 40px;
+}
+>>> .report-echarts-table .ivu-table .ivu-table-header .ivu-table-cell {
+ white-space: pre;
+}
+>>> .ivu-row .ivu-col {
+ position: static;
+}
+>>> .quality-table-cell span{
+  color:#5EB6FC;
+}
+>>> .total-records-table-cell span {
+  color: #42C151;
+}
+>>> .total-exceptions-table-cell span {
+  color: #D70101;
+}
+</style>

+ 2 - 1
src/main.js

@@ -8,13 +8,14 @@ import './assets/styles/common.css';
 import './assets/iconfont/iconfont.css';
 import store from './store'
 // import 'lib-flexible'
-import {get,post,patch,put,deletefn} from './libs/http.js';
+import {get,post,patch,put,deletefn,axiosAll} from './libs/http.js';
 //定义全局变量
 Vue.prototype.$post = post
 Vue.prototype.$get = get
 Vue.prototype.$patch = patch
 Vue.prototype.$put = put
 Vue.prototype.$deletefn = deletefn
+Vue.prototype.$axiosAll = axiosAll
 import Common from './components/common' //自定义通用全局组件
 // 注册自定义通用全局组件
 Vue.use(Common)

+ 18 - 0
src/router/index.js

@@ -3,6 +3,8 @@ import VueRouter from 'vue-router'
 import utils from '@/libs/utils'
 // import Home from '../views/Home.vue'
 const Login = ()=>import("@/login/Login.vue")
+const DownAllQualityReport = ()=>import("@/login/DownAllQualityReport.vue")
+const DownAppQualityReport = ()=>import("@/login/DownAppQualityReport.vue")
 const MainPage = ()=>import('@/views/MainPage.vue')
 const HomePage = ()=>import('@/views/homecomponents/HomePage.vue')
 const EquipmentMonitor = ()=>import('@/views/homecomponents/EquipmentAnalysis/EquipmentMonitor.vue')
@@ -22,6 +24,7 @@ const ResourceManagement = ()=>import('@/views/homecomponents/SystemSettings/Res
 const OperationLog = ()=>import('@/views/homecomponents/SystemSettings/OperationLog.vue')
 const DataMonitor = ()=>import('@/views/homecomponents/DataManagement/DataMonitor.vue')
 const DataRules = ()=>import('@/views/homecomponents/DataManagement/DataRules.vue')
+const DataReport = ()=>import('@/views/homecomponents/DataManagement/DataReport.vue')
 Vue.use(VueRouter)
 
 const routes = [
@@ -31,6 +34,16 @@ const routes = [
     component: Login,
   },
   {
+    path: '/login/DownAllQualityReport',
+    name: 'DownAllQualityReport',
+    component: DownAllQualityReport,
+  },
+  {
+    path: '/login/DownAppQualityReport',
+    name: 'DownAppQualityReport',
+    component: DownAppQualityReport,
+  },
+  {
     path: '/MainPage',
     component: MainPage,
     meta: { Auth: true }, // 添加该字段,表示进入这个路由是需要登录的
@@ -138,6 +151,11 @@ const routes = [
         name: 'DataRules', 
         component: DataRules
       },
+      {
+        path: 'DataReport', 
+        name: 'DataReport', 
+        component: DataReport
+      },
       // {
       //   path: 'BasicInfomation',
       //   component: BasicInfomation,

+ 369 - 0
src/views/homecomponents/DataManagement/DataReport.vue

@@ -0,0 +1,369 @@
+<template>
+  <div class="content-main-manage">
+    <div class="content-main">
+     <div class="content-body-wrap">
+       <div class="content-body">
+         <statistics-list :tabsInitData="tabsInitData" :tabsTitleColor="tabsTitleColor" :spanNum=0 w="20%" :unitArr="unitArr" :tabsIcon="tabsIcon" url="metroapi/dataQuality/report/statistical" ref="statistics"></statistics-list>
+          <div class="search-list">
+            <div class="search-left">
+              <Form class="common-form common-form-list" ref="tableParams" :model="tableParams" inline>
+                 <FormItem label="" prop="dataRange">
+                  <Select v-model="tableParams.appId" placeholder="来源应用">
+                    <Option v-for="item in appData" :value="item.id" :key="item.id">{{ item.appName}}</Option>
+                  </Select>
+                </FormItem>
+                <FormItem label="" prop="reportClass">
+                  <Select v-model="tableParams.reportClass" placeholder="请选择报告类型">
+                      <Option v-for="item in reportList" :value="item.value" :key="item.value">{{ item.label }}</Option>
+                    </Select>
+                </FormItem>
+                <FormItem label="" >
+                  <Button type="primary" class="common-btn-search" @click="searchClick">
+                    <Icon type="ios-search" style="margin-right:4px;font-size: 16px"/> 筛选
+                  </Button> 
+                  <Button type="primary" class="common-btn-search" style="margin-left:10px" @click="resetClick('tableParams')">
+                    <Icon type="ios-search" style="margin-right:4px;font-size: 16px"/> 重置
+                  </Button>
+                </FormItem>
+              </Form>
+            </div>
+            </div> 
+            <div class="manage-main-center">
+              <Table :columns="columns" :data="tableData" class="common-table app-table" no-data-text="" :row-class-name="rowClassName" :loading="loading">
+                <template slot="loading">
+                    <Loading-animation></Loading-animation>
+                </template>
+                 <template slot-scope="{ row }" slot="action">
+                  <Tooltip content="查看" placement="top">
+                      <i class="iconfont icon-chakan" style="cursor:pointer;color:#ebd100;fontSize:20px;marginRight:6px;vertical-align: middle" @click="lookClick(row)"></i>
+                  </Tooltip>
+                  <Tooltip content="下载" placement="top">
+                      <i class="iconfont icon-_chakanxiazai" style="cursor:pointer;color: #0bb5f4;fontSize:20px;marginRight:6px" @click="downClick(row)"></i>
+                  </Tooltip>
+                </template>
+              </Table>
+            </div>
+            <div class="common-page">
+              <div class="common-page-total">
+                共<span>{{tablePage}}</span>页 / <span>{{tableTotal}}</span>条数据
+              </div>
+              <Page :total="tableTotal" :current="tableParams.pageNum" :page-size="tableParams.pageSize" @on-change="changePage" @on-page-size-change="sizeChange" show-elevator />
+            </div>
+       </div>
+     </div>
+    </div>
+      <down-all-quality-report ref="report" class="down-report"></down-all-quality-report>
+      <down-app-quality-report ref="appReport" class="down-report"></down-app-quality-report>
+  </div>
+</template>
+<script>
+import StatisticsList from '../../../components/StatisticsList.vue'
+import DownAllQualityReport from '../../../login/DownAllQualityReport.vue'
+import DownAppQualityReport from '../../../login/DownAppQualityReport.vue';
+export default {
+  name: "DataReport",
+  components: {
+      StatisticsList,DownAllQualityReport,DownAppQualityReport
+    },
+  data() {
+    return {
+      tabsIcon: [
+        { imgSrc: require('@/assets/images/dataReport1.png') },
+        { imgSrc: require('@/assets/images/dataReport2.png') },
+        { imgSrc: require('@/assets/images/dataReport3.png') },
+        { imgSrc: require('@/assets/images/dataReport4.png') },
+        { imgSrc: require('@/assets/images/dataReport5.png') },
+      ],
+      tabsTitleColor:['#45F2FD', '#EBF310', '#54D593', '#FD7545','#fabb2e'],
+      unitArr: ['条','条','条','条','条'],
+      tabsInitData: [
+        { name: '数据质量日报', value: 0},
+        { name: '数据质量月报', value: 0},
+        { name: '数据质量年报', value: 0},
+        { name: '平台数据质量报告', value: 0},
+        { name: '应用数据质量报告', value: 0}
+      ],
+      loading: true,
+      reportList: [{label: "日报",value: 'DAY'},{label: "月报",value: 'MONTH'},{label: "年报",value: 'YEAR'}],
+      targetTypeNameList: [],
+      tableParams: {
+        appId: '',
+        reportClass: '',
+        pageNum: 1,
+        pageSize: 10
+      },
+      tableData: [],
+      tableTotal: 0,
+      tablePage: 0,
+      columns: [
+          {
+            title: '序号',
+            type: 'index',
+            align: 'center',
+            ellipsis: true,
+            tooltip: true
+          },
+           {
+            title: '报告名称',
+            key: 'reportName',
+            align: 'center',
+            ellipsis: true,
+            tooltip: true
+          },
+          {
+            title: '应用',
+            key: 'appName',
+            align: 'center',
+            ellipsis: true,
+            tooltip: true
+          },
+          {
+            title: '报告类型',
+            key: 'reportClassName',
+            align: 'center',
+            ellipsis: true,
+            tooltip: true
+          },
+          {
+            title: '创建时间',
+            key: 'createTime',
+            align: 'center',
+            ellipsis: true,
+            tooltip: true
+          },
+          {
+            title: '操作',
+            align: 'center',
+            slot: 'action',
+            width: 120,
+          }
+      ],
+      applicationParams: {
+        level: '',
+        lineId: '',
+        stationId: '',
+        equipmentCheck: '',
+        instrumentCheck: '',
+        pageNum: 1,
+        pageSize: 9999
+      },
+      appData: []
+    };
+  },
+  mounted() {
+    this.getType()
+    this.getTableData()
+  },
+  methods: {
+    rowClassName(row, index) {
+      if (index % 2 == 0) {
+        return "ivu-table-stripe-even";
+      } else {
+        return "ivu-table-stripe-odd";
+      }
+    },
+    // 分页
+    changePage (val) {
+      this.tableParams.pageNum = val
+      this.getTableData()
+    },
+    //跳转
+    sizeChange (val) {
+      this.tableParams.pageSize = val
+      this.getTableData()
+    },
+    getType  () {
+      // 指标类型数据
+      this.$get('metroapi/application/info/list', this.applicationParams).then(res=>{
+        if (res.httpCode == 1 ){
+          this.appData = res.data.data
+          this.appData.unshift({ id: '-1', appName: '来源应用' })
+        } else {
+          this.appData = []
+        }
+      })
+    },
+    // 获取表格数据
+    getTableData () {
+      let params = JSON.parse(JSON.stringify(this.tableParams))
+      params.appId= params.appId == '-1'?'':params.appId
+      this.loading = true
+      this.$get('metroapi/dataQuality/report/list?', params).then(res=>{
+        this.loading = false
+          if (res.httpCode == 1 ){
+            this.tableData = res.data.data
+            this.tableTotal = res.data.count
+            if (res.data.data.length==0) {
+              this.tablePage = 0
+            } else {
+              this.tablePage = res.data.count<= 10 ? 1: Math.ceil(res.data.count/this.tableParams.pageSize)
+            }
+            if (res.data.data.length==0 && this.tableParams.pageNum>1) {
+              this.tableParams.pageNum--
+              return this.getTableData()
+            }
+          } else {
+            this.tableData = []
+            this.tableTotal = 0
+          }
+        })
+    },
+    searchClick () {
+      this.tableParams.pageNum = 1
+      this.getTableData()
+    },
+    resetClick (name) {
+     this.$refs[name].resetFields()
+     this.tableParams.pageNum = 1
+     this.getTableData()
+    }, 
+    lookClick (row) {
+      if (row.appName == '全部') {
+        let newpage = this.$router.resolve({ 
+          path: '/login/DownAllQualityReport',
+          query: {reportClassName:row.reportClassName, beginDate:row.beginDate,endDate:row.endDate}
+        })
+        window.open(newpage.href, '_blank');
+      } else {
+        let newpage = this.$router.resolve({ 
+          path: '/login/DownAppQualityReport',
+          query: {reportClassName:row.reportClassName, beginDate:row.beginDate,endDate:row.endDate,appId:row.appId,appName:row.appName}
+        })
+        window.open(newpage.href, '_blank');
+      }
+    },
+    downClick (row) {
+      if (row.appName == '全部') {
+        this.$refs.report.downReport(row)
+      } else {
+        this.$refs.appReport.downReport(row)
+      }
+    },
+  }
+};
+</script>
+<style scoped lang="stylus">
+.content-main-manage {
+  overflow: hidden;
+  height: calc(100% - 50px);
+  width: 100%;
+}
+.content-main {
+  width: 100%;
+  height: 100%;
+}
+.content-body-wrap {
+  width: 100%;
+  height: 100%;
+  background: #06214d;
+  padding: 10px;
+}
+.content-body {
+  height: 100%;
+  position: relative;
+}
+.search-list {
+  display: flex;
+  justify-content: space-between;
+  padding: 15px 0;
+}
+.search-left {
+  display: flex;
+  align-items: center;
+   .ivu-select {
+     width: 150px;
+     height: 32px;
+   }
+   .ivu-select-single .ivu-select-selection {
+     height: 100%;
+   }
+    >>> .ivu-input {
+     width: 225px;
+     height: 32px;
+   }
+    >>> .ivu-date-picker-editor .ivu-input {
+     width: 315px;
+   }
+    >>> .ivu-input-prefix, >>> .ivu-input-suffix {
+     height: 32px;
+     line-height: 32px;
+   }
+}
+>>> .common-form-list .ivu-form-item {
+ margin-bottom: 0px;
+}
+.manage-main-center {
+  width: 100%;
+  height: calc(100% - 150px);
+}
+.common-table {
+  max-height: 100%;
+}
+>>> .common-table .ivu-table th {
+  height: 48px;
+ }
+ >>> .common-table .ivu-table td {
+  height: 47px;
+ }
+  >>> .common-table .ivu-spin-fix {
+   top: 48px;
+ }
+  >>> .app-table .ivu-spin-fix {
+   height: calc(100vh - 355px);
+ }
+ >>> .common-table .ivu-table-tip {
+  background: url('../../../assets/images/noData.png') no-repeat center;
+}
+>>> .common-table .ivu-table-tip table {
+ display: none;
+}
+>>> .app-table .ivu-table-tip {
+   height: calc(100vh - 355px);
+ }
+.common-page {
+  margin-top: 15px;
+  display: flex;
+  align-items: center;
+  justify-content: flex-end;
+  position: absolute;
+  bottom: 0;
+  right: 0;
+}
+.common-page-total {
+  color: #fff;
+  padding-right: 10px;
+  font-size: 14px;
+  span {
+    color #409EFF;
+  }
+}
+.modal-content-top-title {
+  font-size: 12px;
+  color: #fff;
+  padding-left: 8px;
+  border-left: 2px solid #0185EA;
+  height: 18px;
+  line-height: 18px;
+  margin-bottom: 20px;
+}
+.modal-content {
+  margin-top: 20px;
+}
+/* 对话框里的input里的placeholder样式修改 */
+/deep/ .ivu-input::-webkit-input-placeholder , /deep/ .ivu-input-number-input::-webkit-input-placeholder{
+  color: #718EBD;
+}
+/deep/ .ivu-input::-moz-placeholder, /deep/ .ivu-input-number-input::-webkit-input-placeholder{   /* Mozilla Firefox 19+ */
+  color: #718EBD;
+}
+/deep/ .ivu-input::-moz-placeholde, /deep/ .ivu-input-number-input::-webkit-input-placeholderr{    /* Mozilla Firefox 4 to 18 */
+ color: #718EBD;
+}
+/deep/ .ivu-input::-ms-input-placeholder, /deep/ .ivu-input-number-input::-webkit-input-placeholder{  /* Internet Explorer 10-11 */
+  color: #718EBD;
+}
+.down-report {
+  top: 0;
+  z-index: -1;
+}
+</style>

+ 5 - 48
src/views/homecomponents/DataManagement/DataRules.vue

@@ -135,7 +135,7 @@ import TabsList from '../../../components/TabsList.vue'
 import RuleStepTwo from './QualityRules/RuleStepTwo.vue'
 import RuleStepThree from './QualityRules/RuleStepThree.vue'
 import RuleStepFour from './QualityRules/RuleStepFour.vue'
-const defaultFrom = {ruleName:'',targetType:'',targetName: '',ruleDesc:'',applicationId:'',applicationName: '',equipmentTypeCode:'',field:'',expr: '',dataType:'all',dataValue:'',logicalValueDTOList:[],exprDesc: ''}
+const defaultFrom = {ruleName:'',targetType:'',targetName: '',ruleDesc:'',applicationId:'',applicationName: '',equipmentTypeCode:'',field:'',expr: '',dataType:'all',dataValue:null,logicalValueDTOList:[],exprDesc: ''}
 export default {
   name: "DataRules",
   components: {
@@ -256,7 +256,6 @@ export default {
             width: 120,
           }
       ],   
-      roleData: [], 
       showModal: false,
       modalStatus: false,
       title: '新增规则',
@@ -265,8 +264,7 @@ export default {
       activeClass: '',
       modalTitle: '',
       currentStep: 1,
-      formOption: {ruleName:'',targetType:'',targetName: '',ruleDesc:'',applicationId:'',applicationName: '',equipmentTypeCode:'',field:'',expr: '',dataType:'all',dataValue: '',logicalValueDTOList:[],exprDesc: ''},
-      // formOption: {"name":"","ruleType":"","moduleName":"","targetTypeNameId":'',"targetTypeName":"","businessTypeId":'',"ruleDescription":"","field":"","unit":" ","formulaJsonMap":{}},
+      formOption: {ruleName:'',targetType:'',targetName: '',ruleDesc:'',applicationId:'',applicationName: '',equipmentTypeCode:'',field:'',expr: '',dataType:'all',dataValue: null,logicalValueDTOList:[],exprDesc: ''},
       ruleValidate: {
         ruleName: [{
           required: true,
@@ -285,37 +283,11 @@ export default {
           trigger: 'blur'
         }],
       }, 
-      // columnsModal: [
-      //   {
-      //       title: '业务类型',
-      //       key: 'businessTypeName',
-      //       align: 'center',
-      //       ellipsis: true,
-      //       tooltip: true
-      //     },
-      //     {
-      //       title: '应用ID',
-      //       key: 'appCode',
-      //       align: 'center',
-      //       ellipsis: true,
-      //       tooltip: true
-      //     },
-      //     {
-      //       title: '应用名称',
-      //       key: 'appName',
-      //       align: 'center',
-      //       ellipsis: true,
-      //       tooltip: true
-      //     },
-      // ],
-      // modalAppData: [],
-      index: 0,
-      appModalId: null,
+      rowObj: {},
     };
   },
   mounted() {
     this.getType()
-    this.getRoleList()
     this.getTableData()
   },
   methods: {
@@ -373,7 +345,6 @@ export default {
         this.loading = false
           if (res.httpCode == 1 ){
             this.tableData = res.data.data
-            this.modalAppData = res.data.data
             this.tableTotal = res.data.count
             if (res.data.data.length==0) {
               this.tablePage = 0
@@ -402,21 +373,8 @@ export default {
      this.tableParams.pageNum = 1
      this.getTableData()
     },   
-    getRoleList () {
-      //获取角色名称
-      // this.$get('metroapi/role/box').then(res=>{
-      //   if (res.httpCode == 1 ){
-      //     this.roleModalData = JSON.parse(JSON.stringify(res.data))
-      //     this.targetTypeNameList = res.data
-      //     this.targetTypeNameList.unshift({ value: '-1', label: '指标类型' })
-      //   } else {
-      //     this.targetTypeNameList = []
-      //   }
-      // })
-    }, 
     addClick () {
       this.formOption = JSON.parse(JSON.stringify(defaultFrom))
-      // this.appModalId = 172
       this.currentStep = 1
       this.title = '新增规则'
       this.showModal = true
@@ -424,9 +382,10 @@ export default {
      editClick (row) {
       this.currentStep = 1
       this.rowObj = row
-      // this.formOption = JSON.parse(JSON.stringify(row));
+      // this.rowObj.dataValue = Number(this.rowObj.dataValue)
       this.title = '编辑规则'
       this.showModal = true
+      // this.formOption = JSON.parse(JSON.stringify(this.rowObj));
       this.formOption = JSON.parse(JSON.stringify(row));
       this.formOption.equipmentTypeCode = !this.formOption.equipmentTypeCode ? 0 : this.formOption.equipmentTypeCode
     },
@@ -483,7 +442,6 @@ export default {
     saveRule () {
       let params = JSON.parse(JSON.stringify(this.formOption))
       params.equipmentTypeCode = params.equipmentTypeCode== '展示全部字段' ? '': params.equipmentTypeCode
-      console.log('params',params)
       this.saveData(params)
     },
     commonOk () {
@@ -536,7 +494,6 @@ export default {
       } else {
         this.formOption.field = obj.id
       }
-      console.log('formOption', this.formOption)
     },
     selectModalBusiness (option) {
       if (option) {

+ 11 - 15
src/views/homecomponents/DataManagement/QualityRules/RuleStepFour.vue

@@ -39,25 +39,23 @@
               <=
             </Col>
             <Col span="20" class="timeliness-form-col"> 
-            {{ruleObj.dataValue}}
+            {{ruleObj.dataValue}}ms
             </Col>
           </Row>
          </div>
          <div v-show="ruleObj.targetName=='准确性'" class="common-form-detail-text"> 
-          <Row v-for="(item, index) in accuracyArr" :key="index" class="common-form-detail-row">
-            <Col span="4">条件{{index+1}}:</Col>
-            <Col span="3">{{item.fieldName}}</Col>
-            <Col span="4" class="timeliness-form-col timeliness-form-col-select">
-              {{item.logical}}
-            </Col>
-            <Col span="13" class="timeliness-form-col">
-            {{item.reation}}
+          <Row v-for="(item, index) in ruleObj.logicalValueDTOList" :key="index" class="common-form-detail-row">
+            <Col span="3">条件{{index+1}}:</Col>
+            <Col span="5">{{ruleObj.field}}</Col>
+            <Col span="1" class="timeliness-form-col timeliness-form-col-select">{{item.logical}}</Col>
+            <Col span="14" class="timeliness-form-col">
+            {{item.value}}
             </Col>
           </Row>
-          <Row v-if="accuracyArr.length>1" class="common-form-detail-row">
+          <Row v-if="ruleObj.logicalValueDTOList && ruleObj.logicalValueDTOList.length>1" class="common-form-detail-row">
             <Col span="7">各条件间关系表达式:</Col>
             <Col span="17">
-              fffffff
+              {{ruleObj.exprDesc}}
             </Col>
           </Row>
          </div>
@@ -81,21 +79,18 @@ export default {
   data() {
     return {
       ruleObj: {},
-      accuracyArr: [{fieldName: 'lat',logical:'<',reation: '10'},{fieldName: 'lat',logical:'>',reation: '0'}]
     };
   },
   watch: {
     currentObj: {
      handler(newValue) {
       this.ruleObj = newValue
-      console.log('RuleStepFour',newValue)
       },
       // deep: true
     }
    },
   mounted() {
     this.ruleObj = this.currentObj
-     console.log('RuleStepFourmounted',this.ruleObj)
   },
   methods: {
    
@@ -119,9 +114,10 @@ export default {
  padding: 15px;
  border: 1px solid #204A8F;
  border-top: none;
+ height: 388px;
 }
 .modal-step2-body-fixed {
-  height: 290px;
+  height: 387px;
   overflow: hidden;
   overflow-y: auto;
 }

+ 69 - 82
src/views/homecomponents/DataManagement/QualityRules/RuleStepThree.vue

@@ -26,53 +26,49 @@
         <div class="rule integrity-rule" v-show="ruleObj.targetName=='完整性'">
           <div v-show="showIntegrity">
             {{inText}} 
-            <!-- <i v-show="inText" class="iconfont icon-shanchu ivu-col-del" style="cursor:pointer; color:#BC2020;padding-left:6px" @click="removeIntegrity"></i> -->
           </div>
         </div>      
         <div class="rule uniformity-rule" v-show="ruleObj.targetName=='一致性'">
           <div v-show="showUniformity1">数据处理前字段值 = 数据处理后字段值
-            <!-- <i class="iconfont icon-shanchu ivu-col-del" style="cursor:pointer; color:#BC2020;padding-left:6px" @click="removeUniformity(1)"></i> -->
           </div>
           <div class="uniformity-rule-mode" v-show="showUniformity2">
             数据类型为&nbsp;
             <Select v-model="ruleObj.dataType" placeholder="数据类型" style="width: 166px">
               <Option v-for="item in dataTypeList" :value="item.value" :key="item.value">{{ item.label }}</Option>
             </Select>
-            <!-- <i class="iconfont icon-shanchu ivu-col-del" style="cursor:pointer; color:#BC2020;padding-left:6px" @click="removeUniformity(2)"></i> -->
           </div>
         </div>
         <div class="rule timeliness-rule" v-show="ruleObj.targetName=='及时性(数据采集)'">
           <Form ref="formDynamicTime1" :model="formCustom" :label-width="0" class="timeliness-form" v-show="showTimeliness1">
             <Row v-for="(item, index) in formCustom.timelinArry1" :key="index">
-              <!-- <Col span="1">{{item.indexMode}}</Col> -->
               <Col span="2">数据采集</Col>
               <Col span="1">{{item.logical}}</Col>
               <Col span="4" class="timeliness-form-col">
-                <FormItem :prop="'timelinArry1.'+index+'.dataValue'" :rules="{required: true,message: '请输入判断条件',trigger: 'blur'}">
-                  <Input placeholder="判断条件" clearable v-model="item.dataValue" />
+                <FormItem :prop="'timelinArry1.'+index+'.dataValue'" :rules="{required: true,type:'number',message: '请输入判断条件',trigger: 'blur'}">
+                  <InputNumber v-model="item.dataValue" placeholder="判断条件" :min="1" :max="100000000" :active-change="false"></InputNumber>
                 </FormItem>
               </Col>
-              <!-- <Col span="2"><i class="iconfont icon-shanchu ivu-col-del" style="cursor:pointer; color:#BC2020;padding-left:6px"  @click="removeTimeliness(index)"></i></Col> -->
+              <Col span="1"><span class="timeliness-rule-unit">ms</span></Col>
             </Row>
           </Form>
         </div>
         <div class="rule timeliness-rule" v-show="ruleObj.targetName=='及时性(数据入库)'">
           <Form ref="formDynamicTime2" :model="formCustom" :label-width="0" class="timeliness-form" v-show="showTimeliness2">
             <Row v-for="(item, index) in formCustom.timelinArry2" :key="index">
-              <!-- <Col span="1">{{item.indexMode}}</Col> -->
               <Col span="2">数据入库</Col>
               <Col span="1">{{item.logical}}</Col>
               <Col span="4" class="timeliness-form-col">
-                <FormItem :prop="'timelinArry2.'+index+'.dataValue'" :rules="{required: true,message: '请输入判断条件',trigger: 'blur'}">
-                  <Input placeholder="判断条件" clearable v-model="item.dataValue" />
+                <FormItem :prop="'timelinArry2.'+index+'.dataValue'" :rules="{required: true,type:'number',message: '请输入判断条件',trigger: 'blur'}">
+                  <InputNumber v-model="item.dataValue" placeholder="判断条件" :min="1" :max="100000000" :active-change="false"></InputNumber>
                 </FormItem>
               </Col>
-              <!-- <Col span="2"><i class="iconfont icon-shanchu ivu-col-del" style="cursor:pointer; color:#BC2020;padding-left:6px"  @click="removeTimeliness(index)"></i></Col> -->
+              <Col span="1"><span class="timeliness-rule-unit">ms</span></Col>
             </Row>
           </Form>
         </div>
         <div class="rule timeliness-rule common-scroll" v-show="ruleObj.targetName=='准确性'">
-          <Form ref="formDynamic" :model="formCustomAcc" :label-width="0" class="timeliness-form" v-show="showAccuracy">
+          <Form ref="formDynamicAcc" :model="formCustomAcc" :label-width="0" class="timeliness-form" v-show="showAccuracy">
+            <!-- <template v-if="formCustomAcc.accuracyArr && formCustomAcc.accuracyArr.length>0"> -->
             <Row v-for="(item, index) in formCustomAcc.accuracyArr" :key="index">
               <Col span="1">条件{{index+1}}</Col>
               <Col span="3">{{ruleObj.field}}</Col>
@@ -84,24 +80,25 @@
                 </FormItem>
               </Col>
               <Col span="4" class="timeliness-form-col">
-                <FormItem :prop="'accuracyArr.'+index+'.value'" :rules="{required: clickbtn==1 ? true: false,message: '请输入判断条件',trigger: 'blur'}">
-                  <Input placeholder="判断条件" clearable v-model="item.value" />
+                <FormItem :prop="'accuracyArr.'+index+'.value'" :rules="{required: clickbtn==1 ? true: false,type:'number',message: '请输入判断条件',trigger: 'blur'}">
+                  <InputNumber v-model.trim="item.value" placeholder="判断条件" :max="100000000" :active-change="false"></InputNumber>
                 </FormItem>
               </Col>
               <Col span="2">
-                <i class="iconfont icon-tianjia" style="cursor:pointer;color:#2DA0F8;;padding-left:10px" @click="handleAddAcc('formDynamic')"></i>
+                <i class="iconfont icon-tianjia" style="cursor:pointer;color:#2DA0F8;;padding-left:10px" @click="handleAddAcc('formDynamicAcc')"></i>
                 <i class="iconfont icon-shanchu ivu-col-del" style="cursor:pointer; color:#BC2020;padding-left:6px"  @click="removeAccliness(index)"></i>
               </Col>
             </Row>
             <Row v-if="formCustomAcc.accuracyArr && formCustomAcc.accuracyArr.length>1">
-              <Col span="3">各条件间关系表达式</Col>
-              <Col span="21">
+              <Col span="4">各条件间关系表达式</Col>
+              <Col span="20" class="accuracy-last-relation">
                <FormItem prop="exprDesc" :rules="{required: clickdel ? true: false,message: '请输入各条件间关系表达式',trigger: 'blur'}">
-                 <Input placeholder="条件1&&条件2" clearable v-model="formCustomAcc.exprDesc" />
+                 <Input placeholder="条件1&&条件2" clearable v-model.trim="formCustomAcc.exprDesc" />
                 </FormItem>    
              </Col>
             </Row>
-          </Form>       
+            <!-- </template> -->
+          </Form>     
         </div>
       </div>
     </div>
@@ -123,43 +120,34 @@ export default {
   data() {
     return {
       ruleObj: {},
-      defaulTtimelinArry:[
-        { indexMode: '条件1',name: '数据采集',logical: '<='},
-        { indexMode: '条件2',name: '数据入库',logical: '<='},
-      ],
       formCustom: {
         timelinArry1: [
-          {name: '数据采集',logical: '<=',dataValue:''},
+          {name: '数据采集',logical: '<=',dataValue:null},
         ],
         timelinArry2:[
-          {name: '数据入库',logical: '<=',dataValue:''}
+          {name: '数据入库',logical: '<=',dataValue:null}
         ],
       },
       inText: '',
       dataTypeList: [{label:'任意',value:'all'},{label:'short',value:'short'},{label:'int',value:'int'},{label:'long',value:'long'},{label:'float',value:'float'},{label:'double',value:'double'},{label:'char',value:'char'},{label:'boolean',value:'boolean'},{label:'BigDecimal',value:'BigDecimal'},{label:'String',value:'String'}],
       // dataType: 'all',
       showIntegrity: false,
-      // UniformityIndex: 0,
       showUniformity1: false,
       showUniformity2: false,
       showTimeliness1: false,
       showTimeliness2: false,
       showAccuracy: false,
       symbloList: [
-        { value: '=', label: '=' },
+        { value: '==', label: '==' },
         { value: '!=', label: '!=' },
         { value: '>', label: '>' },
         { value: '<', label: '<' },
         { value: '>=', label: '>=' },
-        { value: '<=', label: '<=' },
-        { value: '[,]', label: '[,]' },
-        { value: '[,)', label: '[,)' },
-        { value: '(,]', label: '(,]' },
-        { value: '(,)', label: '(,)' }
+        { value: '<=', label: '<=' } 
       ],
       formCustomAcc: {
         accuracyArr: [{
-          logical: '',value:''
+          logical: '',value:null
         }],
         exprDesc:''
       },
@@ -170,9 +158,7 @@ export default {
   watch: {
     currentObj: {
      handler(newValue) {
-      //  console.log(newValue)
        this.ruleObj = newValue
-       console.log(this.ruleObj.dataType)
        this.showRule()
       },
       // deep: true
@@ -192,10 +178,6 @@ export default {
        this.inText = '不能是字符串null、NULL、无、空格,不能是空'
         this.showIntegrity = true
       } else if (this.ruleObj.targetName == '一致性') {
-        // console.log()
-        // if (this.ruleObj.dataType) {
-        //   this.showUniformity2 = true
-        // }
         this.showUniformity1 = true
         this.showUniformity2 = true
       } else if (this.ruleObj.targetName == '及时性(数据采集)') {
@@ -204,80 +186,87 @@ export default {
         this.showTimeliness2 = true
       } else if (this.ruleObj.targetName == '准确性') {
         this.showAccuracy = true
+        if (this.formCustomAcc.accuracyArr && this.formCustomAcc.accuracyArr.length>1) {
+          this.clickdel = true
+        }
       }
     },
-    handleAdd (targetNameName) {
+    handleAdd (targetName) {
       this.inText = ''
       this.showUniformity1 = false
       this.showUniformity2 = false
       this.showTimeliness1 = false
       this.showTimeliness2 = false
-      this.showAccuracy = false
-      if (targetNameName == '完整性') {
+      if (targetName == '完整性') {
        this.inText = '不能是字符串null、NULL、无、空格,不能是空'
        this.showIntegrity = true
-      } else if (targetNameName == '一致性') {
+      } else if (targetName == '一致性') {
        this.showUniformity1 = true
        this.showUniformity2 = true
-      } else if (this.ruleObj.targetName == '及时性(数据采集)') {
-        // this.formCustom.timelinArry = JSON.parse(JSON.stringify(this.defaulTtimelinArry))
+      } else if (targetName == '及时性(数据采集)') {
         this.showTimeliness1 = true
-      } else if (this.ruleObj.targetName == '及时性(数据入库)') {
-        // this.formCustom.timelinArry = JSON.parse(JSON.stringify(this.defaulTtimelinArry))
+      } else if (targetName == '及时性(数据入库)') {
         this.showTimeliness2 = true
-      } else if (targetNameName == '准确性') {
+      } else if (targetName == '准确性') {
+        if (this.showAccuracy) return;
         this.clickbtn = 1
         this.formCustomAcc.accuracyArr = [{
-          logical: '',value:''
+          logical: '',value:null
         }]
         this.showAccuracy = true
-        console.log(this.showAccuracy)
       }
     },
-    removeIntegrity () { 
-      this.showIntegrity = false
-    },
-    //删除一致性
-   removeUniformity (i) {
-     if (i == 1) {
-       this.showUniformity1 = false
-     } else {
-       this.showUniformity2 = false
-       this.ruleObj.dataType = ''
-     }
-   },
-   removeTimeliness (i) {
-    this.formCustom.timelinArry.splice(i,1)
-    if (i == 0) {
-     this.showTimeliness1 = false 
-    } else if (i == 1) {
-      this.showTimeliness2 = false
-    }
-   },
+     // 删除完整性
+  //   removeIntegrity () { 
+  //     this.showIntegrity = false
+  //   },
+  //   //删除一致性
+  //  removeUniformity (i) {
+  //    if (i == 1) {
+  //      this.showUniformity1 = false
+  //    } else {
+  //      this.showUniformity2 = false
+  //      this.ruleObj.dataType = ''
+  //    }
+  //  },
+  //  // 删除及时性
+  //  removeTimeliness (i) {
+  //   this.formCustom.timelinArry.splice(i,1)
+  //   if (i == 0) {
+  //    this.showTimeliness1 = false 
+  //   } else if (i == 1) {
+  //     this.showTimeliness2 = false
+  //   }
+  //  },
    handleAddAcc (name) {
      this.clickdel = false
      this.clickbtn = 1
      this.$nextTick(()=> {
        this.$refs[name].validate((valid) => {
         if(valid) {
+          this.formCustomAcc.exprDesc = ''
           this.formCustomAcc.accuracyArr.push({
             logical: '',
-            value: '',
+            value: null,
           });
+          if (this.formCustomAcc.accuracyArr.length>1) {
+            this.clickdel = true
+          }
         }
       })
      })
    },
-   // 删除完整
+   // 删除准确
    removeAccliness (index) {
      this.clickbtn = 2
      this.formCustomAcc.accuracyArr.splice(index,1)
      if (this.formCustomAcc.accuracyArr.length ==0) {
        this.showAccuracy = false
-    }
+     }
    },
    // 当前步骤校验方法
     saveValid () {
+        // 前两行是为了检验准确性
       if (this.ruleObj.targetName == '完整性') {
         if (!this.showIntegrity) {
           this.$Message.info('请配置完整性规则')
@@ -312,11 +301,9 @@ export default {
             this.$refs.formDynamicTime2.validate((valid) => {
               validType = valid
             })
-            console.log('入库',validType)
             return validType
         }
       } else if (this.ruleObj.targetName == '准确性') {
-         // 前两行是为了检验准确性
         this.clickbtn = 1
         this.clickdel = true
         if (!this.showAccuracy) {
@@ -324,7 +311,7 @@ export default {
           return false
           } else {
             let validType = false
-            this.$refs.formDynamic.validate((valid) => {
+            this.$refs.formDynamicAcc.validate((valid) => {
               validType = valid
             })
             return validType
@@ -394,27 +381,27 @@ export default {
   align-items: center;
   margin-bottom: 20px;
   height: 100%;
-  // border: 1px solid red;
 }
 >>> .timeliness-form .ivu-col{
   height: 100%;
 }
->>> .timeliness-form .timeliness-form-col {
-  // display: flex;
-  // align-items: center;
-}
 >>> .timeliness-form-col .ivu-form-item{
   width: 100%;
   height: 100%;
   margin-bottom: 0;
   .ivu-form-item-content {
     width: 100%;
-    // padding: 10px 5px;
   }
 }
 .timeliness-form-col-select {
   padding-right: 10px;
 }
+.timeliness-rule-unit {
+  padding-left: 10px;
+}
+>>> .accuracy-last-relation .ivu-form-item{
+  margin-bottom: 0;
+}
 .common-scroll {
   max-height: 300px;
   overflow: hidden;

+ 1 - 8
src/views/homecomponents/DataManagement/QualityRules/RuleStepTwo.vue

@@ -156,7 +156,6 @@ export default {
               }
             })
           }
-          // console.log(this.appModalData)
         } else {
           this.appModalData = []
         }
@@ -275,11 +274,6 @@ export default {
     },
     // 当前步骤校验方法
     saveValid () {
-      console.log(this.equipmentTypeCode)
-      // console.log(this.fieldModalData)
-      console.log(this.fieldModalData.length>0)
-      console.log(!this.fieldCode)
-      // console.log(this.currentObj.equipmentTypeCode)
       if (!this.applicationId) {
         this.$Message.info('请选择来源应用')
         return false
@@ -289,8 +283,7 @@ export default {
       } else if (this.fieldCode == ''){
         this.$Message.info('请选择字段')
         return false
-      } 
-      else {
+      } else {
         return true
       }
     }

+ 1 - 0
src/views/homecomponents/EquipmentAnalysis/LevelDeterConfig.vue

@@ -750,6 +750,7 @@ export default {
     getstrategyData (id) {
       this.$get('metroapi/alert/getStrategy', {strategyId:id}).then(res=>{
         if ( res.httpCode == 1 ){
+          this.appModalName = res.data.appName
           this.detailLabel = [{name:'基础信息',arr:[{name:'策略名称',value:res.data.strategyName},{name:'设备类型',value:res.data.equipmentTypeName},{name:'来源应用',value:res.data.appName}]}]
           this.formCustom.alertStrategyRankDTOList = res.data.alertStrategyRankDTOList
           if (this.formCustom.alertStrategyRankDTOList && this.formCustom.alertStrategyRankDTOList.length>1) {

+ 1 - 1
vue.config.js

@@ -7,7 +7,7 @@ module.exports = {
       open: false,//配置自动启动浏览器 
       proxy: { // 设置代理
       '/metroapi': {
-        target: 'http://192.168.20.188:8088',// http://192.168.20.58:8086 http://192.168.20.188:8088
+        target: 'http://192.168.20.58:8088',// http://192.168.20.58:8086 http://192.168.20.188:8088
         changeOrigin: true, //允许跨域
         pathRewrite: {
             '^/metroapi': ''

部分文件因为文件数量过多而无法显示