recallJt.vue 9.2 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391
  1. <template>
  2. <div class="container" style="margin: 15px 0 0 0" v-loading="loading">
  3. <fullscreen :fullscreen.sync="fullscreen" class="container-box"
  4. style="margin: 0 !important; padding: 0 !important">
  5. <div class="titbox">
  6. <h2>集团绩效</h2>
  7. <div>
  8. <i class="el-icon-refresh" @click="iconCli(1)"></i>
  9. <i class="el-icon-full-screen" @click="iconCli(2)"></i>
  10. </div>
  11. </div>
  12. <el-tabs tab-position="top" v-model="activeName" @tab-click="handleClick">
  13. <el-tab-pane name="0" label="KPI"></el-tab-pane>
  14. <!-- <el-tab-pane name="1" label="GS"></el-tab-pane>-->
  15. </el-tabs>
  16. <div style="height: 100%">
  17. <div style="overflow: none">
  18. <el-date-picker v-model="monthValue" @change="checkMonth" value-format="yyyy-MM" type="month"
  19. placeholder="选择月">
  20. </el-date-picker>
  21. <div style="float: right">
  22. <el-button v-if="dataBody.task.sts == '0' && dataBody.rows.length > 0" size="small"
  23. @click="submit" type="primary">回复</el-button>
  24. <el-button v-if="dataBody.task.sts == '0' && dataBody.rows.length > 0" size="small"
  25. @click="save" type="primary">保存</el-button>
  26. <el-button v-if="dataBody.rows.length > 0" size="small" type="primary" @click="exportExcel">导出
  27. </el-button>
  28. <el-button size="small" @click="goBack" type="primary">返回</el-button>
  29. </div>
  30. </div>
  31. <div v-if="dataBody.rows.length > 0" id="tabbox">
  32. <div style="width: 30%; margin: 15px auto">
  33. <el-input readonly v-model="dataBody.table.tabName"></el-input>
  34. </div>
  35. <table class="dataBody-box" border-collapse="collapse" border="1">
  36. <tbody>
  37. <tr v-for="(item, index) in dataBody.rows" :key="index">
  38. <td @contextmenu="showMenu(index, zindex)" class="cell" v-for="(row, zindex) in item"
  39. :key="zindex" :rowspan="row.rowSpan" :colspan="row.colSpan"
  40. v-show="row.displayFlag == '0'">
  41. <div v-show="false">
  42. {{ (dataBody.rows[index][zindex].colNum = zindex) }}
  43. {{ (dataBody.rows[index][zindex].rowNum = index) }}
  44. </div>
  45. <el-input :disabled="dataBody.task.sts != '0'" class="table-input"
  46. v-model="row.cellVal"></el-input>
  47. </td>
  48. </tr>
  49. </tbody>
  50. </table>
  51. </div>
  52. <div class="center-style" v-else>请选择需要查看的绩效</div>
  53. </div>
  54. <vue-context-menu :contextMenuData="contextMenuData" @deleteHang="deleteHang" @addHangUp="addHangUp">
  55. </vue-context-menu>
  56. </fullscreen>
  57. </div>
  58. </template>
  59. <script>
  60. export default {
  61. data() {
  62. return {
  63. contextMenuData: {
  64. menuName: "demo",
  65. //菜单显示的位置
  66. axis: {
  67. x: null,
  68. y: null,
  69. },
  70. //菜单选项
  71. menulists: [{
  72. fnHandler: "deleteHang", //绑定事件
  73. btnName: "删除行", //菜单名称
  74. },
  75. {
  76. fnHandler: "addHangUp", //绑定事件
  77. btnName: "插入行", //菜单名称
  78. },
  79. ],
  80. },
  81. activeName: "0",
  82. disabled: true,
  83. options: [],
  84. value: "",
  85. monthValue: "",
  86. isMove: false,
  87. autoStyle: {},
  88. xindex: "",
  89. yindex: "",
  90. dataBody: {
  91. rows: [],
  92. table: {
  93. opName: "",
  94. opNo: "",
  95. opTime: "",
  96. opTimeFrom: "",
  97. opTimeTo: "",
  98. tabCode: "",
  99. tabCodePks: "",
  100. tabName: "",
  101. },
  102. task: {
  103. sts: 0,
  104. },
  105. },
  106. hangIndex: "",
  107. lieIndex: "",
  108. fullscreen: false,
  109. loading: false,
  110. fileList: [],
  111. };
  112. },
  113. methods: {
  114. showMenu(index, zindex) {
  115. this.hangIndex = index;
  116. this.lieIndex = zindex;
  117. event.preventDefault();
  118. var x = event.clientX;
  119. var y = event.clientY;
  120. // Get the current location
  121. this.contextMenuData.axis = {
  122. x,
  123. y,
  124. };
  125. },
  126. // 向上增加行
  127. addHangUp() {
  128. let itemArr = [];
  129. for (let i = 0; i < this.hangIndex; i++) {
  130. this.dataBody.rows[i].map((item) => {
  131. if (
  132. this.hangIndex <= parseInt(item.rowSpan) + i - 1 &&
  133. parseInt(item.rowSpan) > 1
  134. ) {
  135. item.rowSpan = parseInt(item.rowSpan) + 1;
  136. }
  137. });
  138. }
  139. itemArr = JSON.parse(JSON.stringify(this.dataBody.rows[this.hangIndex]));
  140. itemArr.map((item) => {
  141. item.rowSpan = "1";
  142. item.cellVal = "";
  143. });
  144. this.dataBody.rows.splice(this.hangIndex, 0, itemArr);
  145. },
  146. // 删除行
  147. deleteHang() {
  148. if (
  149. parseInt(this.dataBody.rows[this.hangIndex][this.lieIndex].rowSpan) > 1
  150. ) {
  151. this.$message({
  152. message: "当前行有合并项不能删除",
  153. type: "wanrning",
  154. });
  155. return;
  156. }
  157. let num = 0;
  158. this.dataBody.rows[this.hangIndex].map((item, index) => {
  159. if (parseInt(item.rowSpan) > 1) {
  160. this.dataBody.rows[parseInt(this.hangIndex) + 1][index].displayFlag =
  161. "0";
  162. this.dataBody.rows[parseInt(this.hangIndex) + 1][index].rowSpan =
  163. parseInt(item.rowSpan) - 1;
  164. } else if (item.displayFlag == "1") {
  165. for (let i = this.hangIndex; i >= 0; i--) {
  166. num = 0;
  167. this.dataBody.rows[i].map((item, zindex) => {
  168. if (item.displayFlag == "0") {
  169. num++;
  170. }
  171. if (
  172. parseInt(item.rowSpan) > 1 &&
  173. zindex == index &&
  174. this.hangIndex <= parseInt(item.rowSpan) + i - 1
  175. ) {
  176. item.rowSpan = parseInt(item.rowSpan) - 1;
  177. }
  178. });
  179. if (num == this.dataBody.rows[i].length) {
  180. return;
  181. }
  182. }
  183. }
  184. });
  185. this.dataBody.rows.splice(this.hangIndex, 1);
  186. },
  187. handleClick(val) {
  188. this.getInitData();
  189. },
  190. // 回复
  191. submit() {
  192. this.loading = true;
  193. this.$http({
  194. url: "/market/kpidepts/saveInfo",
  195. method: "post",
  196. headers: {
  197. "Content-Type": "application/json",
  198. },
  199. data: this.dataBody,
  200. }).then((res) => {
  201. if (res.data.result == 0) {
  202. this.$message({
  203. message: "回复成功",
  204. type: "success",
  205. });
  206. this.getInitData();
  207. }
  208. this.loading = false;
  209. });
  210. },
  211. exportExcel() {
  212. this.$http({
  213. url: "/market/kpidepts/downloadKpi",
  214. method: "get",
  215. headers: {
  216. "Content-Type": "application/json",
  217. },
  218. responseType: "blob",
  219. params: {
  220. tabInstId: this.dataBody.tabInstId
  221. },
  222. }).then((response) => {
  223. if (window.navigator && window.navigator.msSaveOrOpenBlob) {
  224. let blob = new Blob([response.data], {
  225. type: "application/vnd.ms-excel",
  226. });
  227. window.navigator.msSaveOrOpenBlob(
  228. blob,
  229. this.dataBody.table.tabName + ".xlsx"
  230. );
  231. } else {
  232. /* 火狐谷歌的文件下载方式 */
  233. var blob = new Blob([response.data]);
  234. var downloadElement = document.createElement("a");
  235. var href = window.URL.createObjectURL(blob);
  236. downloadElement.href = href;
  237. downloadElement.download = this.dataBody.table.tabName + ".xlsx";
  238. document.body.appendChild(downloadElement);
  239. downloadElement.click();
  240. document.body.removeChild(downloadElement);
  241. window.URL.revokeObjectURL(href);
  242. }
  243. });
  244. },
  245. checkMonth(val) {
  246. this.getInitData();
  247. },
  248. goBack() {
  249. this.$router.push("/leader");
  250. },
  251. //功能栏
  252. iconCli(v) {
  253. if (v === 1) {
  254. this.getList(this.params, this.pageSize);
  255. }
  256. if (v === 2) {
  257. this.fullscreen = !this.fullscreen;
  258. }
  259. },
  260. // 保存
  261. save() {
  262. this.loading = true;
  263. this.$http({
  264. url: "/market/kpidepts/save",
  265. method: "post",
  266. headers: {
  267. "Content-Type": "application/json",
  268. },
  269. data: this.dataBody,
  270. }).then((res) => {
  271. if (res.data.result == 0) {
  272. this.loading = false;
  273. this.$message({
  274. message: "操作成功",
  275. type: "success",
  276. });
  277. }
  278. });
  279. },
  280. getInitData(val) {
  281. this.loading = true;
  282. this.$http({
  283. url: "/market/kpidepts/load",
  284. method: "post",
  285. headers: {
  286. "Content-Type": "application/json",
  287. },
  288. data: {
  289. kpiMonth: this.monthValue,
  290. tempType: "3",
  291. subType: this.activeName,
  292. kpiYear: "",
  293. receiveDeptCode: "",
  294. },
  295. }).then((res) => {
  296. if (res.data.result == 0) {
  297. this.dataBody = res.data.body;
  298. } else {
  299. this.$message({
  300. message: "无绩效数据",
  301. type: "success",
  302. });
  303. this.dataBody.rows = [];
  304. }
  305. this.loading = false;
  306. });
  307. },
  308. },
  309. mounted() {
  310. this.getInitData();
  311. },
  312. };
  313. </script>
  314. <style>
  315. #tabbox .el-input.is-disabled .el-input__inner {
  316. color: black;
  317. background-color: white;
  318. }
  319. .btn-wrapper-simple {
  320. height: auto !important;
  321. }
  322. </style>
  323. <style lang="scss" scoped>
  324. #tabbox {
  325. height: 65%;
  326. overflow-y: auto;
  327. }
  328. .dataBody-box {
  329. border-collapse: collapse;
  330. margin-top: 20px;
  331. .cell {
  332. position: relative;
  333. }
  334. }
  335. .fcous {
  336. border-color: red;
  337. }
  338. .center-style {
  339. display: flex;
  340. align-items: center;
  341. justify-content: center;
  342. height: 100%;
  343. }
  344. .auto-dom {
  345. width: 3px;
  346. opacity: 0;
  347. position: absolute;
  348. right: 0;
  349. top: 0;
  350. z-index: 1000;
  351. cursor: pointer;
  352. height: 100%;
  353. }
  354. </style>>
  355. <style scoped lang="scss">
  356. .btn-default {
  357. display: inline;
  358. margin-left: 10px;
  359. }
  360. .titbox {
  361. margin-bottom: 20px;
  362. div {
  363. float: right;
  364. i {
  365. font-size: 22px;
  366. margin-left: 20px;
  367. cursor: pointer;
  368. }
  369. }
  370. }
  371. .tabbox {
  372. margin-top: 15px;
  373. }
  374. .pageBox {
  375. text-align: right;
  376. margin-top: 10px;
  377. }
  378. </style>