Commit bbbd2dee85fe8c2a2f9df43c18a1b54b1a8b8930

Authored by zhangdaiscott
1 parent fd16e99a

JeecgBoot低代码平台 2.4.5 版本发布,钉钉与企业微信集成版本

Showing 225 changed files with 13144 additions and 10013 deletions

Too many changes to show.

To preserve performance only 62 of 225 files are displayed.

README.md
... ... @@ -7,12 +7,12 @@
7 7 JEECG BOOT 低代码开发平台(前后端分离版本)
8 8 ===============
9 9  
10   -当前最新版本: 2.4.3(发布日期:2021-03-22
  10 +当前最新版本: 2.4.5(发布日期:2021-06-07
11 11  
12 12  
13 13 [![AUR](https://img.shields.io/badge/license-Apache%20License%202.0-blue.svg)](https://github.com/zhangdaiscott/jeecg-boot/blob/master/LICENSE)
14 14 [![](https://img.shields.io/badge/Author-北京国炬软件-orange.svg)](http://www.jeecg.com)
15   -[![](https://img.shields.io/badge/version-2.4.3-brightgreen.svg)](https://github.com/zhangdaiscott/jeecg-boot)
  15 +[![](https://img.shields.io/badge/version-2.4.5-brightgreen.svg)](https://github.com/zhangdaiscott/jeecg-boot)
16 16 [![GitHub stars](https://img.shields.io/github/stars/zhangdaiscott/jeecg-boot.svg?style=social&label=Stars)](https://github.com/zhangdaiscott/jeecg-boot)
17 17 [![GitHub forks](https://img.shields.io/github/forks/zhangdaiscott/jeecg-boot.svg?style=social&label=Fork)](https://github.com/zhangdaiscott/jeecg-boot)
18 18  
... ... @@ -23,7 +23,7 @@ JEECG BOOT 低代码开发平台(前后端分离版本)
23 23  
24 24 <h3 align="center">Java Low Code Platform for Enterprise web applications</h3>
25 25  
26   -JeecgBoot 是一款基于代码生成器的`低代码`开发平台!前后端分离架构 SpringBoot2.x,SpringCloud,Ant Design&Vue,Mybatis-plus,Shiro,JWT,支持微服务。强大的代码生成器让前后端代码一键生成,实现低代码开发! JeecgBoot 引领新的低代码开发模式(OnlineCoding-> 代码生成器-> 手工MERGE), 帮助解决Java项目70%的重复工作,让开发更多关注业务。既能快速提高效率,节省研发成本,同时又不失灵活性!
  26 +JeecgBoot 是一款基于代码生成器的`低代码平台`!前后端分离架构 SpringBoot2.x,SpringCloud,Ant Design&Vue,Mybatis-plus,Shiro,JWT,支持微服务。强大的代码生成器让前后端代码一键生成,实现低代码开发! JeecgBoot 引领新的低代码开发模式(OnlineCoding-> 代码生成器-> 手工MERGE), 帮助解决Java项目70%的重复工作,让开发更多关注业务。既能快速提高效率,节省研发成本,同时又不失灵活性!
27 27  
28 28 JeecgBoot 提供了一系列`低代码模块`,实现在线开发`真正的零代码`:Online表单开发、Online报表、报表配置能力、在线图表设计、大屏设计、移动配置能力、表单设计器、在线设计流程、流程自动化配置、插件能力(可插拔)等等!
29 29  
... ...
ant-design-vue-jeecg/README.md
1 1 Ant Design Jeecg Vue
2 2 ====
3 3  
4   -当前最新版本: 2.4.3(发布日期:20210322
  4 +当前最新版本: 2.4.5(发布日期:20210607
5 5  
6 6 Overview
7 7 ----
8 8  
9 9 基于 [Ant Design of Vue](https://vuecomponent.github.io/ant-design-vue/docs/vue/introduce-cn/) 实现的 Ant Design Pro Vue 版
10   -Jeecg-boot 的前UI框架,采用前后端分离方案,提供强大代码生成器的低代码平台。
  10 +Jeecg-boot 的前UI框架,采用前后端分离方案,提供强大代码生成器的低代码平台。
11 11 前端页面代码和后端功能代码一键生成,不需要写任何代码,保持jeecg一贯的强大!!
12 12  
13 13  
... ...
ant-design-vue-jeecg/package-lock.json
1 1 {
2 2 "name": "vue-antd-jeecg",
3   - "version": "2.4.3",
  3 + "version": "2.2.1",
4 4 "lockfileVersion": 1,
5 5 "requires": true,
6 6 "dependencies": {
7 7 "@ant-design/colors": {
8 8 "version": "3.2.2",
9   - "resolved": "https://registry.npm.taobao.org/@ant-design/colors/download/@ant-design/colors-3.2.2.tgz",
10   - "integrity": "sha1-WtQ9YZ6RHzSI66wwPWBuZqhCOQM=",
  9 + "resolved": "https://registry.npmjs.org/@ant-design/colors/-/colors-3.2.2.tgz",
  10 + "integrity": "sha512-YKgNbG2dlzqMhA9NtI3/pbY16m3Yl/EeWBRa+lB1X1YaYxHrxNexiQYCLTWO/uDvAjLFMEDU+zR901waBtMtjQ==",
11 11 "requires": {
12 12 "tinycolor2": "^1.4.1"
13 13 }
14 14 },
15 15 "@ant-design/icons": {
16 16 "version": "2.1.1",
17   - "resolved": "https://registry.npm.taobao.org/@ant-design/icons/download/@ant-design/icons-2.1.1.tgz?cache=0&sync_timestamp=1612952243741&other_urls=https%3A%2F%2Fregistry.npm.taobao.org%2F%40ant-design%2Ficons%2Fdownload%2F%40ant-design%2Ficons-2.1.1.tgz",
18   - "integrity": "sha1-e5wI3/1PXUHbZn2dvl4BB9C9mko="
  17 + "resolved": "https://registry.npmjs.org/@ant-design/icons/-/icons-2.1.1.tgz",
  18 + "integrity": "sha512-jCH+k2Vjlno4YWl6g535nHR09PwCEmTBKAG6VqF+rhkrSPRLfgpU2maagwbZPLjaHuU5Jd1DFQ2KJpQuI6uG8w=="
19 19 },
20 20 "@ant-design/icons-vue": {
21 21 "version": "2.0.0",
22   - "resolved": "https://registry.npm.taobao.org/@ant-design/icons-vue/download/@ant-design/icons-vue-2.0.0.tgz?cache=0&other_urls=https%3A%2F%2Fregistry.npm.taobao.org%2F%40ant-design%2Ficons-vue%2Fdownload%2F%40ant-design%2Ficons-vue-2.0.0.tgz",
23   - "integrity": "sha1-A1f1AQpATp80qHpLQbKgjfaR284=",
  22 + "resolved": "https://registry.npmjs.org/@ant-design/icons-vue/-/icons-vue-2.0.0.tgz",
  23 + "integrity": "sha512-2c0QQE5hL4N48k5NkPG5sdpMl9YnvyNhf0U7YkdZYDlLnspoRU7vIA0UK9eHBs6OpFLcJB6o8eJrIl2ajBskPg==",
24 24 "requires": {
25 25 "@ant-design/colors": "^3.1.0",
26 26 "babel-runtime": "^6.26.0"
... ... @@ -1417,18 +1417,18 @@
1417 1417 "dev": true
1418 1418 },
1419 1419 "@simonwep/pickr": {
1420   - "version": "1.7.4",
1421   - "resolved": "https://registry.npm.taobao.org/@simonwep/pickr/download/@simonwep/pickr-1.7.4.tgz",
1422   - "integrity": "sha1-sU/NlFiQOIuHDNbbTWx41THyUUE=",
  1420 + "version": "1.7.1",
  1421 + "resolved": "https://registry.npmjs.org/@simonwep/pickr/-/pickr-1.7.1.tgz",
  1422 + "integrity": "sha512-ftbskrPKAkRLYVj8IhV4Bn86g16It9Uq/p4G0FdjRz36pKKjW0JdxdDWDIVuAev0Urg8604Ho98js6JmjXdiZQ==",
1423 1423 "requires": {
1424 1424 "core-js": "^3.6.5",
1425   - "nanopop": "^2.1.0"
  1425 + "nanopop": "^1.3.0"
1426 1426 },
1427 1427 "dependencies": {
1428 1428 "core-js": {
1429   - "version": "3.9.1",
1430   - "resolved": "https://registry.npm.taobao.org/core-js/download/core-js-3.9.1.tgz?cache=0&other_urls=https%3A%2F%2Fregistry.npm.taobao.org%2Fcore-js%2Fdownload%2Fcore-js-3.9.1.tgz",
1431   - "integrity": "sha1-zsjeWT246yqF/7Db3rMSy25UYK4="
  1429 + "version": "3.6.5",
  1430 + "resolved": "https://registry.npmjs.org/core-js/-/core-js-3.6.5.tgz",
  1431 + "integrity": "sha512-vZVEEwZoIsI+vPEuoF9Iqf5H7/M3eeQqWlQnYa8FSKKePuYTf5MWnxb5SDAzCa60b3JBRS5g9b+Dq7b1y/RCrA=="
1432 1432 }
1433 1433 }
1434 1434 },
... ... @@ -1443,6 +1443,11 @@
1443 1443 "string-width": "^2.0.0"
1444 1444 }
1445 1445 },
  1446 + "@sphinxxxx/color-conversion": {
  1447 + "version": "2.2.2",
  1448 + "resolved": "https://registry.npmjs.org/@sphinxxxx/color-conversion/-/color-conversion-2.2.2.tgz",
  1449 + "integrity": "sha512-XExJS3cLqgrmNBIP3bBw6+1oQ1ksGjFh0+oClDKFYpCCqx/hlqwWO5KO/S63fzUo67SxI9dMrF0y5T/Ey7h8Zw=="
  1450 + },
1446 1451 "@tinymce/tinymce-vue": {
1447 1452 "version": "2.1.0",
1448 1453 "resolved": "https://registry.npmjs.org/@tinymce/tinymce-vue/-/tinymce-vue-2.1.0.tgz",
... ... @@ -3730,6 +3735,11 @@
3730 3735 "negotiator": "0.6.2"
3731 3736 }
3732 3737 },
  3738 + "ace-builds": {
  3739 + "version": "1.4.12",
  3740 + "resolved": "https://registry.npmjs.org/ace-builds/-/ace-builds-1.4.12.tgz",
  3741 + "integrity": "sha512-G+chJctFPiiLGvs3+/Mly3apXTcfgE45dT5yp12BcWZ1kUs+gm0qd3/fv4gsz6fVag4mM0moHVpjHDIgph6Psg=="
  3742 + },
3733 3743 "acorn": {
3734 3744 "version": "5.7.4",
3735 3745 "resolved": "https://registry.npmjs.org/acorn/-/acorn-5.7.4.tgz",
... ... @@ -3777,8 +3787,8 @@
3777 3787 },
3778 3788 "add-dom-event-listener": {
3779 3789 "version": "1.1.0",
3780   - "resolved": "https://registry.npm.taobao.org/add-dom-event-listener/download/add-dom-event-listener-1.1.0.tgz",
3781   - "integrity": "sha1-apLbOg3Qq8JU4JXA8dwUrLuq4xA=",
  3790 + "resolved": "https://registry.npmjs.org/add-dom-event-listener/-/add-dom-event-listener-1.1.0.tgz",
  3791 + "integrity": "sha512-WCxx1ixHT0GQU9hb0KI/mhgRQhnU+U3GvwY6ZvVjYq8rsihIGoaIOUbY0yMPBxLH5MDtr0kz3fisWGNcbWW7Jw==",
3782 3792 "requires": {
3783 3793 "object-assign": "4.x"
3784 3794 }
... ... @@ -3914,9 +3924,9 @@
3914 3924 "integrity": "sha1-tDLdM1i2NM914eRmQ2gkBTPB3b4="
3915 3925 },
3916 3926 "ant-design-vue": {
3917   - "version": "1.7.4",
3918   - "resolved": "https://registry.npm.taobao.org/ant-design-vue/download/ant-design-vue-1.7.4.tgz",
3919   - "integrity": "sha1-hU6QmF3A+pzMbWgcEEVgwA6q+FU=",
  3927 + "version": "1.6.3",
  3928 + "resolved": "https://registry.npmjs.org/ant-design-vue/-/ant-design-vue-1.6.3.tgz",
  3929 + "integrity": "sha512-Zt0z0SXzHCgow0chv4OA8lONxVOzXf7iLmZxdVHlsS3IaPn5n8QNPCzBUh3z0IXBdaDPiX9tjELQCXf9vdXdlw==",
3920 3930 "requires": {
3921 3931 "@ant-design/icons": "^2.1.1",
3922 3932 "@ant-design/icons-vue": "^2.0.0",
... ... @@ -4028,8 +4038,8 @@
4028 4038 },
4029 4039 "array-tree-filter": {
4030 4040 "version": "2.1.0",
4031   - "resolved": "https://registry.npm.taobao.org/array-tree-filter/download/array-tree-filter-2.1.0.tgz",
4032   - "integrity": "sha1-hzrAD+yDdJ8lWsjdCDgUtPYykZA="
  4041 + "resolved": "https://registry.npmjs.org/array-tree-filter/-/array-tree-filter-2.1.0.tgz",
  4042 + "integrity": "sha512-4ROwICNlNw/Hqa9v+rk5h22KjmzB1JGTMVKP2AKJBOCgb0yL0ASf0+YvCcLNNwquOHNX48jkeZIJ3a+oOQqKcw=="
4033 4043 },
4034 4044 "array-union": {
4035 4045 "version": "1.0.2",
... ... @@ -4138,9 +4148,9 @@
4138 4148 "dev": true
4139 4149 },
4140 4150 "async-validator": {
4141   - "version": "3.5.1",
4142   - "resolved": "https://registry.npm.taobao.org/async-validator/download/async-validator-3.5.1.tgz?cache=0&sync_timestamp=1605751734916&other_urls=https%3A%2F%2Fregistry.npm.taobao.org%2Fasync-validator%2Fdownload%2Fasync-validator-3.5.1.tgz",
4143   - "integrity": "sha1-zWK5aIskZfSEIOJ620d2CrG1VZ8="
  4151 + "version": "3.3.0",
  4152 + "resolved": "https://registry.npmjs.org/async-validator/-/async-validator-3.3.0.tgz",
  4153 + "integrity": "sha512-cAHGD9EL8aCqWXjnb44q94MWiDFzUo1tMhvLb2WzcpWqGiKugsjWG9cvl+jPgkPca7asNbsBU3fa0cwkI/P+Xg=="
4144 4154 },
4145 4155 "asynckit": {
4146 4156 "version": "0.4.0",
... ... @@ -4501,8 +4511,8 @@
4501 4511 },
4502 4512 "babel-helper-vue-jsx-merge-props": {
4503 4513 "version": "2.0.3",
4504   - "resolved": "https://registry.npm.taobao.org/babel-helper-vue-jsx-merge-props/download/babel-helper-vue-jsx-merge-props-2.0.3.tgz",
4505   - "integrity": "sha1-Iq69OzOQIyjlEyk6jkmSs4T58bY="
  4514 + "resolved": "https://registry.npmjs.org/babel-helper-vue-jsx-merge-props/-/babel-helper-vue-jsx-merge-props-2.0.3.tgz",
  4515 + "integrity": "sha512-gsLiKK7Qrb7zYJNgiXKpXblxbV5ffSwR0f5whkPAaBAR4fhi6bwRZxX9wBlIc5M/v8CCkXUbXZL4N/nSE97cqg=="
4506 4516 },
4507 4517 "babel-helpers": {
4508 4518 "version": "6.24.1",
... ... @@ -5617,8 +5627,8 @@
5617 5627 },
5618 5628 "classnames": {
5619 5629 "version": "2.2.6",
5620   - "resolved": "https://registry.npm.taobao.org/classnames/download/classnames-2.2.6.tgz",
5621   - "integrity": "sha1-Q5Nb/90pHzJtrQogUwmzjQD2UM4="
  5630 + "resolved": "https://registry.npmjs.org/classnames/-/classnames-2.2.6.tgz",
  5631 + "integrity": "sha512-JR/iSQOSt+LQIWwrwEzJ9uk0xfN3mTVYMwt1Ir5mUcSN6pU+V4zQFFaJsclJbPuAUQH+yfWef6tm7l1quW3C8Q=="
5622 5632 },
5623 5633 "clean-css": {
5624 5634 "version": "4.2.3",
... ... @@ -6079,7 +6089,7 @@
6079 6089 },
6080 6090 "component-classes": {
6081 6091 "version": "1.2.6",
6082   - "resolved": "https://registry.npm.taobao.org/component-classes/download/component-classes-1.2.6.tgz",
  6092 + "resolved": "https://registry.npmjs.org/component-classes/-/component-classes-1.2.6.tgz",
6083 6093 "integrity": "sha1-xkI5TDYYpNiwuJGe/Mu9kw5c1pE=",
6084 6094 "requires": {
6085 6095 "component-indexof": "0.0.3"
... ... @@ -6092,7 +6102,7 @@
6092 6102 },
6093 6103 "component-indexof": {
6094 6104 "version": "0.0.3",
6095   - "resolved": "https://registry.npm.taobao.org/component-indexof/download/component-indexof-0.0.3.tgz",
  6105 + "resolved": "https://registry.npmjs.org/component-indexof/-/component-indexof-0.0.3.tgz",
6096 6106 "integrity": "sha1-EdCRMSI5648yyPJa6csAL/6NPCQ="
6097 6107 },
6098 6108 "compressible": {
... ... @@ -8018,7 +8028,7 @@
8018 8028 },
8019 8029 "dom-closest": {
8020 8030 "version": "0.2.0",
8021   - "resolved": "https://registry.npm.taobao.org/dom-closest/download/dom-closest-0.2.0.tgz",
  8031 + "resolved": "https://registry.npmjs.org/dom-closest/-/dom-closest-0.2.0.tgz",
8022 8032 "integrity": "sha1-69n5HRvyLo1vR3h2u80+yQIWwM8=",
8023 8033 "requires": {
8024 8034 "dom-matches": ">=1.0.1"
... ... @@ -8035,13 +8045,13 @@
8035 8045 },
8036 8046 "dom-matches": {
8037 8047 "version": "2.0.0",
8038   - "resolved": "https://registry.npm.taobao.org/dom-matches/download/dom-matches-2.0.0.tgz",
  8048 + "resolved": "https://registry.npmjs.org/dom-matches/-/dom-matches-2.0.0.tgz",
8039 8049 "integrity": "sha1-0nKLQWqHUzmA6wibhI0lPPI6dYw="
8040 8050 },
8041 8051 "dom-scroll-into-view": {
8042 8052 "version": "2.0.1",
8043   - "resolved": "https://registry.npm.taobao.org/dom-scroll-into-view/download/dom-scroll-into-view-2.0.1.tgz",
8044   - "integrity": "sha1-DezIUigB/Y0/HGujVadNOCxfmJs="
  8053 + "resolved": "https://registry.npmjs.org/dom-scroll-into-view/-/dom-scroll-into-view-2.0.1.tgz",
  8054 + "integrity": "sha512-bvVTQe1lfaUr1oFzZX80ce9KLDlZ3iU+XGNE/bz9HnGdklTieqsbmsLHe+rT2XWqopvL0PckkYqN7ksmm5pe3w=="
8045 8055 },
8046 8056 "dom-serializer": {
8047 8057 "version": "0.2.2",
... ... @@ -10588,7 +10598,7 @@
10588 10598 },
10589 10599 "intersperse": {
10590 10600 "version": "1.0.0",
10591   - "resolved": "https://registry.npm.taobao.org/intersperse/download/intersperse-1.0.0.tgz",
  10601 + "resolved": "https://registry.npmjs.org/intersperse/-/intersperse-1.0.0.tgz",
10592 10602 "integrity": "sha1-8lYfsc/vn1J3zDNHoiiGtDUaUYE="
10593 10603 },
10594 10604 "invariant": {
... ... @@ -10759,13 +10769,13 @@
10759 10769 },
10760 10770 "is-mobile": {
10761 10771 "version": "2.2.2",
10762   - "resolved": "https://registry.npm.taobao.org/is-mobile/download/is-mobile-2.2.2.tgz",
10763   - "integrity": "sha1-9snF1Q7gElTOBec5vdg18e1OmVQ="
  10772 + "resolved": "https://registry.npmjs.org/is-mobile/-/is-mobile-2.2.2.tgz",
  10773 + "integrity": "sha512-wW/SXnYJkTjs++tVK5b6kVITZpAZPtUrt9SF80vvxGiF/Oywal+COk1jlRkiVq15RFNEQKQY31TkV24/1T5cVg=="
10764 10774 },
10765 10775 "is-negative-zero": {
10766   - "version": "2.0.1",
10767   - "resolved": "https://registry.npm.taobao.org/is-negative-zero/download/is-negative-zero-2.0.1.tgz",
10768   - "integrity": "sha1-PedGwY3aIxkkGlNnWQjY92bxHCQ="
  10776 + "version": "2.0.0",
  10777 + "resolved": "https://registry.npmjs.org/is-negative-zero/-/is-negative-zero-2.0.0.tgz",
  10778 + "integrity": "sha1-lVOxIbD6wohp2p7UWeIMdUN4hGE="
10769 10779 },
10770 10780 "is-number": {
10771 10781 "version": "7.0.0",
... ... @@ -10886,8 +10896,8 @@
10886 10896 },
10887 10897 "ismobilejs": {
10888 10898 "version": "1.1.1",
10889   - "resolved": "https://registry.npm.taobao.org/ismobilejs/download/ismobilejs-1.1.1.tgz",
10890   - "integrity": "sha1-xWygro5Sskyg8iul7zIVot27qg4="
  10899 + "resolved": "https://registry.npmjs.org/ismobilejs/-/ismobilejs-1.1.1.tgz",
  10900 + "integrity": "sha512-VaFW53yt8QO61k2WJui0dHf4SlL8lxBofUuUmwBo0ljPk0Drz2TiuDW4jo3wDcv41qy/SxrJ+VAzJ/qYqsmzRw=="
10891 10901 },
10892 10902 "isobject": {
10893 10903 "version": "3.0.1",
... ... @@ -10900,12 +10910,22 @@
10900 10910 "integrity": "sha1-R+Y/evVa+m+S4VAOaQ64uFKcCZo=",
10901 10911 "dev": true
10902 10912 },
  10913 + "javascript-natural-sort": {
  10914 + "version": "0.7.1",
  10915 + "resolved": "https://registry.npmjs.org/javascript-natural-sort/-/javascript-natural-sort-0.7.1.tgz",
  10916 + "integrity": "sha1-+eIwPUUH9tdDVac2ZNFED7Wg71k="
  10917 + },
10903 10918 "javascript-stringify": {
10904 10919 "version": "1.6.0",
10905 10920 "resolved": "https://registry.npmjs.org/javascript-stringify/-/javascript-stringify-1.6.0.tgz",
10906 10921 "integrity": "sha1-FC0RHzpuPa6PSpr9d9RYVbWpzOM=",
10907 10922 "dev": true
10908 10923 },
  10924 + "jmespath": {
  10925 + "version": "0.15.0",
  10926 + "resolved": "https://registry.npmjs.org/jmespath/-/jmespath-0.15.0.tgz",
  10927 + "integrity": "sha1-o/Iiqarp+Wb10nx5ZRDigJF2Qhc="
  10928 + },
10909 10929 "js-base64": {
10910 10930 "version": "2.6.3",
10911 10931 "resolved": "https://registry.npmjs.org/js-base64/-/js-base64-2.6.3.tgz",
... ... @@ -10984,6 +11004,11 @@
10984 11004 "resolved": "https://registry.npmjs.org/json-schema-traverse/-/json-schema-traverse-0.4.1.tgz",
10985 11005 "integrity": "sha512-xbbCH5dCYU5T8LcEhhuh7HJ88HXuW3qsI3Y0zOZFKfZEHcpWiHU/Jxzk629Brsab/mMiHQti9wMP+845RPe3Vg=="
10986 11006 },
  11007 + "json-source-map": {
  11008 + "version": "0.6.1",
  11009 + "resolved": "https://registry.npmjs.org/json-source-map/-/json-source-map-0.6.1.tgz",
  11010 + "integrity": "sha512-1QoztHPsMQqhDq0hlXY5ZqcEdUzxQEIxgFkKl4WUp2pgShObl+9ovi4kRh2TfvAfxAoHOJ9vIMEqk3k4iex7tg=="
  11011 + },
10987 11012 "json-stable-stringify-without-jsonify": {
10988 11013 "version": "1.0.1",
10989 11014 "resolved": "https://registry.npmjs.org/json-stable-stringify-without-jsonify/-/json-stable-stringify-without-jsonify-1.0.1.tgz",
... ... @@ -11006,7 +11031,7 @@
11006 11031 },
11007 11032 "json2mq": {
11008 11033 "version": "0.2.0",
11009   - "resolved": "https://registry.npm.taobao.org/json2mq/download/json2mq-0.2.0.tgz",
  11034 + "resolved": "https://registry.npmjs.org/json2mq/-/json2mq-0.2.0.tgz",
11010 11035 "integrity": "sha1-tje9O6nqvhIsg+lyBIOusQ0skEo=",
11011 11036 "requires": {
11012 11037 "string-convert": "^0.2.0"
... ... @@ -11025,6 +11050,21 @@
11025 11050 "minimist": "^1.2.0"
11026 11051 }
11027 11052 },
  11053 + "jsoneditor": {
  11054 + "version": "9.0.3",
  11055 + "resolved": "https://registry.npmjs.org/jsoneditor/-/jsoneditor-9.0.3.tgz",
  11056 + "integrity": "sha512-4uwT7nmNBAlC2KUUpsHaX2GZ+KoOohjtE/HzGToufYASGjnMzkf6EcLS+pAwwVHLv7VUnXmAuMY4NaQ9cS25lA==",
  11057 + "requires": {
  11058 + "ace-builds": "^1.4.11",
  11059 + "ajv": "^6.12.2",
  11060 + "javascript-natural-sort": "^0.7.1",
  11061 + "jmespath": "^0.15.0",
  11062 + "json-source-map": "^0.6.1",
  11063 + "mobius1-selectr": "^2.4.13",
  11064 + "picomodal": "^3.0.0",
  11065 + "vanilla-picker": "^2.10.1"
  11066 + }
  11067 + },
11028 11068 "jsonfile": {
11029 11069 "version": "4.0.0",
11030 11070 "resolved": "https://registry.npmjs.org/jsonfile/-/jsonfile-4.0.0.tgz",
... ... @@ -11432,7 +11472,7 @@
11432 11472 },
11433 11473 "lodash.toarray": {
11434 11474 "version": "4.4.0",
11435   - "resolved": "https://registry.npm.taobao.org/lodash.toarray/download/lodash.toarray-4.4.0.tgz",
  11475 + "resolved": "https://registry.npmjs.org/lodash.toarray/-/lodash.toarray-4.4.0.tgz",
11436 11476 "integrity": "sha1-JMS/zWsvuji/0FlNsRedjptlZWE="
11437 11477 },
11438 11478 "lodash.transform": {
... ... @@ -12024,10 +12064,15 @@
12024 12064 "minimist": "^1.2.5"
12025 12065 }
12026 12066 },
  12067 + "mobius1-selectr": {
  12068 + "version": "2.4.13",
  12069 + "resolved": "https://registry.npmjs.org/mobius1-selectr/-/mobius1-selectr-2.4.13.tgz",
  12070 + "integrity": "sha512-Mk9qDrvU44UUL0EBhbAA1phfQZ7aMZPjwtL7wkpiBzGh8dETGqfsh50mWoX9EkjDlkONlErWXArHCKfoxVg0Bw=="
  12071 + },
12027 12072 "moment": {
12028   - "version": "2.29.1",
12029   - "resolved": "https://registry.npm.taobao.org/moment/download/moment-2.29.1.tgz",
12030   - "integrity": "sha1-sr52n6MZQL6e7qZGnAdeNQBvo9M="
  12073 + "version": "2.27.0",
  12074 + "resolved": "https://registry.npmjs.org/moment/-/moment-2.27.0.tgz",
  12075 + "integrity": "sha512-al0MUK7cpIcglMv3YF13qSgdAIqxHTO7brRtaz3DlSULbqfazqkc5kEjNrLDOM7fsjshoFIihnU8snrP7zUvhQ=="
12031 12076 },
12032 12077 "move-concurrently": {
12033 12078 "version": "1.0.1",
... ... @@ -12064,8 +12109,8 @@
12064 12109 },
12065 12110 "mutationobserver-shim": {
12066 12111 "version": "0.3.7",
12067   - "resolved": "https://registry.npm.taobao.org/mutationobserver-shim/download/mutationobserver-shim-0.3.7.tgz",
12068   - "integrity": "sha1-i/YzsMCwKRoRByVe0ywTCIqMW/M="
  12112 + "resolved": "https://registry.npmjs.org/mutationobserver-shim/-/mutationobserver-shim-0.3.7.tgz",
  12113 + "integrity": "sha512-oRIDTyZQU96nAiz2AQyngwx1e89iApl2hN5AOYwyxLUB47UYsU3Wv9lJWqH5y/QdiYkc5HQLi23ZNB3fELdHcQ=="
12069 12114 },
12070 12115 "mute-stream": {
12071 12116 "version": "0.0.7",
... ... @@ -12110,9 +12155,9 @@
12110 12155 }
12111 12156 },
12112 12157 "nanopop": {
12113   - "version": "2.1.0",
12114   - "resolved": "https://registry.npm.taobao.org/nanopop/download/nanopop-2.1.0.tgz",
12115   - "integrity": "sha1-I0dlE87iQFiIr9LopLVAZrcLnmA="
  12158 + "version": "1.3.0",
  12159 + "resolved": "https://registry.npmjs.org/nanopop/-/nanopop-1.3.0.tgz",
  12160 + "integrity": "sha512-DQDhHyPhKLKrXOjVkChsAoWh/WpKuVINDKl4qvFbguqokRJWQBSNSlPzMS+Xy3yBQKeQ39rICMB2asDvdUiVxw=="
12116 12161 },
12117 12162 "natural-compare": {
12118 12163 "version": "1.4.0",
... ... @@ -12151,8 +12196,8 @@
12151 12196 },
12152 12197 "node-emoji": {
12153 12198 "version": "1.10.0",
12154   - "resolved": "https://registry.npm.taobao.org/node-emoji/download/node-emoji-1.10.0.tgz",
12155   - "integrity": "sha1-iIar0l2ce7YYAqZYUj0fjSqJsto=",
  12199 + "resolved": "https://registry.npmjs.org/node-emoji/-/node-emoji-1.10.0.tgz",
  12200 + "integrity": "sha512-Yt3384If5H6BYGVHiHwTL+99OzJKHhgp82S8/dktEK73T26BazdgZ4JZh92xSVtGNJvz9UbXdNAc5hcrXV42vw==",
12156 12201 "requires": {
12157 12202 "lodash.toarray": "^4.4.0"
12158 12203 }
... ... @@ -12410,8 +12455,8 @@
12410 12455 },
12411 12456 "omit.js": {
12412 12457 "version": "1.0.2",
12413   - "resolved": "https://registry.npm.taobao.org/omit.js/download/omit.js-1.0.2.tgz",
12414   - "integrity": "sha1-kaFPDrqEBm36AVvzDkdMR/MLyFg=",
  12458 + "resolved": "https://registry.npmjs.org/omit.js/-/omit.js-1.0.2.tgz",
  12459 + "integrity": "sha512-/QPc6G2NS+8d4L/cQhbk6Yit1WTB6Us2g84A7A/1+w9d/eRGHyEqC5kkQtHVoHZ5NFWGG7tUGgrhVZwgZanKrQ==",
12415 12460 "requires": {
12416 12461 "babel-runtime": "^6.23.0"
12417 12462 }
... ... @@ -12823,6 +12868,11 @@
12823 12868 "integrity": "sha512-q0M/9eZHzmr0AulXyPwNfZjtwZ/RBZlbN3K3CErVrk50T2ASYI7Bye0EvekFY3IP1Nt2DHu0re+V2ZHIpMkuWg==",
12824 12869 "optional": true
12825 12870 },
  12871 + "picomodal": {
  12872 + "version": "3.0.0",
  12873 + "resolved": "https://registry.npmjs.org/picomodal/-/picomodal-3.0.0.tgz",
  12874 + "integrity": "sha1-+s0w9PvzSoCcHgTqUl8ATzmcC4I="
  12875 + },
12826 12876 "pify": {
12827 12877 "version": "3.0.0",
12828 12878 "resolved": "https://registry.npmjs.org/pify/-/pify-3.0.0.tgz",
... ... @@ -14630,8 +14680,8 @@
14630 14680 },
14631 14681 "raf": {
14632 14682 "version": "3.4.1",
14633   - "resolved": "https://registry.npm.taobao.org/raf/download/raf-3.4.1.tgz",
14634   - "integrity": "sha1-B0LpmkplUvRF1z4+4DKK8P8e3jk=",
  14683 + "resolved": "https://registry.npmjs.org/raf/-/raf-3.4.1.tgz",
  14684 + "integrity": "sha512-Sq4CW4QhwOHE8ucn6J34MqtZCeWFP2aQSmrlroYgqAV1PjStIhJXxYuTgUIfkEk7zTLjmIjLmU5q+fbD1NnOJA==",
14635 14685 "requires": {
14636 14686 "performance-now": "^2.1.0"
14637 14687 }
... ... @@ -15028,8 +15078,8 @@
15028 15078 },
15029 15079 "resize-observer-polyfill": {
15030 15080 "version": "1.5.1",
15031   - "resolved": "https://registry.npm.taobao.org/resize-observer-polyfill/download/resize-observer-polyfill-1.5.1.tgz",
15032   - "integrity": "sha1-DpAg3T0hAkRY1OvSfiPkAmmBBGQ="
  15081 + "resolved": "https://registry.npmjs.org/resize-observer-polyfill/-/resize-observer-polyfill-1.5.1.tgz",
  15082 + "integrity": "sha512-LwZrotdHOo12nQuZlHEmtuXdqGoOD0OhaxopaNFxWzInpEgaLWoVuAMbTzixuosCx2nEG58ngzW3vxdWoxIgdg=="
15033 15083 },
15034 15084 "resolve": {
15035 15085 "version": "1.17.0",
... ... @@ -15459,13 +15509,13 @@
15459 15509 },
15460 15510 "shallow-equal": {
15461 15511 "version": "1.2.1",
15462   - "resolved": "https://registry.npm.taobao.org/shallow-equal/download/shallow-equal-1.2.1.tgz",
15463   - "integrity": "sha1-TBar+lYEOqINBQMk76aJQLDaedo="
  15512 + "resolved": "https://registry.npmjs.org/shallow-equal/-/shallow-equal-1.2.1.tgz",
  15513 + "integrity": "sha512-S4vJDjHHMBaiZuT9NPb616CSmLf618jawtv3sufLl6ivK8WocjAo58cXwbRV1cgqxH0Qbv+iUt6m05eqEa2IRA=="
15464 15514 },
15465 15515 "shallowequal": {
15466 15516 "version": "1.1.0",
15467   - "resolved": "https://registry.npm.taobao.org/shallowequal/download/shallowequal-1.1.0.tgz",
15468   - "integrity": "sha1-GI1SHelbkIdAT9TctosT3wrk5/g="
  15517 + "resolved": "https://registry.npmjs.org/shallowequal/-/shallowequal-1.1.0.tgz",
  15518 + "integrity": "sha512-y0m1JoUZSlPAjXVtPPW70aZWfIL/dSP7AFkRnniLCrK/8MDKog3TySTBmckD+RObVxH0v4Tox67+F14PdED2oQ=="
15469 15519 },
15470 15520 "shebang-command": {
15471 15521 "version": "1.2.0",
... ... @@ -15951,7 +16001,7 @@
15951 16001 },
15952 16002 "string-convert": {
15953 16003 "version": "0.2.1",
15954   - "resolved": "https://registry.npm.taobao.org/string-convert/download/string-convert-0.2.1.tgz",
  16004 + "resolved": "https://registry.npmjs.org/string-convert/-/string-convert-0.2.1.tgz",
15955 16005 "integrity": "sha1-aYLMMEn7tM2F+LJFaLnZvznu/5c="
15956 16006 },
15957 16007 "string-width": {
... ... @@ -16481,9 +16531,9 @@
16481 16531 "integrity": "sha512-NB6Dk1A9xgQPMoGqC5CVXn123gWyte215ONT5Pp5a0yt4nlEoO1ZWeCwpncaekPHXO60i47ihFnZPiRPjRMq4Q=="
16482 16532 },
16483 16533 "tinycolor2": {
16484   - "version": "1.4.2",
16485   - "resolved": "https://registry.npm.taobao.org/tinycolor2/download/tinycolor2-1.4.2.tgz?cache=0&sync_timestamp=1601056395015&other_urls=https%3A%2F%2Fregistry.npm.taobao.org%2Ftinycolor2%2Fdownload%2Ftinycolor2-1.4.2.tgz",
16486   - "integrity": "sha1-P2pNEHGtB2dtf6Ry4frECnGdiAM="
  16534 + "version": "1.4.1",
  16535 + "resolved": "https://registry.npmjs.org/tinycolor2/-/tinycolor2-1.4.1.tgz",
  16536 + "integrity": "sha1-9PrTM0R7wLB9TcjpIJ2POaisd+g="
16487 16537 },
16488 16538 "tinymce": {
16489 16539 "version": "5.4.1",
... ... @@ -16956,6 +17006,14 @@
16956 17006 "spdx-expression-parse": "^3.0.0"
16957 17007 }
16958 17008 },
  17009 + "vanilla-picker": {
  17010 + "version": "2.10.1",
  17011 + "resolved": "https://registry.npmjs.org/vanilla-picker/-/vanilla-picker-2.10.1.tgz",
  17012 + "integrity": "sha512-Bo4HOKkSorcQoRB08HwDMb8X2jt3SsZw7gzFlbzXbhnaxdUVJBm3LOUudr7M1SCVwPCo8d3nq8ajiAg8lAoqPg==",
  17013 + "requires": {
  17014 + "@sphinxxxx/color-conversion": "^2.2.2"
  17015 + }
  17016 + },
16959 17017 "vary": {
16960 17018 "version": "1.1.2",
16961 17019 "resolved": "https://registry.npmjs.org/vary/-/vary-1.1.2.tgz",
... ... @@ -17220,8 +17278,8 @@
17220 17278 },
17221 17279 "vue-ref": {
17222 17280 "version": "2.0.0",
17223   - "resolved": "https://registry.npm.taobao.org/vue-ref/download/vue-ref-2.0.0.tgz",
17224   - "integrity": "sha1-SDCE1zKr7RHaeWd4qCZqOvDqGpw="
  17281 + "resolved": "https://registry.npmjs.org/vue-ref/-/vue-ref-2.0.0.tgz",
  17282 + "integrity": "sha512-uKNKpFOVeWNqS2mrBZqnpLyXJo5Q+vnkex6JvpENvhXHFNBW/SJTP8vJywLuVT3DpxwXcF9N0dyIiZ4/NpTexQ=="
17225 17283 },
17226 17284 "vue-router": {
17227 17285 "version": "3.3.4",
... ... @@ -17269,20 +17327,10 @@
17269 17327 "resolved": "https://registry.npmjs.org/vuex/-/vuex-3.5.1.tgz",
17270 17328 "integrity": "sha512-w7oJzmHQs0FM9LXodfskhw9wgKBiaB+totOdb8sNzbTB2KDCEEwEs29NzBZFh/lmEK1t5tDmM1vtsO7ubG1DFw=="
17271 17329 },
17272   - "vxe-table": {
17273   - "version": "2.9.13",
17274   - "resolved": "https://registry.npm.taobao.org/vxe-table/download/vxe-table-2.9.13.tgz",
17275   - "integrity": "sha1-YZzVhRYN3ptSa5DOVSo1jss6YGA="
17276   - },
17277   - "vxe-table-plugin-antd": {
17278   - "version": "1.8.10",
17279   - "resolved": "https://registry.npm.taobao.org/vxe-table-plugin-antd/download/vxe-table-plugin-antd-1.8.10.tgz",
17280   - "integrity": "sha1-psAr/HzyJUYxETG4uFTAqtqwIOo="
17281   - },
17282 17330 "warning": {
17283 17331 "version": "4.0.3",
17284   - "resolved": "https://registry.npm.taobao.org/warning/download/warning-4.0.3.tgz",
17285   - "integrity": "sha1-Fungd+uKhtavfWSqHgX9hbRnjKM=",
  17332 + "resolved": "https://registry.npmjs.org/warning/-/warning-4.0.3.tgz",
  17333 + "integrity": "sha512-rpJyN222KWIvHJ/F53XSZv0Zl/accqHR8et1kpaMTD/fLCRxtV8iX8czMzY7sVZupTI3zcUTg8eycS2kNF9l6w==",
17286 17334 "requires": {
17287 17335 "loose-envify": "^1.0.0"
17288 17336 }
... ... @@ -18128,11 +18176,6 @@
18128 18176 "async-limiter": "~1.0.0"
18129 18177 }
18130 18178 },
18131   - "xe-utils": {
18132   - "version": "2.4.8",
18133   - "resolved": "https://registry.npm.taobao.org/xe-utils/download/xe-utils-2.4.8.tgz",
18134   - "integrity": "sha1-Dv2jyoH2tV9oqKMeJ2+xfaWcmLM="
18135   - },
18136 18179 "xregexp": {
18137 18180 "version": "4.3.0",
18138 18181 "resolved": "https://registry.npmjs.org/xregexp/-/xregexp-4.3.0.tgz",
... ...
ant-design-vue-jeecg/package.json
1 1 {
2 2 "name": "vue-antd-jeecg",
3   - "version": "2.4.3",
  3 + "version": "2.4.5",
4 4 "private": true,
5 5 "scripts": {
6 6 "pre": "cnpm install || yarn --registry https://registry.npm.taobao.org || npm install --registry https://registry.npm.taobao.org ",
... ... @@ -11,7 +11,7 @@
11 11 },
12 12 "dependencies": {
13 13 "ant-design-vue": "^1.7.2",
14   - "@jeecg/antd-online-mini": "2.4.3-RC",
  14 + "@jeecg/antd-online-mini": "2.4.5-RC",
15 15 "@antv/data-set": "^0.11.4",
16 16 "viser-vue": "^2.4.8",
17 17 "axios": "^0.18.0",
... ... @@ -43,7 +43,8 @@
43 43 "dom-align": "1.12.0",
44 44 "xe-utils": "2.4.8",
45 45 "vxe-table": "2.9.13",
46   - "vxe-table-plugin-antd": "1.8.10"
  46 + "vxe-table-plugin-antd": "1.8.10",
  47 + "cron-parser": "^2.10.0"
47 48 },
48 49 "devDependencies": {
49 50 "@babel/polyfill": "^7.2.5",
... ... @@ -96,10 +97,7 @@
96 97 "vue/html-closing-bracket-newline": 0,
97 98 "vue/no-parsing-error": 0,
98 99 "no-tabs": 0,
99   - "indent": [
100   - "off",
101   - 2
102   - ],
  100 + "indent": ["off", 2],
103 101 "no-console": 0,
104 102 "space-before-function-paren": 0
105 103 }
... ...
ant-design-vue-jeecg/src/components/JVxeCells/JVxePopupCell.vue
... ... @@ -6,7 +6,7 @@
6 6 </template>
7 7  
8 8 <script>
9   - import JVxeCellMixins, { vModel, dispatchEvent } from '@/components/jeecg/JVxeTable/mixins/JVxeCellMixins'
  9 + import JVxeCellMixins, { dispatchEvent, vModel } from '@/components/jeecg/JVxeTable/mixins/JVxeCellMixins'
10 10  
11 11 export default {
12 12 name: 'JVxePopupCell',
... ... @@ -22,6 +22,8 @@
22 22 orgFields: col.orgFields,
23 23 destFields: col.destFields,
24 24 groupId: caseId,
  25 + param: col.param,
  26 + sorter: col.sorter,
25 27 }
26 28 },
27 29 },
... ... @@ -48,7 +50,9 @@
48 50 // 【组件增强】注释详见:JVxeCellMixins.js
49 51 enhanced: {
50 52 aopEvents: {
51   - editActived: event => dispatchEvent(event, 'ant-input'),
  53 + editActived(event) {
  54 + dispatchEvent.call(this, event, 'ant-input')
  55 + },
52 56 },
53 57 },
54 58 }
... ...
ant-design-vue-jeecg/src/components/JVxeCells/JVxeSelectDictSearchCell.js
... ... @@ -254,7 +254,9 @@ export const DictSearchInputCell = {
254 254 // 【组件增强】注释详见:JVxeCellMixins.js
255 255 enhanced: {
256 256 aopEvents: {
257   - editActived: event => dispatchEvent(event, 'ant-select'),
  257 + editActived(event) {
  258 + dispatchEvent.call(this, event, 'ant-select')
  259 + },
258 260 },
259 261 }
260 262 }
261 263 \ No newline at end of file
... ...
ant-design-vue-jeecg/src/components/README.md
... ... @@ -39,5 +39,5 @@ UserMenu.vue:首页右上侧的内容
39 39 ![输入图片说明](https://static.oschina.net/uploads/img/201904/12201226_laQK.png "在这里输入图片标题")
40 40 ####16.trend包 趋势显示组件(如下图)
41 41 ![输入图片说明](https://static.oschina.net/uploads/img/201904/12201600_Wo8K.png "在这里输入图片标题")
42   -![corn表达式](https://oscimg.oschina.net/oscnet/661f9ac09016395f9f49286143af3241623.jpg)
43   -![corn控件添加清除按钮](https://oscimg.oschina.net/oscnet/15096e49f2e29bd829e304d56770025d03c.jpg)
44 42 \ No newline at end of file
  43 +![cron表达式](https://oscimg.oschina.net/oscnet/661f9ac09016395f9f49286143af3241623.jpg)
  44 +![cron控件添加清除按钮](https://oscimg.oschina.net/oscnet/15096e49f2e29bd829e304d56770025d03c.jpg)
45 45 \ No newline at end of file
... ...
ant-design-vue-jeecg/src/components/dict/JDictSelectTag.vue
... ... @@ -25,7 +25,6 @@
25 25 props: {
26 26 dictCode: String,
27 27 placeholder: String,
28   - triggerChange: Boolean,
29 28 disabled: Boolean,
30 29 value: [String, Number],
31 30 type: String,
... ... @@ -82,19 +81,15 @@
82 81 }
83 82 })
84 83 },
85   - handleInput(e) {
  84 + handleInput(e='') {
86 85 let val;
87   - if(this.tagType=="radio"){
  86 + if(Object.keys(e).includes('target')){
88 87 val = e.target.value
89 88 }else{
90 89 val = e
91 90 }
92 91 console.log(val);
93   - if(this.triggerChange){
94   - this.$emit('change', val);
95   - }else{
96   - this.$emit('input', val);
97   - }
  92 + this.$emit('change', val);
98 93 },
99 94 setCurrentDictOptions(dictOptions){
100 95 this.dictOptions = dictOptions
... ... @@ -102,6 +97,10 @@
102 97 getCurrentDictOptions(){
103 98 return this.dictOptions
104 99 }
  100 + },
  101 + model:{
  102 + prop: 'value',
  103 + event: 'change'
105 104 }
106 105 }
107 106 </script>
... ...
ant-design-vue-jeecg/src/components/dict/JSearchSelectTag.vue
... ... @@ -65,7 +65,11 @@
65 65 type: Number,
66 66 default: 10,
67 67 required: false
68   - }
  68 + },
  69 + getPopupContainer: {
  70 + type:Function,
  71 + default: null
  72 + },
69 73 },
70 74 data(){
71 75 this.loadData = debounce(this.loadData, 800);//消抖
... ... @@ -226,7 +230,9 @@
226 230 return this.options
227 231 },
228 232 getParentContainer(node){
229   - if(!this.popContainer){
  233 + if(typeof this.getPopupContainer === 'function'){
  234 + return this.getPopupContainer(node)
  235 + } else if(!this.popContainer){
230 236 return node.parentNode
231 237 }else{
232 238 return document.querySelector(this.popContainer)
... ...
ant-design-vue-jeecg/src/components/jeecg/JCron.vue
1 1 <template>
2 2 <div class="components-input-demo-presuffix">
3   - <a-input @click="openModal" placeholder="corn表达式" v-model="cron" @change="handleOK">
4   - <a-icon slot="prefix" type="schedule" title="corn控件"/>
  3 + <a-input @click="openModal" placeholder="cron表达式" v-model="cron" @change="(e)=>handleOK(e.target.value)">
  4 + <a-icon slot="prefix" type="schedule" title="cron控件"/>
5 5 <a-icon v-if="cron" slot="suffix" type="close-circle" @click="handleEmpty" title="清空"/>
6 6 </a-input>
7 7 <JCronModal ref="innerVueCron" :data="cron" @ok="handleOK"></JCronModal>
... ...
ant-design-vue-jeecg/src/components/jeecg/JEasyCron/EasyCron.vue 0 → 100644
  1 +<template>
  2 + <div class="j-easy-cron">
  3 + <div class="content">
  4 + <div>
  5 + <a-tabs size="small" v-model="curtab">
  6 + <a-tab-pane tab="秒" key="second" v-if="!hideSecond">
  7 + <second-ui v-model="second" :disabled="disabled"></second-ui>
  8 + </a-tab-pane>
  9 + <a-tab-pane tab="分" key="minute">
  10 + <minute-ui v-model="minute" :disabled="disabled"></minute-ui>
  11 + </a-tab-pane>
  12 + <a-tab-pane tab="时" key="hour">
  13 + <hour-ui v-model="hour" :disabled="disabled"></hour-ui>
  14 + </a-tab-pane>
  15 + <a-tab-pane tab="日" key="day">
  16 + <day-ui v-model="day" :week="week" :disabled="disabled"></day-ui>
  17 + </a-tab-pane>
  18 + <a-tab-pane tab="月" key="month">
  19 + <month-ui v-model="month" :disabled="disabled"></month-ui>
  20 + </a-tab-pane>
  21 + <a-tab-pane tab="周" key="week">
  22 + <week-ui v-model="week" :day="day" :disabled="disabled"></week-ui>
  23 + </a-tab-pane>
  24 + <a-tab-pane tab="年" key="year" v-if="!hideYear && !hideSecond">
  25 + <year-ui v-model="year" :disabled="disabled"></year-ui>
  26 + </a-tab-pane>
  27 + </a-tabs>
  28 + </div>
  29 + <a-divider/>
  30 + <!-- 执行时间预览 -->
  31 + <a-row :gutter="8">
  32 + <a-col :span="18" style="margin-top: 22px;">
  33 + <a-row :gutter="8">
  34 + <a-col :span="8" style="margin-bottom: 8px;">
  35 + <a-input addon-before="秒" v-model="inputValues.second" @blur="onInputBlur"/>
  36 + </a-col>
  37 + <a-col :span="8" style="margin-bottom: 8px;">
  38 + <a-input addon-before="分" v-model="inputValues.minute" @blur="onInputBlur"/>
  39 + </a-col>
  40 + <a-col :span="8" style="margin-bottom: 8px;">
  41 + <a-input addon-before="时" v-model="inputValues.hour" @blur="onInputBlur"/>
  42 + </a-col>
  43 + <a-col :span="8" style="margin-bottom: 8px;">
  44 + <a-input addon-before="日" v-model="inputValues.day" @blur="onInputBlur"/>
  45 + </a-col>
  46 + <a-col :span="8" style="margin-bottom: 8px;">
  47 + <a-input addon-before="月" v-model="inputValues.month" @blur="onInputBlur"/>
  48 + </a-col>
  49 + <a-col :span="8" style="margin-bottom: 8px;">
  50 + <a-input addon-before="周" v-model="inputValues.week" @blur="onInputBlur"/>
  51 + </a-col>
  52 + <a-col :span="8" style="margin-bottom: 8px;">
  53 + <a-input addon-before="年" v-model="inputValues.year" @blur="onInputBlur"/>
  54 + </a-col>
  55 + <a-col :span="16" style="margin-bottom: 8px;">
  56 + <a-input addon-before="Cron" v-model="inputValues.cron" @blur="onInputCronBlur"/>
  57 + </a-col>
  58 + </a-row>
  59 + </a-col>
  60 + <a-col :span="6">
  61 +
  62 + <div>近十次执行时间(不含年)</div>
  63 + <a-textarea type="textarea" :value="preTimeList" :rows="5"/>
  64 + </a-col>
  65 + </a-row>
  66 + </div>
  67 + </div>
  68 +</template>
  69 +
  70 +<script>
  71 +import SecondUi from './tabs/second'
  72 +import MinuteUi from './tabs/minute'
  73 +import HourUi from './tabs/hour'
  74 +import DayUi from './tabs/day'
  75 +import WeekUi from './tabs/week'
  76 +import MonthUi from './tabs/month'
  77 +import YearUi from './tabs/year'
  78 +import CronParser from 'cron-parser'
  79 +import dateFormat from './format-date'
  80 +import { simpleDebounce } from '@/utils/util'
  81 +import ACol from 'ant-design-vue/es/grid/Col'
  82 +
  83 +export default {
  84 + name: 'easy-cron',
  85 + components: {
  86 + ACol,
  87 + SecondUi,
  88 + MinuteUi,
  89 + HourUi,
  90 + DayUi,
  91 + WeekUi,
  92 + MonthUi,
  93 + YearUi
  94 + },
  95 + props: {
  96 + cronValue: {
  97 + type: String,
  98 + default: ''
  99 + },
  100 + disabled: {
  101 + type: Boolean,
  102 + default: false
  103 + },
  104 + hideSecond: {
  105 + type: Boolean,
  106 + default: false
  107 + },
  108 + hideYear: {
  109 + type: Boolean,
  110 + default: false
  111 + },
  112 + remote: {
  113 + type: Function,
  114 + default: null
  115 + }
  116 + },
  117 + data() {
  118 + return {
  119 + curtab: this.hideSecond ? 'minute' : 'second',
  120 + second: '*',
  121 + minute: '*',
  122 + hour: '*',
  123 + day: '*',
  124 + month: '*',
  125 + week: '?',
  126 + year: '*',
  127 + inputValues: {second: '', minute: '', hour: '', day: '', month: '', week: '', year: '', cron: ''},
  128 + preTimeList: '执行预览,会忽略年份参数',
  129 + }
  130 + },
  131 + computed: {
  132 + cronValue_c() {
  133 + let result = []
  134 + if (!this.hideSecond) result.push(this.second ? this.second : '*')
  135 + result.push(this.minute ? this.minute : '*')
  136 + result.push(this.hour ? this.hour : '*')
  137 + result.push(this.day ? this.day : '*')
  138 + result.push(this.month ? this.month : '*')
  139 + result.push(this.week ? this.week : '?')
  140 + if (!this.hideYear && !this.hideSecond) result.push(this.year ? this.year : '*')
  141 + return result.join(' ')
  142 + },
  143 + cronValue_c2() {
  144 + const v = this.cronValue_c
  145 + if (this.hideYear || this.hideSecond) return v
  146 + const vs = v.split(' ')
  147 + return vs.slice(0, vs.length - 1).join(' ')
  148 + }
  149 + },
  150 + watch: {
  151 + cronValue(newVal, oldVal) {
  152 + if (newVal === this.cronValue_c) {
  153 + // console.info('same cron value: ' + newVal)
  154 + return
  155 + }
  156 + this.formatValue()
  157 + },
  158 + cronValue_c(newVal, oldVal) {
  159 + this.calTriggerList()
  160 + this.$emit('change', newVal)
  161 +
  162 + Object.assign(this.inputValues, {
  163 + second: this.second,
  164 + minute: this.minute,
  165 + hour: this.hour,
  166 + day: this.day,
  167 + month: this.month,
  168 + week: this.week,
  169 + year: this.year,
  170 + cron: this.cronValue_c,
  171 + })
  172 + }
  173 + },
  174 + created() {
  175 + this.formatValue()
  176 + this.$nextTick(() => {
  177 + this.calTriggerListInner()
  178 + })
  179 + },
  180 + methods: {
  181 + formatValue() {
  182 + if (!this.cronValue) return
  183 + const values = this.cronValue.split(' ').filter(item => !!item)
  184 + if (!values || values.length <= 0) return
  185 + let i = 0
  186 + if (!this.hideSecond) this.second = values[i++]
  187 + if (values.length > i) this.minute = values[i++]
  188 + if (values.length > i) this.hour = values[i++]
  189 + if (values.length > i) this.day = values[i++]
  190 + if (values.length > i) this.month = values[i++]
  191 + if (values.length > i) this.week = values[i++]
  192 + if (values.length > i) this.year = values[i]
  193 + },
  194 + calTriggerList: simpleDebounce(function () {
  195 + this.calTriggerListInner()
  196 + }, 500),
  197 + calTriggerListInner() {
  198 + // 设置了回调函数
  199 + if (this.remote) {
  200 + this.remote(this.cronValue_c, +new Date(), v => {
  201 + this.preTimeList = v
  202 + })
  203 + return
  204 + }
  205 + const format = 'yyyy-MM-dd hh:mm:ss'
  206 + const options = {
  207 + currentDate: dateFormat(new Date(), format)
  208 + }
  209 + const iter = CronParser.parseExpression(this.cronValue_c2, options)
  210 + const result = []
  211 + for (let i = 1; i <= 10; i++) {
  212 + result.push(dateFormat(new Date(iter.next()), format))
  213 + }
  214 + this.preTimeList = result.length > 0 ? result.join('\n') : '无执行时间'
  215 + },
  216 + onInputBlur(){
  217 + this.second = this.inputValues.second
  218 + this.minute = this.inputValues.minute
  219 + this.hour = this.inputValues.hour
  220 + this.day = this.inputValues.day
  221 + this.month = this.inputValues.month
  222 + this.week = this.inputValues.week
  223 + this.year = this.inputValues.year
  224 + },
  225 + onInputCronBlur(event){
  226 + this.$emit('change', event.target.value)
  227 + },
  228 + },
  229 + model: {
  230 + prop: 'cronValue',
  231 + event: 'change'
  232 + },
  233 +}
  234 +</script>
  235 +
  236 +<style scoped lang="less">
  237 + .j-easy-cron {
  238 +
  239 + /deep/ .content {
  240 + .ant-checkbox-wrapper + .ant-checkbox-wrapper {
  241 + margin-left: 0;
  242 + }
  243 + }
  244 +
  245 + }
  246 +</style>
... ...
ant-design-vue-jeecg/src/components/jeecg/JEasyCron/InputCron.vue 0 → 100644
  1 +<template>
  2 + <div class="input-cron">
  3 + <a-input :placeholder="placeholder" v-model="editCronValue" :disabled="disabled">
  4 + <a slot="addonAfter" @click="showConfigDlg" class="config-btn" :disabled="disabled">
  5 + <a-icon type="setting"></a-icon>
  6 + 选择
  7 + </a>
  8 + </a-input>
  9 + <j-modal :visible.sync="show" title="Cron表达式" width="800px">
  10 + <easy-cron
  11 + v-model="editCronValue"
  12 + :exeStartTime="exeStartTime"
  13 + :hideYear="hideYear"
  14 + :remote="remote"
  15 + :hideSecond="hideSecond"
  16 + style="width: 100%"
  17 + ></easy-cron>
  18 + </j-modal>
  19 + </div>
  20 +</template>
  21 +
  22 +<script>
  23 +import EasyCron from './EasyCron.vue'
  24 +
  25 +export default {
  26 + name: 'input-cron',
  27 + components: {EasyCron},
  28 + model: {
  29 + prop: 'cronValue',
  30 + event: 'change'
  31 + },
  32 + props: {
  33 + cronValue: {
  34 + type: String,
  35 + default: ''
  36 + },
  37 + width: {
  38 + type: String,
  39 + default: '800px'
  40 + },
  41 + placeholder: {
  42 + type: String,
  43 + default: '请输入cron表达式'
  44 + },
  45 + disabled: {
  46 + type: Boolean,
  47 + default: false
  48 + },
  49 + exeStartTime: {
  50 + type: [Number, String, Object],
  51 + default: 0
  52 + },
  53 + hideSecond: {
  54 + type: Boolean,
  55 + default: false
  56 + },
  57 + hideYear: {
  58 + type: Boolean,
  59 + default: false
  60 + },
  61 + remote: {
  62 + type: Function,
  63 + default: null
  64 + }
  65 + },
  66 + data() {
  67 + return {
  68 + editCronValue: this.cronValue,
  69 + show: false,
  70 + }
  71 + },
  72 + watch: {
  73 + cronValue(newVal, oldVal) {
  74 + if (newVal === this.editCronValue) {
  75 + return
  76 + }
  77 + this.editCronValue = newVal
  78 + },
  79 + editCronValue(newVal, oldVal) {
  80 + this.$emit('change', newVal)
  81 + }
  82 + },
  83 + methods: {
  84 + showConfigDlg() {
  85 + if (!this.disabled) {
  86 + this.show = true
  87 + }
  88 + }
  89 + }
  90 +}
  91 +</script>
  92 +
  93 +<style scoped>
  94 +
  95 + .config-btn {
  96 + cursor: pointer;
  97 + }
  98 +
  99 +</style>
... ...
ant-design-vue-jeecg/src/components/jeecg/JEasyCron/format-date.js 0 → 100644
  1 +const dateFormat = (date, block) => {
  2 + if (!date) {
  3 + return ''
  4 + }
  5 +
  6 + let format = block || 'yyyy-MM-dd'
  7 +
  8 + date = new Date(date)
  9 +
  10 + const map = {
  11 + M: date.getMonth() + 1, // 月份
  12 + d: date.getDate(), // 日
  13 + h: date.getHours(), // 小时
  14 + m: date.getMinutes(), // 分
  15 + s: date.getSeconds(), // 秒
  16 + q: Math.floor((date.getMonth() + 3) / 3), // 季度
  17 + S: date.getMilliseconds() // 毫秒
  18 + }
  19 +
  20 + format = format.replace(/([yMdhmsqS])+/g, (all, t) => {
  21 + let v = map[t]
  22 + if (v !== undefined) {
  23 + if (all.length > 1) {
  24 + v = `0${v}`
  25 + v = v.substr(v.length - 2)
  26 + }
  27 + return v
  28 + } else if (t === 'y') {
  29 + return (date.getFullYear().toString()).substr(4 - all.length)
  30 + }
  31 + return all
  32 + })
  33 +
  34 + return format
  35 +}
  36 +
  37 +export default dateFormat
... ...
ant-design-vue-jeecg/src/components/jeecg/JEasyCron/index.js 0 → 100644
  1 +// 原开源项目地址:https://gitee.com/toktok/easy-cron
  2 +
  3 +import InputCron from './InputCron.vue'
  4 +
  5 +InputCron.name = 'JEasyCron'
  6 +export default InputCron
0 7 \ No newline at end of file
... ...
ant-design-vue-jeecg/src/components/jeecg/JEasyCron/tabs/const.js 0 → 100644
  1 +export const WEEK_MAP_EN = {
  2 + 'SUN': '0',
  3 + 'MON': '1',
  4 + 'TUE': '2',
  5 + 'WED': '3',
  6 + 'THU': '4',
  7 + 'FRI': '5',
  8 + 'SAT': '6'
  9 +}
  10 +
  11 +export const replaceWeekName = (c) => {
  12 + // console.info('after: ' + c)
  13 + if (c) {
  14 + Object.keys(WEEK_MAP_EN).forEach(k => {
  15 + c = c.replace(new RegExp(k, 'g'), WEEK_MAP_EN[k])
  16 + })
  17 + c = c.replace(new RegExp('7', 'g'), '0')
  18 + }
  19 + // console.info('after: ' + c)
  20 + return c
  21 +}
... ...
ant-design-vue-jeecg/src/components/jeecg/JEasyCron/tabs/day.vue 0 → 100644
  1 +<template>
  2 + <div class="config-list">
  3 + <a-radio-group v-model="type">
  4 + <div class="item">
  5 + <a-radio value="TYPE_NOT_SET" class="choice" :disabled="disableChoice">不设置</a-radio>
  6 + <span class="tip-info">日和周只能设置其中之一</span>
  7 + </div>
  8 + <div class="item">
  9 + <a-radio value="TYPE_EVERY" class="choice" :disabled="disableChoice">每日</a-radio>
  10 + </div>
  11 + <div class="item">
  12 + <a-radio value="TYPE_RANGE" class="choice" :disabled="disableChoice">区间</a-radio>
  13 + 从
  14 + <a-input-number :disabled="type!==TYPE_RANGE || disableChoice" :max="maxValue" :min="minValue" :precision="0" class="w60" v-model="valueRange.start"/>
  15 + 日
  16 + 至
  17 + <a-input-number :disabled="type!==TYPE_RANGE || disableChoice" :max="maxValue" :min="minValue" :precision="0" class="w60" v-model="valueRange.end"/>
  18 + 日
  19 + </div>
  20 + <div class="item">
  21 + <a-radio value="TYPE_LOOP" class="choice" :disabled="disableChoice">循环</a-radio>
  22 + 从
  23 + <a-input-number :disabled="type!==TYPE_LOOP || disableChoice" :max="maxValue" :min="minValue" :precision="0" class="w60" v-model="valueLoop.start"/>
  24 + 日开始,间隔
  25 + <a-input-number :disabled="type!==TYPE_LOOP || disableChoice" :max="maxValue" :min="minValue" :precision="0" class="w60" v-model="valueLoop.interval"/>
  26 + 日
  27 + </div>
  28 + <div class="item">
  29 + <a-radio value="TYPE_WORK" class="choice" :disabled="disableChoice">工作日</a-radio>
  30 + 本月
  31 + <a-input-number :disabled="type!==TYPE_WORK || disableChoice" :max="maxValue" :min="minValue" :precision="0" class="w60" v-model="valueWork"/>
  32 + 日,最近的工作日
  33 + </div>
  34 + <div class="item">
  35 + <a-radio value="TYPE_LAST" class="choice" :disabled="disableChoice">最后一日</a-radio>
  36 + </div>
  37 + <div class="item">
  38 + <a-radio value="TYPE_SPECIFY" class="choice" :disabled="disableChoice">指定</a-radio>
  39 + <div class="list">
  40 + <a-checkbox-group v-model="valueList">
  41 + <template v-for="i in maxValue+1">
  42 + <a-checkbox class="list-check-item" :key="`key-${i-1}`" :value="i-1" :disabled="type!==TYPE_SPECIFY || disabled">{{i-1}}</a-checkbox>
  43 + </template>
  44 + </a-checkbox-group>
  45 + </div>
  46 + </div>
  47 + </a-radio-group>
  48 + </div>
  49 +</template>
  50 +
  51 +<script>
  52 +import mixin from './mixin'
  53 +
  54 +export default {
  55 + name: 'day',
  56 + mixins: [mixin],
  57 + props: {
  58 + week: {
  59 + type: String,
  60 + default: '?'
  61 + }
  62 + },
  63 + data() {
  64 + return {}
  65 + },
  66 + computed: {
  67 + disableChoice() {
  68 + return (this.week && this.week !== '?') || this.disabled
  69 + }
  70 + },
  71 + watch: {
  72 + value_c(newVal, oldVal) {
  73 + // 数值变化
  74 + this.updateValue()
  75 + },
  76 + week(newVal, oldVal) {
  77 + // console.info('new week: ' + newVal)
  78 + this.updateValue()
  79 + }
  80 + },
  81 + methods: {
  82 + updateValue() {
  83 + this.$emit('change', this.disableChoice ? '?' : this.value_c)
  84 + }
  85 + },
  86 + created() {
  87 + this.DEFAULT_VALUE = '*'
  88 + this.minValue = 1
  89 + this.maxValue = 31
  90 + this.valueRange.start = 1
  91 + this.valueRange.end = 31
  92 + this.valueLoop.start = 1
  93 + this.valueLoop.interval = 1
  94 + this.parseProp(this.prop)
  95 + }
  96 +}
  97 +</script>
  98 +
  99 +<style lang="less" scoped>
  100 + @import "mixin.less";
  101 +</style>
... ...
ant-design-vue-jeecg/src/components/jeecg/JEasyCron/tabs/hour.vue 0 → 100644
  1 +<template>
  2 + <div class="config-list">
  3 + <a-radio-group v-model="type">
  4 + <div class="item">
  5 + <a-radio value="TYPE_EVERY" class="choice" :disabled="disabled">每时</a-radio>
  6 + </div>
  7 + <div class="item">
  8 + <a-radio value="TYPE_RANGE" class="choice" :disabled="disabled">区间</a-radio>
  9 + 从
  10 + <a-input-number :disabled="type!==TYPE_RANGE || disabled" :max="maxValue" :min="minValue" :precision="0" class="w60" v-model="valueRange.start"/>
  11 + 时
  12 + 至
  13 + <a-input-number :disabled="type!==TYPE_RANGE || disabled" :max="maxValue" :min="minValue" :precision="0" class="w60" v-model="valueRange.end"/>
  14 + 时
  15 + </div>
  16 + <div class="item">
  17 + <a-radio value="TYPE_LOOP" class="choice" :disabled="disabled">循环</a-radio>
  18 + 从
  19 + <a-input-number :disabled="type!==TYPE_LOOP || disabled" :max="maxValue" :min="minValue" :precision="0" class="w60" v-model="valueLoop.start"/>
  20 + 时开始,间隔
  21 + <a-input-number :disabled="type!==TYPE_LOOP || disabled" :max="maxValue" :min="minValue" :precision="0" class="w60" v-model="valueLoop.interval"/>
  22 + 时
  23 + </div>
  24 + <div class="item">
  25 + <a-radio value="TYPE_SPECIFY" class="choice" :disabled="disabled">指定</a-radio>
  26 + <div class="list">
  27 + <a-checkbox-group v-model="valueList">
  28 + <template v-for="i in maxValue+1">
  29 + <a-checkbox class="list-check-item" :key="`key-${i-1}`" :value="i-1" :disabled="type!==TYPE_SPECIFY || disabled">{{i-1}}</a-checkbox>
  30 + </template>
  31 + </a-checkbox-group>
  32 + </div>
  33 + </div>
  34 + </a-radio-group>
  35 + </div>
  36 +</template>
  37 +
  38 +<script>
  39 +import mixin from './mixin'
  40 +
  41 +export default {
  42 + name: 'minute',
  43 + mixins: [mixin],
  44 + data() {
  45 + return {}
  46 + },
  47 + watch: {
  48 + value_c(newVal, oldVal) {
  49 + this.$emit('change', newVal)
  50 + }
  51 + },
  52 + created() {
  53 + this.DEFAULT_VALUE = '*'
  54 + this.minValue = 0
  55 + this.maxValue = 23
  56 + this.valueRange.start = 0
  57 + this.valueRange.end = 23
  58 + this.valueLoop.start = 0
  59 + this.valueLoop.interval = 1
  60 + this.parseProp(this.prop)
  61 + }
  62 +}
  63 +</script>
  64 +
  65 +<style lang="less" scoped>
  66 + @import "mixin.less";
  67 +</style>
... ...
ant-design-vue-jeecg/src/components/jeecg/JEasyCron/tabs/minute.vue 0 → 100644
  1 +<template>
  2 + <div class="config-list">
  3 + <a-radio-group v-model="type">
  4 + <div class="item">
  5 + <a-radio value="TYPE_EVERY" class="choice" :disabled="disabled">每分</a-radio>
  6 + </div>
  7 + <div class="item">
  8 + <a-radio value="TYPE_RANGE" class="choice" :disabled="disabled">区间</a-radio>
  9 + 从
  10 + <a-input-number :disabled="type!==TYPE_RANGE || disabled" :max="maxValue" :min="minValue" :precision="0" class="w60" v-model="valueRange.start"/>
  11 + 分
  12 + 至
  13 + <a-input-number :disabled="type!==TYPE_RANGE || disabled" :max="maxValue" :min="minValue" :precision="0" class="w60" v-model="valueRange.end"/>
  14 + 分
  15 + </div>
  16 + <div class="item">
  17 + <a-radio value="TYPE_LOOP" class="choice" :disabled="disabled">循环</a-radio>
  18 + 从
  19 + <a-input-number :disabled="type!==TYPE_LOOP || disabled" :max="maxValue" :min="minValue" :precision="0" class="w60" v-model="valueLoop.start"/>
  20 + 分开始,间隔
  21 + <a-input-number :disabled="type!==TYPE_LOOP || disabled" :max="maxValue" :min="minValue" :precision="0" class="w60" v-model="valueLoop.interval"/>
  22 + 分
  23 + </div>
  24 + <div class="item">
  25 + <a-radio value="TYPE_SPECIFY" class="choice" :disabled="disabled">指定</a-radio>
  26 + <div class="list">
  27 + <a-checkbox-group v-model="valueList">
  28 + <template v-for="i in maxValue+1">
  29 + <a-checkbox class="list-check-item" :key="`key-${i-1}`" :value="i-1" :disabled="type!==TYPE_SPECIFY || disabled">{{i-1}}</a-checkbox>
  30 + </template>
  31 + </a-checkbox-group>
  32 + </div>
  33 + </div>
  34 + </a-radio-group>
  35 + </div>
  36 +</template>
  37 +
  38 +<script>
  39 +import mixin from './mixin'
  40 +
  41 +export default {
  42 + name: 'minute',
  43 + mixins: [mixin],
  44 + data() {
  45 + return {}
  46 + },
  47 + watch: {
  48 + value_c(newVal, oldVal) {
  49 + this.$emit('change', newVal)
  50 + }
  51 + },
  52 + created() {
  53 + this.DEFAULT_VALUE = '*'
  54 + this.minValue = 0
  55 + this.maxValue = 59
  56 + this.valueRange.start = 0
  57 + this.valueRange.end = 59
  58 + this.valueLoop.start = 0
  59 + this.valueLoop.interval = 1
  60 + this.parseProp(this.prop)
  61 + }
  62 +}
  63 +</script>
  64 +
  65 +<style lang="less" scoped>
  66 + @import "mixin.less";
  67 +</style>
... ...
ant-design-vue-jeecg/src/components/jeecg/JEasyCron/tabs/mixin.js 0 → 100644
  1 +// 主要用于日和星期的互斥使用
  2 +const TYPE_NOT_SET = 'TYPE_NOT_SET'
  3 +const TYPE_EVERY = 'TYPE_EVERY'
  4 +const TYPE_RANGE = 'TYPE_RANGE'
  5 +const TYPE_LOOP = 'TYPE_LOOP'
  6 +const TYPE_WORK = 'TYPE_WORK'
  7 +const TYPE_LAST = 'TYPE_LAST'
  8 +const TYPE_SPECIFY = 'TYPE_SPECIFY'
  9 +
  10 +const DEFAULT_VALUE = '?'
  11 +
  12 +export default {
  13 + model: {
  14 + prop: 'prop',
  15 + event: 'change'
  16 + },
  17 + props: {
  18 + prop: {
  19 + type: String,
  20 + default: DEFAULT_VALUE
  21 + },
  22 + disabled: {
  23 + type: Boolean,
  24 + default: false
  25 + }
  26 + },
  27 + data () {
  28 + const type = TYPE_EVERY
  29 + return {
  30 + DEFAULT_VALUE,
  31 + // 类型
  32 + type,
  33 + // 启用日或者星期互斥用
  34 + TYPE_NOT_SET,
  35 + TYPE_EVERY,
  36 + TYPE_RANGE,
  37 + TYPE_LOOP,
  38 + TYPE_WORK,
  39 + TYPE_LAST,
  40 + TYPE_SPECIFY,
  41 + // 对于不同的类型,所定义的值也有所不同
  42 + valueRange: {
  43 + start: 0,
  44 + end: 0
  45 + },
  46 + valueLoop: {
  47 + start: 0,
  48 + interval: 1
  49 + },
  50 + valueWeek: {
  51 + start: 0,
  52 + end: 0
  53 + },
  54 + valueList: [],
  55 + valueWork: 1,
  56 + maxValue: 0,
  57 + minValue: 0
  58 + }
  59 + },
  60 + watch: {
  61 + prop (newVal, oldVal) {
  62 + if (newVal === this.value_c) {
  63 + // console.info('skip ' + newVal)
  64 + return
  65 + }
  66 + this.parseProp(newVal)
  67 + }
  68 + },
  69 + computed: {
  70 + value_c () {
  71 + let result = []
  72 + switch (this.type) {
  73 + case TYPE_NOT_SET:
  74 + result.push('?')
  75 + break
  76 + case TYPE_EVERY:
  77 + result.push('*')
  78 + break
  79 + case TYPE_RANGE:
  80 + result.push(`${this.valueRange.start}-${this.valueRange.end}`)
  81 + break
  82 + case TYPE_LOOP:
  83 + result.push(`${this.valueLoop.start}/${this.valueLoop.interval}`)
  84 + break
  85 + case TYPE_WORK:
  86 + result.push(`${this.valueWork}W`)
  87 + break
  88 + case TYPE_LAST:
  89 + result.push('L')
  90 + break
  91 + case TYPE_SPECIFY:
  92 + result.push(this.valueList.join(','))
  93 + break
  94 + default:
  95 + result.push(this.DEFAULT_VALUE)
  96 + break
  97 + }
  98 + return result.length > 0 ? result.join('') : this.DEFAULT_VALUE
  99 + }
  100 + },
  101 + methods: {
  102 + parseProp (value) {
  103 + if (value === this.value_c) {
  104 + // console.info('same ' + value)
  105 + return
  106 + }
  107 + if (typeof (this.preProcessProp) === 'function') {
  108 + value = this.preProcessProp(value)
  109 + }
  110 + try {
  111 + if (!value || value === this.DEFAULT_VALUE) {
  112 + this.type = TYPE_EVERY
  113 + } else if (value.indexOf('?') >= 0) {
  114 + this.type = TYPE_NOT_SET
  115 + } else if (value.indexOf('-') >= 0) {
  116 + this.type = TYPE_RANGE
  117 + const values = value.split('-')
  118 + if (values.length >= 2) {
  119 + this.valueRange.start = parseInt(values[0])
  120 + this.valueRange.end = parseInt(values[1])
  121 + }
  122 + } else if (value.indexOf('/') >= 0) {
  123 + this.type = TYPE_LOOP
  124 + const values = value.split('/')
  125 + if (values.length >= 2) {
  126 + this.valueLoop.start = value[0] === '*' ? 0 : parseInt(values[0])
  127 + this.valueLoop.interval = parseInt(values[1])
  128 + }
  129 + } else if (value.indexOf('W') >= 0) {
  130 + this.type = TYPE_WORK
  131 + const values = value.split('W')
  132 + if (!values[0] && !isNaN(values[0])) {
  133 + this.valueWork = parseInt(values[0])
  134 + }
  135 + } else if (value.indexOf('L') >= 0) {
  136 + this.type = TYPE_LAST
  137 + const values = value.split('L')
  138 + this.valueLast = parseInt(values[0])
  139 + } else if (value.indexOf(',') >= 0 || !isNaN(value)) {
  140 + this.type = TYPE_SPECIFY
  141 + this.valueList = value.split(',').map(item => parseInt(item))
  142 + } else {
  143 + this.type = TYPE_EVERY
  144 + }
  145 + } catch (e) {
  146 + // console.info(e)
  147 + this.type = TYPE_EVERY
  148 + }
  149 + }
  150 + }
  151 +}
... ...
ant-design-vue-jeecg/src/components/jeecg/JEasyCron/tabs/mixin.less 0 → 100644
  1 +
  2 +.config-list {
  3 + text-align: left;
  4 + margin: 0 10px 10px 10px;
  5 +}
  6 +
  7 +.item {
  8 + margin-top: 5px;
  9 +}
  10 +
  11 +.choice {
  12 + padding: 5px 8px;
  13 +}
  14 +
  15 +
  16 +.w60 {
  17 + width: 60px;
  18 +}
  19 +.w80 {
  20 + width: 80px;
  21 +}
  22 +
  23 +.list {
  24 + margin: 0 20px;
  25 +}
  26 +
  27 +.list-check-item {
  28 + padding: 1px 3px;
  29 + width: 4em;
  30 +}
  31 +
  32 +.tip-info {
  33 + color: #999
  34 +}
  35 +
... ...
ant-design-vue-jeecg/src/components/jeecg/JEasyCron/tabs/month.vue 0 → 100644
  1 +<template>
  2 + <div class="config-list">
  3 + <a-radio-group v-model="type">
  4 + <div class="item">
  5 + <a-radio value="TYPE_EVERY" class="choice" :disabled="disabled">每月</a-radio>
  6 + </div>
  7 + <div class="item">
  8 + <a-radio value="TYPE_RANGE" class="choice" :disabled="disabled">区间</a-radio>
  9 + 从
  10 + <a-input-number :disabled="type!==TYPE_RANGE || disabled" :max="maxValue" :min="minValue" :precision="0" class="w60" v-model="valueRange.start"/>
  11 + 月
  12 + 至
  13 + <a-input-number :disabled="type!==TYPE_RANGE || disabled" :max="maxValue" :min="minValue" :precision="0" class="w60" v-model="valueRange.end"/>
  14 + 月
  15 + </div>
  16 + <div class="item">
  17 + <a-radio value="TYPE_LOOP" class="choice" :disabled="disabled">循环</a-radio>
  18 + 从
  19 + <a-input-number :disabled="type!==TYPE_LOOP || disabled" :max="maxValue" :min="minValue" :precision="0" class="w60" v-model="valueLoop.start"/>
  20 + 月开始,间隔
  21 + <a-input-number :disabled="type!==TYPE_LOOP || disabled" :max="maxValue" :min="minValue" :precision="0" class="w60" v-model="valueLoop.interval"/>
  22 + 月
  23 + </div>
  24 + <div class="item">
  25 + <a-radio value="TYPE_SPECIFY" class="choice" :disabled="disabled">指定</a-radio>
  26 + <div class="list">
  27 + <a-checkbox-group v-model="valueList">
  28 + <template v-for="i in maxValue+1">
  29 + <a-checkbox class="list-check-item" :key="`key-${i-1}`" :value="i-1" :disabled="type!==TYPE_SPECIFY || disabled">{{i-1}}</a-checkbox>
  30 + </template>
  31 + </a-checkbox-group>
  32 + </div>
  33 + </div>
  34 + </a-radio-group>
  35 + </div>
  36 +</template>
  37 +
  38 +<script>
  39 +import mixin from './mixin'
  40 +
  41 +export default {
  42 + name: 'month',
  43 + mixins: [mixin],
  44 + data() {
  45 + return {}
  46 + },
  47 + watch: {
  48 + value_c(newVal, oldVal) {
  49 + this.$emit('change', newVal)
  50 + }
  51 + },
  52 + created() {
  53 + this.DEFAULT_VALUE = '*'
  54 + this.minValue = 1
  55 + this.maxValue = 12
  56 + this.valueRange.start = 1
  57 + this.valueRange.end = 12
  58 + this.valueLoop.start = 1
  59 + this.valueLoop.interval = 1
  60 + this.parseProp(this.prop)
  61 + }
  62 +}
  63 +</script>
  64 +
  65 +<style lang="less" scoped>
  66 + @import "mixin.less";
  67 +</style>
... ...
ant-design-vue-jeecg/src/components/jeecg/JEasyCron/tabs/second.vue 0 → 100644
  1 +<template>
  2 + <div class="config-list">
  3 + <a-radio-group v-model="type">
  4 + <div class="item">
  5 + <a-radio value="TYPE_EVERY" class="choice" :disabled="disabled">每秒</a-radio>
  6 + </div>
  7 + <div class="item">
  8 + <a-radio value="TYPE_RANGE" class="choice" :disabled="disabled">区间</a-radio>
  9 + 从
  10 + <a-input-number :disabled="type!==TYPE_RANGE || disabled" :max="maxValue" :min="minValue" :precision="0" class="w60" v-model="valueRange.start"/>
  11 + 秒
  12 + 至
  13 + <a-input-number :disabled="type!==TYPE_RANGE || disabled" :max="maxValue" :min="minValue" :precision="0" class="w60" v-model="valueRange.end"/>
  14 + 秒
  15 + </div>
  16 + <div class="item">
  17 + <a-radio value="TYPE_LOOP" class="choice" :disabled="disabled">循环</a-radio>
  18 + 从
  19 + <a-input-number :disabled="type!==TYPE_LOOP || disabled" :max="maxValue" :min="minValue" :precision="0" class="w60" v-model="valueLoop.start"/>
  20 + 秒开始,间隔
  21 + <a-input-number :disabled="type!==TYPE_LOOP || disabled" :max="maxValue" :min="minValue" :precision="0" class="w60" v-model="valueLoop.interval"/>
  22 + 秒
  23 + </div>
  24 + <div class="item">
  25 + <a-radio value="TYPE_SPECIFY" class="choice" :disabled="disabled">指定</a-radio>
  26 + <div class="list">
  27 + <a-checkbox-group v-model="valueList">
  28 + <template v-for="i in maxValue+1">
  29 + <a-checkbox class="list-check-item" :key="`key-${i-1}`" :value="i-1" :disabled="type!==TYPE_SPECIFY || disabled">{{i-1}}</a-checkbox>
  30 + </template>
  31 + </a-checkbox-group>
  32 + </div>
  33 + </div>
  34 + </a-radio-group>
  35 + </div>
  36 +</template>
  37 +
  38 +<script>
  39 +import mixin from './mixin'
  40 +
  41 +export default {
  42 + name: 'second',
  43 + mixins: [mixin],
  44 + data() {
  45 + return {}
  46 + },
  47 + watch: {
  48 + value_c(newVal, oldVal) {
  49 + this.$emit('change', newVal)
  50 + }
  51 + },
  52 + created() {
  53 + this.DEFAULT_VALUE = '*'
  54 + this.minValue = 0
  55 + this.maxValue = 59
  56 + this.valueRange.start = 0
  57 + this.valueRange.end = 59
  58 + this.valueLoop.start = 0
  59 + this.valueLoop.interval = 1
  60 + // console.info('created')
  61 + this.parseProp(this.prop)
  62 + }
  63 +}
  64 +</script>
  65 +
  66 +<style lang="less" scoped>
  67 + @import "mixin.less";
  68 +</style>
... ...
ant-design-vue-jeecg/src/components/jeecg/JEasyCron/tabs/week.vue 0 → 100644
  1 +<template>
  2 + <div class="config-list">
  3 + <a-radio-group v-model="type">
  4 + <div class="item">
  5 + <a-radio value="TYPE_NOT_SET" class="choice" :disabled="disableChoice">不设置</a-radio>
  6 + <span class="tip-info">日和周只能设置其中之一</span>
  7 + </div>
  8 + <div class="item">
  9 + <a-radio value="TYPE_RANGE" class="choice" :disabled="disableChoice">区间</a-radio>
  10 + 从
  11 + <a-select v-model="valueRange.start" class="w80" :disabled="type!==TYPE_RANGE || disableChoice">
  12 + <template v-for="(v, k) of WEEK_MAP">
  13 + <a-select-option :value="v">{{k}}</a-select-option>
  14 + </template>
  15 + </a-select>
  16 + 至
  17 + <a-select v-model="valueRange.end" class="w80" :disabled="type!==TYPE_RANGE || disableChoice">
  18 + <template v-for="(v, k) of WEEK_MAP">
  19 + <a-select-option :value="v">{{k}}</a-select-option>
  20 + </template>
  21 + </a-select>
  22 + </div>
  23 + <div class="item">
  24 + <a-radio value="TYPE_LOOP" class="choice" :disabled="disableChoice">循环</a-radio>
  25 + 从
  26 + <a-select v-model="valueLoop.start" class="w80" :disabled="type!==TYPE_LOOP || disableChoice">
  27 + <template v-for="(v, k) of WEEK_MAP">
  28 + <a-select-option :value="v">{{k}}</a-select-option>
  29 + </template>
  30 + </a-select>
  31 + 开始,间隔
  32 + <a-input-number :disabled="type!==TYPE_LOOP || disableChoice" :max="maxValue" :min="minValue" :precision="0" class="w60" v-model="valueLoop.interval"/>
  33 + 天
  34 + </div>
  35 + <div class="item">
  36 + <a-radio value="TYPE_SPECIFY" class="choice" :disabled="disableChoice">指定</a-radio>
  37 + <div class="list">
  38 + <a-checkbox-group v-model="valueList">
  39 + <template v-for="i in maxValue+1">
  40 + <a-checkbox class="list-check-item" :key="`key-${i-1}`" :value="i-1" :disabled="type!==TYPE_SPECIFY || disabled">{{i-1}}</a-checkbox>
  41 + </template>
  42 + </a-checkbox-group>
  43 + </div>
  44 + </div>
  45 + </a-radio-group>
  46 + </div>
  47 +</template>
  48 +
  49 +<script>
  50 +import mixin from './mixin'
  51 +import { replaceWeekName, WEEK_MAP_EN } from './const.js'
  52 +
  53 +const WEEK_MAP = {
  54 + '周日': 0,
  55 + '周一': 1,
  56 + '周二': 2,
  57 + '周三': 3,
  58 + '周四': 4,
  59 + '周五': 5,
  60 + '周六': 6
  61 +}
  62 +
  63 +export default {
  64 + name: 'week',
  65 + mixins: [mixin],
  66 + props: {
  67 + day: {
  68 + type: String,
  69 + default: '*'
  70 + }
  71 + },
  72 + data() {
  73 + return {
  74 + WEEK_MAP,
  75 + WEEK_MAP_EN
  76 + }
  77 + },
  78 + computed: {
  79 + disableChoice() {
  80 + return (this.day && this.day !== '?') || this.disabled
  81 + }
  82 + },
  83 + watch: {
  84 + value_c(newVal, oldVal) {
  85 + // 如果设置日,那么星期就直接不设置
  86 + this.updateValue()
  87 + },
  88 + day(newVal) {
  89 + // console.info('new day: ' + newVal)
  90 + this.updateValue()
  91 + }
  92 + },
  93 + methods: {
  94 + updateValue() {
  95 + this.$emit('change', this.disableChoice ? '?' : this.value_c)
  96 + },
  97 + preProcessProp(c) {
  98 + return replaceWeekName(c)
  99 + }
  100 + },
  101 + created() {
  102 + this.DEFAULT_VALUE = '*'
  103 + // 0,7表示周日 1表示周一
  104 + this.minValue = 0
  105 + this.maxValue = 6
  106 + this.valueRange.start = 0
  107 + this.valueRange.end = 6
  108 + this.valueLoop.start = 2
  109 + this.valueLoop.interval = 1
  110 + this.parseProp(this.prop)
  111 + }
  112 +}
  113 +</script>
  114 +
  115 +<style lang="less" scoped>
  116 + @import "mixin.less";
  117 +</style>
... ...
ant-design-vue-jeecg/src/components/jeecg/JEasyCron/tabs/year.vue 0 → 100644
  1 +<template>
  2 + <div class="config-list">
  3 + <a-radio-group v-model="type">
  4 + <div class="item">
  5 + <a-radio value="TYPE_EVERY" class="choice" :disabled="disabled">每年</a-radio>
  6 + </div>
  7 + <div class="item">
  8 + <a-radio value="TYPE_RANGE" class="choice" :disabled="disabled">区间</a-radio>
  9 + 从
  10 + <a-input-number :disabled="type!==TYPE_RANGE || disabled" :min="0" :precision="0" class="w60" v-model="valueRange.start"/>
  11 + 年
  12 + 至
  13 + <a-input-number :disabled="type!==TYPE_RANGE || disabled" :min="1" :precision="0" class="w60" v-model="valueRange.end"/>
  14 + 年
  15 + </div>
  16 + <div class="item">
  17 + <a-radio value="TYPE_LOOP" class="choice" :disabled="disabled">循环</a-radio>
  18 + 从
  19 + <a-input-number :disabled="type!==TYPE_LOOP || disabled" :min="0" :precision="0" class="w60" v-model="valueLoop.start"/>
  20 + 年开始,间隔
  21 + <a-input-number :disabled="type!==TYPE_LOOP || disabled" :min="1" :precision="0" class="w60" v-model="valueLoop.interval"/>
  22 + 年
  23 + </div>
  24 + </a-radio-group>
  25 + </div>
  26 +</template>
  27 +
  28 +<script>
  29 +import mixin from './mixin'
  30 +
  31 +export default {
  32 + name: 'year',
  33 + mixins: [mixin],
  34 + data() {
  35 + return {}
  36 + },
  37 + watch: {
  38 + value_c(newVal, oldVal) {
  39 + // console.info('change:' + newVal)
  40 + this.$emit('change', newVal)
  41 + }
  42 + },
  43 + created() {
  44 + const nowYear = (new Date()).getFullYear()
  45 + this.DEFAULT_VALUE = '*'
  46 + this.minValue = 0
  47 + this.maxValue = 0
  48 + this.valueRange.start = nowYear
  49 + this.valueRange.end = nowYear + 100
  50 + this.valueLoop.start = nowYear
  51 + this.valueLoop.interval = 1
  52 + // console.info('created')
  53 + this.parseProp(this.prop)
  54 + }
  55 +}
  56 +</script>
  57 +
  58 +<style lang="less" scoped>
  59 + @import "mixin.less";
  60 +</style>
... ...
ant-design-vue-jeecg/src/components/jeecg/JEasyCron/validator.js 0 → 100644
  1 +import CronParser from 'cron-parser'
  2 +import { replaceWeekName } from './tabs/const'
  3 +
  4 +export default (rule, value, callback) => {
  5 + // 没填写就不校验
  6 + if (!value) {
  7 + callback()
  8 + return true
  9 + }
  10 + const values = value.split(' ').filter(item => !!item)
  11 + if (values.length > 7) {
  12 + callback(new Error('Cron表达式最多7项!'))
  13 + return false
  14 + }
  15 + // 检查第7项
  16 + let e = value
  17 + if (values.length === 7) {
  18 + const year = replaceWeekName(values[6])
  19 + if (year !== '*' && year !== '?') {
  20 + let yearValues = []
  21 + if (year.indexOf('-') >= 0) {
  22 + yearValues = year.split('-')
  23 + } else if (year.indexOf('/')) {
  24 + yearValues = year.split('/')
  25 + } else {
  26 + yearValues = [year]
  27 + }
  28 + // console.info(yearValues)
  29 + // 判断是否都是数字
  30 + const checkYear = yearValues.some(item => isNaN(item))
  31 + if (checkYear) {
  32 + callback(new Error('Cron表达式参数[年]错误:' + year))
  33 + return false
  34 + }
  35 + }
  36 + // 取其中的前六项
  37 + e = values.slice(0, 6).join(' ')
  38 + }
  39 + // 6位 没有年
  40 + // 5位没有秒、年
  41 + let result = true
  42 + try {
  43 + const iter = CronParser.parseExpression(e)
  44 + iter.next()
  45 + callback()
  46 + } catch (e) {
  47 + callback(new Error('Cron表达式错误:' + e))
  48 + result = false
  49 + }
  50 + return result
  51 +}
... ...
ant-design-vue-jeecg/src/components/jeecg/JEditableTable.vue
... ... @@ -350,7 +350,7 @@
350 350 <a-tooltip v-bind="buildTooltipProps(row, col, id)">
351 351 <a-upload
352 352 name="file"
353   - :data="{'isup':1}"
  353 + :data="{'isup':1, ...(col.data||{})}"
354 354 :multiple="false"
355 355 :action="col.action"
356 356 :headers="uploadGetHeaders(row,col)"
... ... @@ -381,6 +381,8 @@
381 381 :dest-fields="col.destFields"
382 382 :code="col.popupCode"
383 383 :groupId="caseId"
  384 + :param="col.param"
  385 + :sorter="col.sorter"
384 386 @input="(value,others)=>popupCallback(value,others,id,row,col,rowIndex)"
385 387 />
386 388 <span
... ... @@ -595,6 +597,33 @@
595 597 </template>
596 598 <!-- select搜索 -end -->
597 599  
  600 + <!-- select异步搜索 -begin -->
  601 + <template v-else-if="col.type === formTypes.sel_search_async">
  602 + <a-tooltip v-bind="buildTooltipProps(row, col, id)">
  603 + <j-search-select-tag
  604 + v-if="isEditRow(row, col)"
  605 + :id="id"
  606 + :key="i"
  607 + :value="searchSelectAsyncValues[id]"
  608 + :placeholder="replaceProps(col, col.placeholder)"
  609 + :dict="col.dict"
  610 + :async="true"
  611 + :getPopupContainer="getParentContainer"
  612 + v-bind="buildProps(row,col)"
  613 + style="width: 100%;"
  614 + @change="(v)=>handleSearchSelectAsyncChange(v,id,row,col)"
  615 + >
  616 + </j-search-select-tag>
  617 + <span
  618 + v-else
  619 + class="j-td-span no-edit"
  620 + :class="{disabled: buildProps(row,col).disabled}"
  621 + @click="handleEditRow(row, col)"
  622 + >{{ searchSelectAsyncValues[id] }}</span>
  623 + </a-tooltip>
  624 + </template>
  625 + <!-- select异步搜索 -end -->
  626 +
598 627 <div v-else-if="col.type === formTypes.slot" :key="i">
599 628 <a-tooltip v-bind="buildTooltipProps(row, col, id)">
600 629 <slot
... ... @@ -615,7 +644,7 @@
615 644 </div>
616 645  
617 646 <!-- else (normal) -->
618   - <span v-else :key="i" v-bind="buildProps(row,col)">{{ inputValues[rowIndex][col.key] }}</span>
  647 + <span class="comp-normal" v-else :key="i" :title="inputValues[rowIndex][col.key]" v-bind="buildProps(row,col)">{{ inputValues[rowIndex][col.key] }}</span>
619 648 </template>
620 649 </div>
621 650 </div>
... ... @@ -672,13 +701,13 @@
672 701 import Draggable from 'vuedraggable'
673 702 import { ACCESS_TOKEN } from '@/store/mutation-types'
674 703 import { FormTypes, VALIDATE_NO_PASSED } from '@/utils/JEditableTableUtil'
675   - import { cloneObject, randomString, randomNumber, getEventPath } from '@/utils/util'
  704 + import { cloneObject, getEventPath, randomNumber, randomString } from '@/utils/util'
676 705 import JDate from '@/components/jeecg/JDate'
677 706 import { filterDictText, initDictOptions } from '@/components/dict/JDictSelectUtil'
678   - import { getFileAccessHttpUrl } from '@/api/manage';
  707 + import { getFileAccessHttpUrl } from '@/api/manage'
679 708 import JInputPop from '@/components/jeecg/minipop/JInputPop'
680 709 import JFilePop from '@/components/jeecg/minipop/JFilePop'
681   - import { getNoAuthCols } from "@/utils/authFilter"
  710 + import { getNoAuthCols } from '@/utils/authFilter'
682 711  
683 712 // 行高,需要在实例加载完成前用到
684 713 let rowHeight = 61
... ... @@ -814,6 +843,7 @@
814 843 metaCheckboxValues: {},
815 844 multiSelectValues: {},
816 845 searchSelectValues: {},
  846 + searchSelectAsyncValues: {},
817 847 // 绑定左侧选择框已选择的id
818 848 selectedRowIds: [],
819 849 // 存储被删除行的id
... ... @@ -1048,6 +1078,10 @@
1048 1078 this.inputValues = []
1049 1079 this.rows = []
1050 1080 this.deleteIds = []
  1081 + this.selectedRowIds = []
  1082 + this.tooltips = {}
  1083 + this.notPassedIds = []
  1084 + // 重置values
1051 1085 this.selectValues = {}
1052 1086 this.checkboxValues = {}
1053 1087 this.jdateValues = {}
... ... @@ -1055,14 +1089,16 @@
1055 1089 this.departCompValues = {}
1056 1090 this.userCompValues = {}
1057 1091 this.slotValues = {}
1058   - this.selectedRowIds = []
1059   - this.tooltips = {}
1060   - this.notPassedIds = []
1061   - this.uploadValues = []
1062   - this.popupValues = []
1063   - this.radioValues = []
1064   - this.multiSelectValues = []
1065   - this.searchSelectValues = []
  1092 + //update-begin-author:shunjlei date:20210415 for:类型赋值错误
  1093 + this.uploadValues = {}
  1094 + this.popupValues = {}
  1095 + this.radioValues = {}
  1096 + this.multiSelectValues = {}
  1097 + this.searchSelectValues = {}
  1098 + this.searchSelectAsyncValues = {}
  1099 + //update-end-author:shunjlei date:20210415 for:类型赋值错误
  1100 +
  1101 + // 重置滚动条
1066 1102 this.scrollTop = 0
1067 1103 this.$nextTick(() => {
1068 1104 this.getElement('tbody').scrollTop = 0
... ... @@ -1136,6 +1172,7 @@
1136 1172 let radioValues = { ...this.radioValues }
1137 1173 let multiSelectValues = { ...this.multiSelectValues }
1138 1174 let searchSelectValues = { ...this.searchSelectValues }
  1175 + let searchSelectAsyncValues = { ...this.searchSelectAsyncValues }
1139 1176 // 禁用行的id
1140 1177 let disabledRowIds = (this.disabledRowIds || [])
1141 1178 dataSource.forEach((data, newValueIndex) => {
... ... @@ -1225,6 +1262,8 @@
1225 1262 radioValues[inputId] = sourceValue
1226 1263 } else if (column.type === FormTypes.sel_search) {
1227 1264 searchSelectValues[inputId] = sourceValue
  1265 + } else if (column.type === FormTypes.sel_search_async) {
  1266 + searchSelectAsyncValues[inputId] = sourceValue
1228 1267 } else if (column.type === FormTypes.list_multi) {
1229 1268 if (typeof sourceValue === 'string' && sourceValue.length > 0) {
1230 1269 multiSelectValues[inputId] = sourceValue.split(',')
... ... @@ -1245,6 +1284,8 @@
1245 1284 status: 'done',
1246 1285 path: sourceValue
1247 1286 }
  1287 + } else {
  1288 + uploadValues[inputId] = null
1248 1289 }
1249 1290 } else {
1250 1291 value[column.key] = sourceValue
... ... @@ -1309,6 +1350,7 @@
1309 1350 this.radioValues = radioValues
1310 1351 this.multiSelectValues = multiSelectValues
1311 1352 this.searchSelectValues = searchSelectValues
  1353 + this.searchSelectAsyncValues = searchSelectAsyncValues
1312 1354 // 重新计算所有统计列
1313 1355 this.recalcAllStatisticsColumns()
1314 1356 // 更新到 dom
... ... @@ -1543,6 +1585,8 @@
1543 1585 value[column.key] = this.radioValues[inputId]
1544 1586 } else if (column.type === FormTypes.sel_search) {
1545 1587 value[column.key] = this.searchSelectValues[inputId]
  1588 + } else if (column.type === FormTypes.sel_search_async) {
  1589 + value[column.key] = this.searchSelectAsyncValues[inputId]
1546 1590 } else if (column.type === FormTypes.list_multi) {
1547 1591 if (!this.multiSelectValues[inputId] || this.multiSelectValues[inputId].length === 0) {
1548 1592 value[column.key] = ''
... ... @@ -1671,6 +1715,7 @@
1671 1715 radioValues: this.radioValues,
1672 1716 multiSelectValues: this.multiSelectValues,
1673 1717 searchSelectValues: this.searchSelectValues,
  1718 + searchSelectAsyncValues: this.searchSelectAsyncValues,
1674 1719 })
1675 1720 },
1676 1721 /** 设置某行某列的值 */
... ... @@ -1736,6 +1781,8 @@
1736 1781 edited = this.setOneValue(this.multiSelectValues, modelKey, newValue, true)
1737 1782 } else if (column.type === FormTypes.sel_search) {
1738 1783 edited = this.setOneValue(this.searchSelectValues, modelKey, newValue)
  1784 + } else if (column.type === FormTypes.sel_search_async) {
  1785 + edited = this.setOneValue(this.searchSelectAsyncValues, modelKey, newValue)
1739 1786 } else {
1740 1787 edited = false
1741 1788 }
... ... @@ -2731,6 +2778,11 @@
2731 2778 this.validateOneInput(value, row, column, this.notPassedIds, true, 'change')
2732 2779 this.elemValueChange(FormTypes.sel_search, row, column, value)
2733 2780 },
  2781 + handleSearchSelectAsyncChange(value, id, row, column) {
  2782 + this.searchSelectAsyncValues = this.bindValuesChange(value, id, 'searchSelectAsyncValues')
  2783 + this.validateOneInput(value, row, column, this.notPassedIds, true, 'change')
  2784 + this.elemValueChange(FormTypes.sel_search_async, row, column, value)
  2785 + },
2734 2786 filterOption(input, option) {
2735 2787 return option.componentOptions.children[0].text.toLowerCase().indexOf(input.toLowerCase()) >= 0
2736 2788 },
... ... @@ -2992,6 +3044,8 @@
2992 3044 border-bottom: @border;
2993 3045 transition: background-color 300ms;
2994 3046 width: 100%;
  3047 + height: 61px;
  3048 + overflow: hidden;
2995 3049 position: absolute;
2996 3050 left: 0;
2997 3051 z-index: 10;
... ... @@ -3101,6 +3155,12 @@
3101 3155 }
3102 3156 }
3103 3157  
  3158 + .comp-normal {
  3159 + white-space: nowrap;
  3160 + overflow: hidden;
  3161 + text-overflow: ellipsis;
  3162 + }
  3163 +
3104 3164 .j-td-span {
3105 3165 position: relative;
3106 3166 padding: 4px 11px;
... ...
ant-design-vue-jeecg/src/components/jeecg/JImportModal.vue
... ... @@ -6,6 +6,13 @@
6 6 :confirmLoading="uploading"
7 7 @cancel="handleClose">
8 8  
  9 + <div style="margin: 0px 0px 5px 1px" v-if="online">
  10 + <span style="display: inline-block;height: 32px;line-height: 32px;vertical-align: middle;">是否开启校验:</span>
  11 + <span style="display: inline-block;height: 32px;margin-left: 6px">
  12 + <a-switch :checked="validateStatus==1" @change="handleChangeValidateStatus" checked-children="是" un-checked-children="否" size="small"/>
  13 + </span>
  14 + </div>
  15 +
9 16 <a-upload
10 17 name="file"
11 18 :multiple="true"
... ... @@ -47,6 +54,12 @@
47 54 type: String,
48 55 default: '',
49 56 required: false
  57 + },
  58 + //是否online导入
  59 + online:{
  60 + type: Boolean,
  61 + default: false,
  62 + required: false
50 63 }
51 64 },
52 65 data(){
... ... @@ -55,7 +68,8 @@
55 68 uploading:false,
56 69 fileList:[],
57 70 uploadAction:'',
58   - foreignKeys:''
  71 + foreignKeys:'',
  72 + validateStatus: 0
59 73 }
60 74 },
61 75 watch: {
... ... @@ -78,6 +92,7 @@
78 92 this.uploading = false
79 93 this.visible = true
80 94 this.foreignKeys = arg;
  95 + this.validateStatus = 0
81 96 },
82 97 handleRemove(file) {
83 98 const index = this.fileList.indexOf(file);
... ... @@ -98,6 +113,9 @@
98 113 if(this.foreignKeys && this.foreignKeys.length>0){
99 114 formData.append('foreignKeys',this.foreignKeys);
100 115 }
  116 + if(this.online==true){
  117 + formData.append('validateStatus',this.validateStatus);
  118 + }
101 119 fileList.forEach((file) => {
102 120 formData.append('files[]', file);
103 121 });
... ... @@ -105,14 +123,41 @@
105 123 postAction(this.uploadAction, formData).then((res) => {
106 124 this.uploading = false
107 125 if(res.success){
108   - this.$message.success(res.message)
  126 + if(res.code == 201){
  127 + this.errorTip(res.message, res.result)
  128 + }else{
  129 + this.$message.success(res.message)
  130 + }
109 131 this.visible=false
110 132 this.$emit('ok')
111 133 }else{
112 134 this.$message.warning(res.message)
113 135 }
114 136 })
115   - }
  137 + },
  138 + // 是否开启校验 开关改变事件
  139 + handleChangeValidateStatus(checked){
  140 + this.validateStatus = checked==true?1:0
  141 + },
  142 + // 错误信息提示
  143 + errorTip(tipMessage, fileUrl) {
  144 + const h = this.$createElement;
  145 + let href = window._CONFIG['domianURL'] + fileUrl
  146 + this.$warning({
  147 + title: '导入成功,但是有错误数据!',
  148 + content: h('div', {}, [
  149 + h('div', tipMessage),
  150 + h('span', '具体详情请 '),
  151 + h('a', {
  152 + attrs: {
  153 + href: href,
  154 + target: '_blank'
  155 + },
  156 + },'点击下载'),
  157 + ]),
  158 + onOk() {},
  159 + });
  160 + },
116 161  
117 162 }
118 163 }
... ...
ant-design-vue-jeecg/src/components/jeecg/JPopup.vue
... ... @@ -10,6 +10,7 @@
10 10 ref="jPopupOnlReport"
11 11 :code="code"
12 12 :multi="multi"
  13 + :sorter="sorter"
13 14 :groupId="uniqGroupId"
14 15 :param="param"
15 16 @ok="callBack"
... ... @@ -47,6 +48,11 @@
47 48 default: '',
48 49 required: false
49 50 },
  51 + /** 排序列,指定要排序的列,使用方式:列名=desc|asc */
  52 + sorter: {
  53 + type: String,
  54 + default: ''
  55 + },
50 56 width: {
51 57 type: Number,
52 58 default: 1200,
... ...
ant-design-vue-jeecg/src/components/jeecg/JUpload.vue
... ... @@ -12,7 +12,7 @@
12 12  
13 13 <a-upload
14 14 name="file"
15   - :multiple="true"
  15 + :multiple="multiple"
16 16 :action="uploadAction"
17 17 :headers="headers"
18 18 :data="{'biz':bizPath}"
... ... @@ -135,6 +135,10 @@
135 135 required:false,
136 136 default: true
137 137 },
  138 + multiple: {
  139 + type: Boolean,
  140 + default: true
  141 + },
138 142 },
139 143 watch:{
140 144 value:{
... ...
ant-design-vue-jeecg/src/components/jeecg/JVxeTable/components/JVxeTable.js
... ... @@ -13,7 +13,7 @@ import JVxeDetailsModal from &#39;./JVxeDetailsModal&#39;
13 13 import JVxePagination from './JVxePagination'
14 14 import { cloneObject, getVmParentByName, pushIfNotExist, randomString, simpleDebounce } from '@/utils/util'
15 15 import { UtilTools } from 'vxe-table/packages/tools/src/utils'
16   -import { getNoAuthCols } from "@/utils/authFilter"
  16 +import { getNoAuthCols } from '@/utils/authFilter'
17 17  
18 18 export default {
19 19 name: 'JVxeTable',
... ... @@ -95,6 +95,9 @@ export default {
95 95 // 是否异步删除行,如果你要实现异步删除,那么需要把这个选项开启,
96 96 // 在remove事件里调用confirmRemove方法才会真正删除(除非删除的全是新增的行)
97 97 asyncRemove: PropTypes.bool.def(false),
  98 + // 是否一直显示组件,如果为false则只有点击的时候才出现组件
  99 + // 注:该参数不能动态修改;如果行、列字段多的情况下,会根据机器性能造成不同程度的卡顿。
  100 + alwaysEdit: PropTypes.bool.def(false),
98 101 },
99 102 data() {
100 103 return {
... ... @@ -354,7 +357,7 @@ export default {
354 357 col.visible = false
355 358 } else if (enhanced.switches.editRender) {
356 359 renderName = 'editRender'
357   - renderOptions.type = enhanced.switches.visible ? 'visible' : 'default'
  360 + renderOptions.type = (enhanced.switches.visible || this.alwaysEdit) ? 'visible' : 'default'
358 361 }
359 362 } else {
360 363 renderOptions.name = JVXETypes._prefix + JVXETypes.normal
... ... @@ -1076,7 +1079,7 @@ export default {
1076 1079 // 添加默认值
1077 1080 xTable.tableFullColumn.forEach(column => {
1078 1081 let col = column.own
1079   - if (record[col.key] == null || record[col.key] === '') {
  1082 + if (col.key && (record[col.key] == null || record[col.key] === '')) {
1080 1083 // 设置默认值
1081 1084 let createValue = getEnhancedMixins(col.$type || col.type, 'createValue')
1082 1085 record[col.key] = createValue({row: record, column, $table: xTable})
... ...
ant-design-vue-jeecg/src/components/jeecg/JVxeTable/components/cells/JVxeDateCell.vue
... ... @@ -55,7 +55,9 @@
55 55 // 【组件增强】注释详见:JVxeCellMixins.js
56 56 enhanced: {
57 57 aopEvents: {
58   - editActived: event => dispatchEvent(event, 'ant-calendar-picker', el => el.children[0].dispatchEvent(event.$event)),
  58 + editActived(event) {
  59 + dispatchEvent.call(this, event, 'ant-calendar-picker', el => el.children[0].dispatchEvent(event.$event))
  60 + },
59 61 },
60 62 }
61 63 }
... ...
ant-design-vue-jeecg/src/components/jeecg/JVxeTable/components/cells/JVxeDragSortCell.vue
... ... @@ -34,7 +34,7 @@
34 34 return this.rowIndex === 0
35 35 },
36 36 disabledMoveDown() {
37   - return this.rowIndex === (this.rows.length - 1)
  37 + return this.rowIndex === (this.fullDataLength - 1)
38 38 },
39 39 },
40 40 methods: {
... ...
ant-design-vue-jeecg/src/components/jeecg/JVxeTable/components/cells/JVxeSelectCell.vue
... ... @@ -116,7 +116,9 @@
116 116 // 【组件增强】注释详见:JVxeCellMixins.js
117 117 enhanced: {
118 118 aopEvents: {
119   - editActived: event => dispatchEvent(event, 'ant-select'),
  119 + editActived(event) {
  120 + dispatchEvent.call(this, event, 'ant-select')
  121 + },
120 122 },
121 123 translate: {enabled: true},
122 124 getValue(value) {
... ...
ant-design-vue-jeecg/src/components/jeecg/JVxeTable/components/cells/JVxeTextareaCell.vue
... ... @@ -23,7 +23,9 @@
23 23 autofocus: '.ant-input',
24 24 },
25 25 aopEvents: {
26   - editActived: event => dispatchEvent(event, 'anticon-fullscreen'),
  26 + editActived(event) {
  27 + dispatchEvent.call(this, event, 'anticon-fullscreen')
  28 + },
27 29 },
28 30 },
29 31 }
... ...
ant-design-vue-jeecg/src/components/jeecg/JVxeTable/mixins/JVxeCellMixins.js
... ... @@ -36,6 +36,9 @@ export default {
36 36 rows() {
37 37 return this.params.data
38 38 },
  39 + fullDataLength() {
  40 + return this.params.$table.tableFullData.length
  41 + },
39 42 rowIndex() {
40 43 return this.params.rowIndex
41 44 },
... ... @@ -291,6 +294,10 @@ export function vModel(value, row, property) {
291 294  
292 295 /** 模拟触发事件 */
293 296 export function dispatchEvent({cell, $event}, className, handler) {
  297 + // alwaysEdit 下不模拟触发事件,否者会导致触发两次
  298 + if (this && this.alwaysEdit) {
  299 + return
  300 + }
294 301 window.setTimeout(() => {
295 302 let element = cell.getElementsByClassName(className)
296 303 if (element && element.length > 0) {
... ... @@ -298,9 +305,7 @@ export function dispatchEvent({cell, $event}, className, handler) {
298 305 handler(element[0])
299 306 } else {
300 307 // 模拟触发点击事件
301   - console.log($event)
302 308 if($event){
303   - console.log("$event===>",$event)
304 309 element[0].dispatchEvent($event)
305 310 }
306 311 }
... ...
ant-design-vue-jeecg/src/components/jeecg/index.js
... ... @@ -26,6 +26,7 @@ import JSlider from &#39;./JSlider.vue&#39;
26 26 import JSwitch from './JSwitch.vue'
27 27 import JTime from './JTime.vue'
28 28 import JTreeTable from './JTreeTable.vue'
  29 +import JEasyCron from "@/components/jeecg/JEasyCron";
29 30  
30 31 //jeecgbiz
31 32 import JSelectDepart from '../jeecgbiz/JSelectDepart.vue'
... ... @@ -71,5 +72,6 @@ export default {
71 72 Vue.component('JSelectPosition', JSelectPosition)
72 73 Vue.component('JSelectRole', JSelectRole)
73 74 Vue.component('JSelectUserByDep', JSelectUserByDep)
  75 + Vue.component(JEasyCron.name, JEasyCron)
74 76 }
75 77 }
76 78 \ No newline at end of file
... ...
ant-design-vue-jeecg/src/components/jeecg/modal/JCronModal.vue
1 1 <template>
2 2 <a-modal
3   - title="corn表达式"
  3 + title="cron表达式"
4 4 :width="modalWidth"
5 5 :visible="visible"
6 6 :confirmLoading="confirmLoading"
... ...
ant-design-vue-jeecg/src/components/jeecg/modal/JPopupOnlReport.vue
... ... @@ -78,7 +78,7 @@
78 78 const MODAL_WIDTH = 1200;
79 79 export default {
80 80 name: 'JPopupOnlReport',
81   - props: ['multi', 'code', 'groupId', 'param'],
  81 + props: ['multi', 'code', 'sorter', 'groupId', 'param'],
82 82 components:{
83 83 },
84 84 data(){
... ... @@ -122,8 +122,9 @@
122 122 cgRpConfigId:"",
123 123 modalWidth:MODAL_WIDTH,
124 124 tableScroll:{x:true},
125   - dynamicParam:{}
126   -
  125 + dynamicParam:{},
  126 + // 排序字段,默认无排序
  127 + iSorter: null,
127 128 }
128 129 },
129 130 mounted() {
... ... @@ -139,7 +140,28 @@
139 140 this.dynamicParamHandler()
140 141 this.loadData();
141 142 },
142   - }
  143 + },
  144 + sorter: {
  145 + immediate: true,
  146 + handler() {
  147 + if (this.sorter) {
  148 + let arr = this.sorter.split('=')
  149 + if (arr.length === 2 && ['asc', 'desc'].includes(arr[1].toLowerCase())) {
  150 + this.iSorter = {column: arr[0], order: arr[1].toLowerCase()}
  151 + // 排序字段受控
  152 + this.table.columns.forEach(col => {
  153 + if (col.dataIndex === this.iSorter.column) {
  154 + this.$set(col, 'sortOrder', this.iSorter.order === 'asc' ? 'ascend' : 'descend')
  155 + } else {
  156 + this.$set(col, 'sortOrder', false)
  157 + }
  158 + })
  159 + } else {
  160 + console.warn('【JPopup】sorter参数不合法')
  161 + }
  162 + }
  163 + },
  164 + },
143 165 },
144 166 computed:{
145 167 showSearchFlag(){
... ... @@ -167,6 +189,10 @@
167 189 return filterMultiDictText(this.dictOptions[dictCode], text+"");
168 190 }
169 191 }
  192 + // 排序字段受控
  193 + if (this.iSorter && currColumns[a].dataIndex === this.iSorter.column) {
  194 + currColumns[a].sortOrder = this.iSorter.order === 'asc' ? 'ascend' : 'descend'
  195 + }
170 196 }
171 197 this.table.columns = [...currColumns]
172 198 this.initQueryInfo()
... ... @@ -253,7 +279,7 @@
253 279 paramTarget['self_'+key] = this.dynamicParam[key]
254 280 })
255 281 }
256   - let param = Object.assign(paramTarget, this.queryParam, this.sorter);
  282 + let param = Object.assign(paramTarget, this.queryParam, this.iSorter);
257 283 param.pageNo = this.table.pagination.current;
258 284 param.pageSize = this.table.pagination.pageSize;
259 285 return filterObj(param);
... ... @@ -288,8 +314,18 @@
288 314 handleChangeInTable(pagination, filters, sorter) {
289 315 //分页、排序、筛选变化时触发
290 316 if (Object.keys(sorter).length > 0) {
291   - this.sorter.column = sorter.field
292   - this.sorter.order = 'ascend' == sorter.order ? 'asc' : 'desc'
  317 + this.iSorter = {
  318 + column: sorter.field,
  319 + order: 'ascend' === sorter.order ? 'asc' : 'desc'
  320 + }
  321 + // 排序字段受控
  322 + this.table.columns.forEach(col => {
  323 + if (col.dataIndex === sorter.field) {
  324 + this.$set(col, 'sortOrder',sorter.order)
  325 + } else {
  326 + this.$set(col, 'sortOrder', false)
  327 + }
  328 + })
293 329 }
294 330 this.table.pagination = pagination
295 331 this.loadData()
... ...
ant-design-vue-jeecg/src/components/jeecgbiz/modal/JSelectUserByDepModal.vue
... ... @@ -56,8 +56,9 @@
56 56 </template>
57 57  
58 58 <script>
59   - import {filterObj} from '@/utils/util'
  59 + import { pushIfNotExist, filterObj } from '@/utils/util'
60 60 import {queryDepartTreeList, getUserList, queryUserByDepId} from '@/api/api'
  61 + import { getAction } from '@/api/manage'
61 62  
62 63 export default {
63 64 name: 'JSelectUserByDepModal',
... ... @@ -106,6 +107,7 @@
106 107 ],
107 108 scrollTrigger: {},
108 109 dataSource: [],
  110 + selectionRows: [],
109 111 selectedRowKeys: [],
110 112 selectUserRows: [],
111 113 selectUserIds: [],
... ... @@ -163,11 +165,13 @@
163 165 pageSize: values.length
164 166 }).then((res) => {
165 167 if (res.success) {
  168 + this.selectionRows = []
166 169 let selectedRowKeys = []
167 170 let realNames = []
168 171 res.result.records.forEach(user => {
169 172 realNames.push(user['realname'])
170 173 selectedRowKeys.push(user['id'])
  174 + this.selectionRows.push(user)
171 175 })
172 176 this.selectedRowKeys = selectedRowKeys
173 177 this.$emit('initComp', realNames.join(','))
... ... @@ -182,20 +186,16 @@
182 186 if (arg === 1) {
183 187 this.ipagination.current = 1;
184 188 }
185   - if (this.selectedDepIds && this.selectedDepIds.length > 0) {
186   - await this.initQueryUserByDepId(this.selectedDepIds)
187   - } else {
188   - this.loading = true
189   - let params = this.getQueryParams()//查询条件
190   - await getUserList(params).then((res) => {
191   - if (res.success) {
192   - this.dataSource = res.result.records
193   - this.ipagination.total = res.result.total
194   - }
195   - }).finally(() => {
196   - this.loading = false
197   - })
198   - }
  189 + let params = this.getQueryParams()//查询条件
  190 + this.loading = true
  191 + getAction('/sys/user/queryUserComponentData', params).then(res=>{
  192 + if (res.success) {
  193 + this.dataSource = res.result.records
  194 + this.ipagination.total = res.result.total
  195 + }
  196 + }).finally(() => {
  197 + this.loading = false
  198 + })
199 199 },
200 200 // 触发屏幕自适应
201 201 resetScreenSize() {
... ... @@ -218,6 +218,7 @@
218 218 param.field = this.getQueryField();
219 219 param.pageNo = this.ipagination.current;
220 220 param.pageSize = this.ipagination.pageSize;
  221 + param.departId = this.selectedDepIds.join(',')
221 222 return filterObj(param);
222 223 },
223 224 getQueryField() {
... ... @@ -229,13 +230,13 @@
229 230 },
230 231 searchReset(num) {
231 232 let that = this;
  233 + that.selectedRowKeys = [];
  234 + that.selectUserIds = [];
  235 + that.selectedDepIds = [];
232 236 if (num !== 0) {
233 237 that.queryParam = {};
234 238 that.loadData(1);
235 239 }
236   - that.selectedRowKeys = [];
237   - that.selectUserIds = [];
238   - that.selectedDepIds = [];
239 240 },
240 241 close() {
241 242 this.searchReset(0);
... ... @@ -258,30 +259,27 @@
258 259 that.close();
259 260 },
260 261 //获取选择用户信息
261   - getSelectUserRows(rowId) {
262   - let dataSource = this.dataSource;
263   - let userIds = "";
264   - this.selectUserRows = [];
265   - for (let i = 0, len = dataSource.length; i < len; i++) {
266   - if (this.selectedRowKeys.includes(dataSource[i].id)) {
267   - this.selectUserRows.push(dataSource[i]);
268   - userIds = userIds + "," + dataSource[i].username
  262 + getSelectUserRows() {
  263 + this.selectUserRows = []
  264 + for (let row of this.selectionRows) {
  265 + if (this.selectedRowKeys.includes(row.id)) {
  266 + this.selectUserRows.push(row)
269 267 }
270 268 }
271   - this.selectUserIds = userIds.substring(1);
  269 + this.selectUserIds = this.selectUserRows.map(row => row.username).join(',')
272 270 },
273 271 // 点击树节点,筛选出对应的用户
274 272 onDepSelect(selectedDepIds) {
275 273 if (selectedDepIds[0] != null) {
276   - this.initQueryUserByDepId(selectedDepIds); // 调用方法根据选选择的id查询用户信息
277 274 if (this.selectedDepIds[0] !== selectedDepIds[0]) {
278 275 this.selectedDepIds = [selectedDepIds[0]];
279 276 }
  277 + this.loadData(1);
280 278 }
281 279 },
282 280 onSelectChange(selectedRowKeys, selectionRows) {
283 281 this.selectedRowKeys = selectedRowKeys;
284   - this.selectionRows = selectionRows;
  282 + selectionRows.forEach(row => pushIfNotExist(this.selectionRows, row, 'id'))
285 283 },
286 284 onSearch() {
287 285 this.loadData(1);
... ...
ant-design-vue-jeecg/src/components/jeecgbiz/thirdApp/JThirdAppButton.vue 0 → 100644
  1 +<template>
  2 + <span v-if="syncToApp || syncToLocal">
  3 + <j-third-app-dropdown v-if="enabledTypes.wechatEnterprise" type="wechatEnterprise" name="企微" v-bind="bindAttrs" v-on="bindEvents"/>
  4 + <j-third-app-dropdown v-if="enabledTypes.dingtalk" type="dingtalk" name="钉钉" v-bind="bindAttrs" v-on="bindEvents"/>
  5 + </span>
  6 + <span v-else>未设置任何同步方向</span>
  7 +</template>
  8 +
  9 +<script>
  10 +import { getAction } from '@/api/manage'
  11 +import { cloneObject } from '@/utils/util'
  12 +import JThirdAppDropdown from './JThirdAppDropdown'
  13 +
  14 +const backEndUrl = {
  15 + // 获取启用的第三方App
  16 + getEnabledType: '/sys/thirdApp/getEnabledType',
  17 + // 企业微信
  18 + wechatEnterprise: {
  19 + user: '/sys/thirdApp/sync/wechatEnterprise/user',
  20 + depart: '/sys/thirdApp/sync/wechatEnterprise/depart',
  21 + },
  22 + // 钉钉
  23 + dingtalk: {
  24 + user: '/sys/thirdApp/sync/dingtalk/user',
  25 + depart: '/sys/thirdApp/sync/dingtalk/depart',
  26 + }
  27 +}
  28 +
  29 +export default {
  30 + name: 'JThirdAppButton',
  31 + components: {JThirdAppDropdown},
  32 + props: {
  33 + // 同步类型,可以是 user、depart
  34 + bizType: {
  35 + type: String,
  36 + required: true,
  37 + },
  38 + // 是否允许同步到第三方APP
  39 + syncToApp: Boolean,
  40 + // 是否允许第三方APP同步到本地
  41 + syncToLocal: Boolean,
  42 + // 选择的行
  43 + selectedRowKeys: Array,
  44 + },
  45 + data() {
  46 + return {
  47 + enabledTypes: {},
  48 + attrs: {
  49 + dingtalk: {},
  50 + },
  51 + }
  52 + },
  53 + computed: {
  54 + bindAttrs() {
  55 + return {
  56 + syncToApp: this.syncToApp,
  57 + syncToLocal: this.syncToLocal
  58 + }
  59 + },
  60 + bindEvents() {
  61 + return {
  62 + 'to-app': this.onToApp,
  63 + 'to-local': this.onToLocal,
  64 + }
  65 + },
  66 + },
  67 + created() {
  68 + this.loadEnabledTypes()
  69 + },
  70 + methods: {
  71 + handleMenuClick() {
  72 + console.log(arguments)
  73 + },
  74 + onToApp(e) {
  75 + this.doSync(e.type, '/toApp')
  76 + },
  77 + onToLocal(e) {
  78 + this.doSync(e.type, '/toLocal')
  79 + },
  80 + // 获取启用的第三方App
  81 + async loadEnabledTypes() {
  82 + this.enabledTypes = await loadEnabledTypes()
  83 + },
  84 + // 开始同步第三方App
  85 + doSync(type, direction) {
  86 + let urls = backEndUrl[type]
  87 + if (!(urls && urls[this.bizType])) {
  88 + console.warn('配置出错')
  89 + return
  90 + }
  91 + let url = urls[this.bizType] + direction
  92 +
  93 + let selectedRowKeys = this.selectedRowKeys
  94 + let content = '确定要开始同步全部数据吗?可能花费较长时间!'
  95 + if (Array.isArray(selectedRowKeys) && selectedRowKeys.length > 0) {
  96 + content = `确定要开始同步这 ${selectedRowKeys.length} 项吗?`
  97 + } else {
  98 + selectedRowKeys = []
  99 + }
  100 + return new Promise((resolve, reject) => {
  101 + let model = this.$confirm({
  102 + title: '同步',
  103 + content,
  104 + onOk: () => {
  105 + model.update({
  106 + keyboard: false,
  107 + okText: '同步中…',
  108 + cancelButtonProps: {props: {disabled: true}}
  109 + })
  110 + return getAction(url, {
  111 + ids: selectedRowKeys.join(',')
  112 + }).then(res => {
  113 + let options = null
  114 + if (res.result) {
  115 + options = {
  116 + width: 600,
  117 + title: res.message,
  118 + content: (h) => {
  119 + let nodes
  120 + let successInfo = [
  121 + `成功信息如下:`,
  122 + this.renderTextarea(h, res.result.successInfo.map((v, i) => `${i + 1}. ${v}`).join('\n')),
  123 + ]
  124 + if (res.success) {
  125 + nodes = [
  126 + ...successInfo,
  127 + h('br'),
  128 + `无失败信息!`,
  129 + ]
  130 + } else {
  131 + nodes = [
  132 + `失败信息如下:`,
  133 + this.renderTextarea(h, res.result.failInfo.map((v, i) => `${i + 1}. ${v}`).join('\n')),
  134 + h('br'),
  135 + ...successInfo,
  136 + ]
  137 + }
  138 + return nodes
  139 + }
  140 + }
  141 + }
  142 + if (res.success) {
  143 + if (options != null) {
  144 + this.$success(options)
  145 + } else {
  146 + this.$message.success(res.message)
  147 + }
  148 + this.$emit('sync-ok')
  149 + } else {
  150 + if (options != null) {
  151 + this.$warning(options)
  152 + } else {
  153 + this.$message.warning(res.message)
  154 + }
  155 + this.$emit('sync-error')
  156 + }
  157 + }).catch(() => model.destroy()).finally(() => {
  158 + resolve()
  159 + this.$emit('sync-finally', {
  160 + type,
  161 + direction,
  162 + isToApp: direction === '/toApp',
  163 + isToLocal: direction === '/toLocal',
  164 + })
  165 + })
  166 + },
  167 + onCancel() {
  168 + resolve()
  169 + },
  170 + })
  171 + })
  172 + },
  173 + renderTextarea(h, value) {
  174 + return h('a-textarea', {
  175 + props: {
  176 + value: value,
  177 + readOnly: true,
  178 + autosize: {minRows: 5, maxRows: 10},
  179 + },
  180 + style: {
  181 + // 关闭textarea的自动换行,使其可以左右滚动
  182 + whiteSpace: 'pre',
  183 + overflow: 'auto',
  184 + }
  185 + })
  186 + }
  187 + },
  188 +}
  189 +
  190 +// 启用了哪些第三方App(在此缓存)
  191 +let enabledTypes = null
  192 +
  193 +// 获取启用的第三方App
  194 +export async function loadEnabledTypes() {
  195 + // 获取缓存
  196 + if (enabledTypes != null) {
  197 + return cloneObject(enabledTypes)
  198 + } else {
  199 + let {success, result} = await getAction(backEndUrl.getEnabledType)
  200 + if (success) {
  201 + // 在此缓存
  202 + enabledTypes = cloneObject(result)
  203 + return result
  204 + } else {
  205 + console.warn('getEnabledType查询失败:', res)
  206 + }
  207 + }
  208 + return {}
  209 +}
  210 +</script>
  211 +
  212 +<style scoped>
  213 +
  214 +</style>
0 215 \ No newline at end of file
... ...
ant-design-vue-jeecg/src/components/jeecgbiz/thirdApp/JThirdAppDropdown.vue 0 → 100644
  1 +<template>
  2 + <a-dropdown v-if="syncToApp && syncToLocal">
  3 + <a-button type="primary" icon="sync">同步{{name}}</a-button>
  4 + <a-menu slot="overlay" @click="handleMenuClick">
  5 + <a-menu-item v-if="syncToApp" key="to-app">同步到{{name}}</a-menu-item>
  6 + <a-menu-item v-if="syncToLocal" key="to-local">同步到本地</a-menu-item>
  7 + </a-menu>
  8 + </a-dropdown>
  9 + <a-button v-else-if="syncToApp" type="primary" icon="sync" @click="handleMenuClick({key:'to-app'})">同步{{name}}</a-button>
  10 + <a-button v-else type="primary" icon="sync" @click="handleMenuClick({key:'to-local'})">同步{{name}}到本地</a-button>
  11 +</template>
  12 +
  13 +<script>
  14 +
  15 +/* JThirdAppButton 的子组件,不可单独使用 */
  16 +export default {
  17 + name: 'JThirdAppDropdown',
  18 + props: {
  19 + type: String,
  20 + name: String,
  21 + syncToApp: Boolean,
  22 + syncToLocal: Boolean,
  23 + },
  24 + methods: {
  25 + handleMenuClick(event) {
  26 + this.$emit(event.key, {type: this.type})
  27 + },
  28 + },
  29 +}
  30 +</script>
  31 +
  32 +<style scoped>
  33 +
  34 +</style>
0 35 \ No newline at end of file
... ...
ant-design-vue-jeecg/src/components/layouts/TabLayout.vue
... ... @@ -36,9 +36,10 @@
36 36 import Contextmenu from '@/components/menu/Contextmenu'
37 37 import { mixin, mixinDevice } from '@/utils/mixin.js'
38 38 import { triggerWindowResizeEvent } from '@/utils/util'
39   - const indexKey = '/dashboard/analysis'
40 39 import Vue from 'vue'
41   - import { CACHE_INCLUDED_ROUTES } from "@/store/mutation-types"
  40 + import { CACHE_INCLUDED_ROUTES } from '@/store/mutation-types'
  41 +
  42 + const indexKey = '/dashboard/analysis'
42 43  
43 44 export default {
44 45 name: 'TabLayout',
... ... @@ -86,13 +87,6 @@
86 87 // 复制一个route对象出来,不能影响原route
87 88 let currentRoute = Object.assign({}, this.$route)
88 89 currentRoute.meta = Object.assign({}, currentRoute.meta)
89   - // update-begin-author:sunjianlei date:20191223 for: 修复刷新后菜单Tab名字显示异常
90   - let storeKey = 'route:title:' + currentRoute.fullPath
91   - let routeTitle = this.$ls.get(storeKey)
92   - if (routeTitle) {
93   - currentRoute.meta.title = routeTitle
94   - }
95   - // update-end-author:sunjianlei date:20191223 for: 修复刷新后菜单Tab名字显示异常
96 90 this.pageList.push(currentRoute)
97 91 this.linkList.push(currentRoute.fullPath)
98 92 this.activePage = currentRoute.fullPath
... ...
ant-design-vue-jeecg/src/components/lazy_antd.js
... ... @@ -57,7 +57,8 @@ import {
57 57 Cascader,
58 58 Slider,
59 59 Transfer,
60   - Rate
  60 + Rate,
  61 + Collapse,
61 62 } from 'ant-design-vue'
62 63 import Viser from 'viser-vue'
63 64  
... ... @@ -112,6 +113,7 @@ Vue.use(Cascader)
112 113 Vue.use(Slider)
113 114 Vue.use(Transfer)
114 115 Vue.use(Rate)
  116 +Vue.use(Collapse)
115 117  
116 118 Vue.prototype.$confirm = Modal.confirm
117 119 Vue.prototype.$message = message
... ...
ant-design-vue-jeecg/src/components/menu/SideMenu.vue
... ... @@ -11,6 +11,7 @@
11 11 :menu="menus"
12 12 :theme="theme"
13 13 @select="onSelect"
  14 + @updateMenuTitle="onUpdateMenuTitle"
14 15 :mode="mode"
15 16 :style="smenuStyle">
16 17 </s-menu>
... ... @@ -19,7 +20,7 @@
19 20 </template>
20 21  
21 22 <script>
22   - import ALayoutSider from "ant-design-vue/es/layout/Sider"
  23 + import ALayoutSider from 'ant-design-vue/es/layout/Sider'
23 24 import Logo from '../tools/Logo'
24 25 import SMenu from './index'
25 26 import { mixin, mixinDevice } from '@/utils/mixin.js'
... ... @@ -68,6 +69,9 @@
68 69 methods: {
69 70 onSelect (obj) {
70 71 this.$emit('menuSelect', obj)
  72 + },
  73 + onUpdateMenuTitle (obj) {
  74 + this.$emit('updateMenuTitle', obj)
71 75 }
72 76 }
73 77 }
... ...
ant-design-vue-jeecg/src/components/menu/index.js
... ... @@ -82,18 +82,49 @@ export default {
82 82 } else {
83 83 this.selectedKeys = [routes.pop().path]
84 84 }
85   - const openKeys = []
  85 + let openKeys = []
86 86 if (this.mode === 'inline') {
87 87 routes.forEach(item => {
88 88 openKeys.push(item.path)
89 89 })
90 90 }
  91 +
  92 + // update-begin-author:sunjianlei date:20210409 for: 修复动态功能测试菜单、带参数菜单标题错误、展开错误的问题
  93 + // 包含冒号的是动态菜单
  94 + if (this.selectedKeys[0].includes(':')) {
  95 + let selectedKey = this.$route.fullPath
  96 + this.selectedKeys = [selectedKey]
  97 + let newOpenKeys = []
  98 + this.fullOpenKeys(this.menu, selectedKey, newOpenKeys)
  99 + if (newOpenKeys.length > 0) {
  100 + openKeys = newOpenKeys.reverse()
  101 + }
  102 + }
  103 + // update-end-author:sunjianlei date:20210409 for: 修复动态功能测试菜单、带参数菜单标题错误、展开错误的问题
  104 +
91 105 //update-begin-author:taoyan date:20190510 for:online表单菜单点击展开的一级目录不对
92 106 if(!this.selectedKeys || this.selectedKeys[0].indexOf(":")<0){
93 107 this.collapsed ? (this.cachedOpenKeys = openKeys) : (this.openKeys = openKeys)
94 108 }
95 109 //update-end-author:taoyan date:20190510 for:online表单菜单点击展开的一级目录不对
96 110 },
  111 + // update-begin-author:sunjianlei date:20210409 for: 修复动态功能测试菜单、带参数菜单标题错误、展开错误的问题
  112 + // 递归查找当前选中的菜单和父级菜单,填充openKeys
  113 + fullOpenKeys(menus, selectedKey, openKeys) {
  114 + for (let item of menus) {
  115 + if (item.path === selectedKey) {
  116 + openKeys.push(item.path)
  117 + this.$emit('updateMenuTitle', item)
  118 + return true
  119 + } else if (Array.isArray(item.children)) {
  120 + if (this.fullOpenKeys(item.children, selectedKey, openKeys)) {
  121 + openKeys.push(item.path)
  122 + return true
  123 + }
  124 + }
  125 + }
  126 + },
  127 + // update-end-author:sunjianlei date:20210409 for: 修复动态功能测试菜单、带参数菜单标题错误、展开错误的问题
97 128  
98 129 // render
99 130 renderItem (menu) {
... ...
ant-design-vue-jeecg/src/components/page/GlobalHeader.vue
... ... @@ -31,7 +31,9 @@
31 31 <s-menu
32 32 mode="horizontal"
33 33 :menu="menus"
34   - :theme="theme"></s-menu>
  34 + :theme="theme"
  35 + @updateMenuTitle="handleUpdateMenuTitle"
  36 + ></s-menu>
35 37 </div>
36 38 <a-icon
37 39 v-else
... ... @@ -155,8 +157,15 @@
155 157 this.topMenuStyle.headerIndexLeft = { 'width': `calc(100% - ${rightWidth})` }
156 158 }
157 159 }
158   - }
  160 + },
159 161 //update-begin--author:sunjianlei---date:20190508------for: 顶部导航栏过长时显示更多按钮-----
  162 +
  163 + // update-begin-author:sunjianlei date:20210508 for: 修复动态功能测试菜单、带参数菜单标题错误、展开错误的问题
  164 + handleUpdateMenuTitle(value) {
  165 + this.$emit('updateMenuTitle', value)
  166 + },
  167 + // update-end-author:sunjianlei date:20210508 for: 修复动态功能测试菜单、带参数菜单标题错误、展开错误的问题
  168 +
160 169 }
161 170 }
162 171 </script>
... ...
ant-design-vue-jeecg/src/components/page/GlobalLayout.vue
... ... @@ -16,6 +16,7 @@
16 16 v-if="device === 'mobile'"
17 17 :menus="menus"
18 18 @menuSelect="menuSelect"
  19 + @updateMenuTitle="handleUpdateMenuTitle"
19 20 :theme="navTheme"
20 21 :collapsed="false"
21 22 :collapsible="true"></side-menu>
... ... @@ -26,6 +27,7 @@
26 27 mode="inline"
27 28 :menus="menus"
28 29 @menuSelect="myMenuSelect"
  30 + @updateMenuTitle="handleUpdateMenuTitle"
29 31 :theme="navTheme"
30 32 :collapsed="collapsed"
31 33 :collapsible="true"></side-menu>
... ... @@ -45,6 +47,7 @@
45 47 mode="inline"
46 48 :menus="menus"
47 49 @menuSelect="menuSelect"
  50 + @updateMenuTitle="handleUpdateMenuTitle"
48 51 :theme="navTheme"
49 52 :collapsed="false"
50 53 :collapsible="true"></side-menu>
... ... @@ -62,6 +65,7 @@
62 65 :collapsed="collapsed"
63 66 :device="device"
64 67 @toggle="toggle"
  68 + @updateMenuTitle="handleUpdateMenuTitle"
65 69 />
66 70  
67 71 <!-- layout content -->
... ... @@ -85,15 +89,14 @@
85 89 import SideMenu from '@/components/menu/SideMenu'
86 90 import GlobalHeader from '@/components/page/GlobalHeader'
87 91 import GlobalFooter from '@/components/page/GlobalFooter'
  92 + import { triggerWindowResizeEvent } from '@/utils/util'
  93 + import { mapActions, mapState } from 'vuex'
  94 + import { mixin, mixinDevice } from '@/utils/mixin.js'
88 95 // update-start---- author:os_chengtgen -- date:20190830 -- for:issues/463 -编译主题颜色已生效,但还一直转圈,显示主题 正在编译 ------
89 96 // import SettingDrawer from '@/components/setting/SettingDrawer'
90 97 // 注释这个因为在个人设置模块已经加载了SettingDrawer页面
91 98 // update-end ---- author:os_chengtgen -- date:20190830 -- for:issues/463 -编译主题颜色已生效,但还一直转圈,显示主题 正在编译 ------
92 99  
93   - import { triggerWindowResizeEvent } from '@/utils/util'
94   - import { mapState, mapActions } from 'vuex'
95   - import { mixin, mixinDevice } from '@/utils/mixin.js'
96   -
97 100 export default {
98 101 name: 'GlobalLayout',
99 102 components: {
... ... @@ -160,10 +163,6 @@
160 163 //此处触发动态路由被点击事件
161 164 this.findMenuBykey(this.menus,value.key)
162 165 this.$emit("dynamicRouterShow",value.key,this.activeMenu.meta.title)
163   - // update-begin-author:sunjianlei date:20191223 for: 修复刷新后菜单Tab名字显示异常
164   - let storeKey = 'route:title:' + this.activeMenu.path
165   - this.$ls.set(storeKey, this.activeMenu.meta.title)
166   - // update-end-author:sunjianlei date:20191223 for: 修复刷新后菜单Tab名字显示异常
167 166 },
168 167 findMenuBykey(menus,key){
169 168 for(let i of menus){
... ... @@ -173,8 +172,17 @@
173 172 this.findMenuBykey(i.children,key)
174 173 }
175 174 }
176   - }
  175 + },
177 176 //update-end-author:taoyan date:20190430 for:动态路由title显示配置的菜单title而不是其对应路由的title
  177 +
  178 + // update-begin-author:sunjianlei date:20210409 for: 修复动态功能测试菜单、带参数菜单标题错误、展开错误的问题
  179 + handleUpdateMenuTitle(value) {
  180 + this.findMenuBykey(this.menus, value.path)
  181 + this.activeMenu.meta.title = value.meta.title
  182 + this.$emit('dynamicRouterShow', value.path, this.activeMenu.meta.title)
  183 + },
  184 + // update-end-author:sunjianlei date:20210409 for: 修复动态功能测试菜单、带参数菜单标题错误、展开错误的问题
  185 +
178 186 }
179 187 }
180 188  
... ...
ant-design-vue-jeecg/src/components/tools/UserMenu.vue
... ... @@ -185,8 +185,8 @@
185 185 return that.Logout({}).then(() => {
186 186 // update-begin author:wangshuai date:20200601 for: 退出登录跳转登录页面
187 187 that.$router.push({ path: '/user/login' });
  188 + window.location.reload()
188 189 // update-end author:wangshuai date:20200601 for: 退出登录跳转登录页面
189   - //window.location.reload()
190 190 }).catch(err => {
191 191 that.$message.error({
192 192 title: '错误',
... ... @@ -225,11 +225,17 @@
225 225 // update_begin author:sunjianlei date:20191230 for: 解决外部链接打开失败的问题
226 226 searchMethods(value) {
227 227 let route = this.searchMenuOptions.filter(item => item.id === value)[0]
228   - if (route.meta.internalOrExternal === true || route.component.includes('layouts/IframePageView')) {
  228 + //update-begin-author:taoyan date:20210528 for: 【菜单问题】配置一个iframe地址的菜单,内部打开,在搜索菜单上打开却新开了一个窗口
  229 + if (route.meta.internalOrExternal === true) {
229 230 window.open(route.meta.url, '_blank')
230 231 } else {
231   - this.$router.push({ path: route.path })
  232 + if(route.component.includes('layouts/IframePageView')){
  233 + this.$router.push(route)
  234 + }else{
  235 + this.$router.push({ path: route.path })
  236 + }
232 237 }
  238 + //update-end-author:taoyan date:20210528 for: 【菜单问题】配置一个iframe地址的菜单,内部打开,在搜索菜单上打开却新开了一个窗口
233 239 this.searchMenuVisible = false
234 240 },
235 241 // update_end author:sunjianlei date:20191230 for: 解决外部链接打开失败的问题
... ...
ant-design-vue-jeecg/src/utils/JEditableTableUtil.js
... ... @@ -14,6 +14,7 @@ const FormTypes = {
14 14 popup:'popup',
15 15 list_multi:"list_multi",
16 16 sel_search:"sel_search",
  17 + sel_search_async:"sel_search_async",
17 18 radio:'radio',
18 19 checkbox_meta:"checkbox_meta",
19 20 input_pop:'input_pop',
... ...
ant-design-vue-jeecg/src/views/jeecg/SelectDemo.vue
... ... @@ -2,26 +2,35 @@
2 2 <a-card :bordered="false" style="height:100%;padding-bottom:200px; ">
3 3  
4 4 <div class="table-page-search-wrapper">
5   - <a-form layout="inline" :form="form">
  5 + <a-form-model ref="form" :model="formData" layout="inline">
6 6  
7 7  
8 8 <!-- 字典下拉 -->
9 9 <a-row :gutter="24">
10 10 <a-col :span="12">
11   - <a-form-item label="性别">
  11 + <a-form-model-item label="性别" prop="sex">
12 12 <j-dict-select-tag v-model="formData.sex" title="性别" dictCode="sex" placeholder="请选择性别"/>
13 13 <!-- <j-dict-select-tag title="性别" dictCode="sex" disabled/>-->
14   - </a-form-item>
  14 + </a-form-model-item>
15 15 </a-col>
16 16 <a-col :span="12">选中值:{{ formData.sex}}</a-col>
17 17 </a-row>
18 18  
  19 + <a-row :gutter="24">
  20 + <a-col :span="12">
  21 + <a-form-model-item label="性别2" prop="sex2">
  22 + <j-dict-select-tag v-model="formData.sex2" type="radioButton" title="性别2" dictCode="sex" placeholder="请选择性别2"/>
  23 + </a-form-model-item>
  24 + </a-col>
  25 + <a-col :span="12">选中值:{{ formData.sex2}}</a-col>
  26 + </a-row>
  27 +
19 28 <!-- 字典表下拉 -->
20 29 <a-row :gutter="24">
21 30 <a-col :span="12">
22   - <a-form-item label="字典表下拉">
  31 + <a-form-model-item label="字典表下拉" prop="user">
23 32 <j-dict-select-tag v-model="formData.user" placeholder="请选择用户" dictCode="sys_user,realname,id"/>
24   - </a-form-item>
  33 + </a-form-model-item>
25 34 </a-col>
26 35 <a-col :span="12">选中值:{{ formData.user}}</a-col>
27 36 </a-row>
... ... @@ -29,9 +38,9 @@
29 38 <!-- 带条件字典表下拉 -->
30 39 <a-row :gutter="24">
31 40 <a-col :span="12">
32   - <a-form-item label="字典表下拉(带条件)">
  41 + <a-form-model-item label="字典表下拉(带条件)" prop="user2">
33 42 <j-dict-select-tag v-model="formData.user2" placeholder="请选择用户" dictCode="sys_user,realname,id,username!='admin' order by create_time"/>
34   - </a-form-item>
  43 + </a-form-model-item>
35 44 </a-col>
36 45 <a-col :span="12">选中值:{{ formData.user2}}</a-col>
37 46 </a-row>
... ... @@ -40,10 +49,10 @@
40 49 <!-- 字典搜索 -->
41 50 <a-row :gutter="24">
42 51 <a-col :span="12">
43   - <a-form-item label="字典搜索(同步)">
  52 + <a-form-model-item label="字典搜索(同步)" prop="searchValue">
44 53 <j-search-select-tag placeholder="请做出你的选择" v-model="formData.searchValue" :dictOptions="searchOptions">
45 54 </j-search-select-tag>
46   - </a-form-item>
  55 + </a-form-model-item>
47 56 </a-col>
48 57 <a-col :span="12">选中值:{{ formData.searchValue}}</a-col>
49 58 </a-row>
... ... @@ -51,7 +60,7 @@
51 60 <!-- 字典搜索 异步加载 -->
52 61 <a-row :gutter="24">
53 62 <a-col :span="12">
54   - <a-form-item label="字典搜索(异步)">
  63 + <a-form-model-item label="字典搜索(异步)" prop="asyncSelectValue">
55 64 <j-search-select-tag
56 65 placeholder="请做出你的选择"
57 66 v-model="formData.asyncSelectValue"
... ... @@ -59,7 +68,7 @@
59 68 :pageSize="6"
60 69 :async="true">
61 70 </j-search-select-tag>
62   - </a-form-item>
  71 + </a-form-model-item>
63 72 </a-col>
64 73 <a-col :span="12">选中值:{{ formData.asyncSelectValue}}</a-col>
65 74 </a-row>
... ... @@ -67,13 +76,13 @@
67 76 <!-- JMultiSelectTag -->
68 77 <a-row :gutter="24">
69 78 <a-col :span="12">
70   - <a-form-item label="字典下拉(多选)">
  79 + <a-form-model-item label="字典下拉(多选)" prop="selMuti">
71 80 <j-multi-select-tag
72 81 v-model="formData.selMuti"
73 82 dictCode="sex"
74 83 placeholder="请选择">
75 84 </j-multi-select-tag>
76   - </a-form-item>
  85 + </a-form-model-item>
77 86 </a-col>
78 87 <a-col :span="12">多选组合(v-model):{{ formData.selMuti }}</a-col>
79 88 </a-row>
... ... @@ -81,48 +90,48 @@
81 90 <!-- 部门选择控件 -->
82 91 <a-row :gutter="24">
83 92 <a-col :span="12">
84   - <a-form-item label="选择部门 自定义返回值">
85   - <j-select-depart v-model="orgCodes" :trigger-change="true" customReturnField="orgCode" :multi="true"></j-select-depart>
86   - </a-form-item>
  93 + <a-form-model-item label="选择部门 自定义返回值" prop="orgCodes">
  94 + <j-select-depart v-model="formData.orgCodes" :trigger-change="true" customReturnField="orgCode" :multi="true"></j-select-depart>
  95 + </a-form-model-item>
87 96 </a-col>
88   - <a-col :span="12">选中的部门Code(v-decorator):{{ orgCodes }}</a-col>
  97 + <a-col :span="12">选中的部门Code(v-model):{{ formData.orgCodes }}</a-col>
89 98 </a-row>
90 99  
91 100 <a-row :gutter="24">
92 101 <a-col :span="12">
93   - <a-form-item label="选择部门">
94   - <j-select-depart v-model="departId" :multi="true"></j-select-depart>
95   - </a-form-item>
  102 + <a-form-model-item label="选择部门" prop="departId">
  103 + <j-select-depart v-model="formData.departId" :multi="true"></j-select-depart>
  104 + </a-form-model-item>
96 105 </a-col>
97   - <a-col :span="12">选中的部门ID(v-model):{{ departId }}</a-col>
  106 + <a-col :span="12">选中的部门ID(v-model):{{ formData.departId }}</a-col>
98 107 </a-row>
99 108  
100 109 <!-- 通过部门选择用户控件 -->
101 110 <a-row :gutter="24">
102 111 <a-col :span="12">
103   - <a-form-item label="选择用户">
104   - <j-select-user-by-dep v-model="userIds" :multi="true"></j-select-user-by-dep>
105   - </a-form-item>
  112 + <a-form-model-item label="选择用户" prop="userIds">
  113 + <j-select-user-by-dep v-model="formData.userIds" :multi="true"></j-select-user-by-dep>
  114 + </a-form-model-item>
106 115 </a-col>
107   - <a-col :span="12">选中的用户(v-model):{{ userIds }}</a-col>
  116 + <a-col :span="12">选中的用户(v-model):{{ formData.userIds }}</a-col>
108 117 </a-row>
109 118  
110 119 <!-- 用户选择控件 -->
111 120 <a-row :gutter="24">
112 121 <a-col :span="12">
113   - <a-form-item label="选择用户">
114   - <j-select-multi-user v-model="multiUser" :query-config="selectUserQueryConfig"/>
115   - </a-form-item>
  122 + <a-form-model-item label="选择用户" prop="multiUser">
  123 + <j-select-multi-user v-model="formData.multiUser" :query-config="selectUserQueryConfig"/>
  124 + </a-form-model-item>
116 125 </a-col>
117   - <a-col :span="12">选中的用户(v-model):{{ multiUser }}</a-col>
  126 + <a-col :span="12">选中的用户(v-model):{{ formData.multiUser }}</a-col>
118 127 </a-row>
119 128  
120 129 <!-- 角色选择 -->
121 130 <a-row :gutter="24">
122 131 <a-col :span="12">
123   - <a-form-item label="选择角色">
  132 + <a-form-model-item label="选择角色" prop="selectRole">
124 133 <j-select-role v-model="formData.selectRole" @change="changeMe"/>
125   - </a-form-item>
  134 + </a-form-model-item>
126 135 </a-col>
127 136 <a-col :span="12">选中值:{{ formData.selectRole}}</a-col>
128 137 </a-row>
... ... @@ -130,9 +139,9 @@
130 139 <!-- 职务选择 -->
131 140 <a-row :gutter="24">
132 141 <a-col :span="12">
133   - <a-form-item label="选择职务">
  142 + <a-form-model-item label="选择职务" prop="selectPosition">
134 143 <j-select-position :buttons="false" v-model="formData.selectPosition" />
135   - </a-form-item>
  144 + </a-form-model-item>
136 145 </a-col>
137 146 <a-col :span="12">选中值:{{ formData.selectPosition}}</a-col>
138 147 </a-row>
... ... @@ -140,90 +149,90 @@
140 149 <!-- JCheckbox -->
141 150 <a-row :gutter="24">
142 151 <a-col :span="12">
143   - <a-form-item label="多选组合">
  152 + <a-form-model-item label="多选组合" prop="jCheckbox">
144 153 <j-checkbox
145   - v-model="jcheckbox.values"
146   - :options="jcheckbox.options"
  154 + v-model="formData.jCheckbox"
  155 + :options="jCheckboxOptions"
147 156 />
148   - </a-form-item>
  157 + </a-form-model-item>
149 158 </a-col>
150   - <a-col :span="12">多选组合(v-model):{{ jcheckbox.values }}</a-col>
  159 + <a-col :span="12">多选组合(v-model):{{ formData.jCheckbox }}</a-col>
151 160 </a-row>
152 161  
153 162 <!-- JCodeEditor -->
154 163 <a-row :gutter="24">
155 164 <a-col :span="12">
156   - <a-form-item label="代码输入框" style="min-height: 120px">
  165 + <a-form-model-item label="代码输入框" style="min-height: 120px" prop="jCodeEditor">
157 166 <j-code-editor
158 167 language="javascript"
159   - v-model="jcodedditor.value"
  168 + v-model="formData.jCodeEditor"
160 169 :fullScreen="true"
161 170 style="min-height: 100px"/>
162   - </a-form-item>
  171 + </a-form-model-item>
163 172 </a-col>
164   - <a-col :span="12">代码输入框(v-model):{{ jcodedditor.value }}</a-col>
  173 + <a-col :span="12">代码输入框(v-model):{{ formData.jCodeEditor }}</a-col>
165 174 </a-row>
166 175  
167 176 <!-- JDate -->
168 177 <a-row :gutter="24">
169 178 <a-col :span="12">
170   - <a-form-item label="日期选择框">
171   - <j-date v-model="jdate.value" :showTime="true" dateFormat="YYYY-MM-DD HH:mm:ss"/>
172   - </a-form-item>
  179 + <a-form-model-item label="日期选择框" prop="jDate">
  180 + <j-date v-model="formData.jDate" :showTime="true" dateFormat="YYYY-MM-DD HH:mm:ss"/>
  181 + </a-form-model-item>
173 182 </a-col>
174   - <a-col :span="12">日期选择框(v-model):{{ jdate.value }}</a-col>
  183 + <a-col :span="12">日期选择框(v-model):{{ formData.jDate }}</a-col>
175 184 </a-row>
176 185  
177 186 <!-- JEditor -->
178 187 <a-row :gutter="24">
179 188 <a-col :span="12">
180   - <a-form-item label="富文本编辑器" style="min-height: 300px">
181   - <j-editor v-model="jeditor.value"/>
182   - </a-form-item>
  189 + <a-form-model-item label="富文本编辑器" style="min-height: 300px" prop="jEditor">
  190 + <j-editor v-model="formData.jEditor"/>
  191 + </a-form-model-item>
183 192 </a-col>
184   - <a-col :span="12">富文本编辑器(v-model):{{ jeditor.value }}</a-col>
  193 + <a-col :span="12">富文本编辑器(v-model):{{ formData.jEditor }}</a-col>
185 194 </a-row>
186 195  
187 196 <!-- JEllipsis -->
188 197 <a-row :gutter="24">
189 198 <a-col :span="12">
190   - <a-form-item label="过长剪切">
191   - <j-ellipsis :value="jellipsis.value" :length="30"/>
192   - </a-form-item>
  199 + <a-form-model-item label="过长剪切" prop="jEllipsis">
  200 + <j-ellipsis :value="formData.jEllipsis" :length="30"/>
  201 + </a-form-model-item>
193 202 </a-col>
194   - <a-col :span="12">过长剪切:{{ jellipsis.value }}</a-col>
  203 + <a-col :span="12">过长剪切:{{ formData.jEllipsis }}</a-col>
195 204 </a-row>
196 205  
197 206 <!-- JSlider -->
198 207 <a-row :gutter="24">
199 208 <a-col :span="12">
200   - <a-form-item label="滑块验证码">
  209 + <a-form-model-item label="滑块验证码" prop="jSlider">
201 210 <j-slider @onSuccess="handleJSliderSuccess"/>
202   - </a-form-item>
  211 + </a-form-model-item>
203 212 </a-col>
204   - <a-col :span="12">滑块验证码验证通过:{{ jslider.value }}</a-col>
  213 + <a-col :span="12">滑块验证码验证通过:{{ formData.jSlider }}</a-col>
205 214 </a-row>
206 215  
207 216 <!-- JSelectMultiple -->
208 217 <a-row :gutter="24">
209 218 <a-col :span="12">
210   - <a-form-item label="多选下拉框">
211   - <j-select-multiple v-model="jselectMultiple.value" :options="jselectMultiple.options"/>
212   - </a-form-item>
  219 + <a-form-model-item label="多选下拉框" prop="jSelectMultiple">
  220 + <j-select-multiple v-model="formData.jSelectMultiple" :options="jSelectMultipleOptions"/>
  221 + </a-form-model-item>
213 222 </a-col>
214   - <a-col :span="12">多选下拉框(v-model):{{ jselectMultiple.value }}</a-col>
  223 + <a-col :span="12">多选下拉框(v-model):{{ formData.jSelectMultiple }}</a-col>
215 224 </a-row>
216 225  
217 226 <!-- JSelectMultiple -->
218 227 <a-row :gutter="24">
219 228 <a-col>
220 229  
221   - <a-form-item label="JModal弹窗">
  230 + <a-form-model-item label="JModal弹窗">
222 231 <a-button style="margin-right: 8px;" @click="()=>modal.visible=true">点击弹出JModal</a-button>
223 232 <span style="margin-right: 8px;">全屏化:<a-switch v-model="modal.fullscreen"/></span>
224 233 <span style="margin-right: 8px;">允许切换全屏:<a-switch v-model="modal.switchFullscreen"/></span>
225 234  
226   - </a-form-item>
  235 + </a-form-model-item>
227 236  
228 237 <j-modal
229 238 :visible.sync="modal.visible"
... ... @@ -244,16 +253,16 @@
244 253  
245 254 <a-row :gutter="24">
246 255 <a-col :span="12">
247   - <a-form-item label="树字典">
248   - <j-tree-dict v-model="formData.treeDict" placeholder="请选择树字典" parentCode="B01" />
249   - </a-form-item>
  256 + <a-form-model-item label="树字典" prop="treeDict">
  257 + <j-tree-dict v-model="formData.treeDict" placeholder="请选择树字典" parentCode="A01" />
  258 + </a-form-model-item>
250 259 </a-col>
251 260 <a-col :span="12">选中的值(v-model):{{ formData.treeDict }}</a-col>
252 261 </a-row>
253 262  
254 263 <a-row :gutter="24">
255 264 <a-col :span="12">
256   - <a-form-item label="下拉树选择">
  265 + <a-form-model-item label="下拉树选择" prop="treeSelect">
257 266 <j-tree-select
258 267 v-model="formData.treeSelect"
259 268 placeholder="请选择菜单"
... ... @@ -261,14 +270,14 @@
261 270 pidField="parent_id"
262 271 pidValue=""
263 272 />
264   - </a-form-item>
  273 + </a-form-model-item>
265 274 </a-col>
266 275 <a-col :span="12">选中的值(v-model):{{ formData.treeSelect }}</a-col>
267 276 </a-row>
268 277  
269 278 <a-row :gutter="24">
270 279 <a-col :span="12">
271   - <a-form-item label="下拉树多选">
  280 + <a-form-model-item label="下拉树多选" prop="treeSelectMultiple">
272 281 <j-tree-select
273 282 v-model="formData.treeSelectMultiple"
274 283 placeholder="请选择菜单"
... ... @@ -277,7 +286,7 @@
277 286 pidValue=""
278 287 multiple
279 288 />
280   - </a-form-item>
  289 + </a-form-model-item>
281 290 </a-col>
282 291 <a-col :span="12">选中的值(v-model):{{ formData.treeSelectMultiple }}</a-col>
283 292 </a-row>
... ... @@ -285,9 +294,9 @@
285 294 <!-- 分类字典树 -->
286 295 <a-row :gutter="24">
287 296 <a-col :span="12">
288   - <a-form-item label="分类字典树">
  297 + <a-form-model-item label="分类字典树" prop="selectCategory">
289 298 <j-category-select v-model="formData.selectCategory" pcode="B01" :multiple="true"/>
290   - </a-form-item>
  299 + </a-form-model-item>
291 300 </a-col>
292 301 <a-col :span="12">选中的值(v-model):{{ formData.selectCategory }}</a-col>
293 302 </a-row>
... ... @@ -295,23 +304,23 @@
295 304 <!-- VueCron -->
296 305 <a-row :gutter="24">
297 306 <a-col :span="12">
298   - <a-form-item label="cron表达式">
299   - <j-cron ref="innerVueCron" v-decorator="['cronExpression', { initialValue: '* * * * * ? *' }]" @change="setCorn"></j-cron>
300   - </a-form-item>
  307 + <a-form-model-item label="cron表达式" prop="cronExpression">
  308 + <j-cron v-model="formData.cronExpression"></j-cron>
  309 + </a-form-model-item>
301 310 </a-col>
302 311 </a-row>
303 312  
304 313 <a-row :gutter="24">
305 314 <a-col :span="12">
306   - <a-form-item label="高级查询">
  315 + <a-form-model-item label="高级查询">
307 316 <j-super-query :fieldList="superQuery.fieldList" />
308   - </a-form-item>
  317 + </a-form-model-item>
309 318 </a-col>
310 319 </a-row>
311 320  
312 321 <a-row :gutter="24">
313 322 <a-col :span="12">
314   - <a-form-item label="高级查询(自定义按钮)">
  323 + <a-form-model-item label="高级查询(自定义按钮)">
315 324 <j-super-query :fieldList="superQuery.fieldList">
316 325 <!--
317 326 v-slot:button 可以更高自由的定制按钮
... ... @@ -334,34 +343,34 @@
334 343 </a-button-group>
335 344 </template>
336 345 </j-super-query>
337   - </a-form-item>
  346 + </a-form-model-item>
338 347 </a-col>
339 348 </a-row>
340 349  
341 350 <a-row :gutter="24">
342 351 <a-col :span="12">
343   - <a-form-item label="图片上传">
344   - <j-image-upload v-model="imgList"></j-image-upload>
345   - </a-form-item>
  352 + <a-form-model-item label="图片上传" prop="imgList">
  353 + <j-image-upload bizPath="scott/pic" v-model="formData.imgList"></j-image-upload>
  354 + </a-form-model-item>
346 355 </a-col>
347   - <a-col :span="12">选中的值(v-model):{{ imgList }}</a-col>
  356 + <a-col :span="12">选中的值(v-model):{{ formData.imgList }}</a-col>
348 357 </a-row>
349 358 <a-row :gutter="24" style="margin-top: 65px;margin-bottom:50px;">
350 359 <a-col :span="12">
351   - <a-form-item label="文件上传">
352   - <j-upload v-model="fileList"></j-upload>
353   - </a-form-item>
  360 + <a-form-model-item label="文件上传" prop="fileList">
  361 + <j-upload v-model="formData.fileList"></j-upload>
  362 + </a-form-model-item>
354 363 </a-col>
355 364 <a-col :span="12">
356 365 选中的值(v-model):
357   - <j-ellipsis :value="fileList" :length="30" v-if="fileList.length>0"/>
  366 + <j-ellipsis :value="formData.fileList" :length="30" v-if="formData.fileList.length>0"/>
358 367 </a-col>
359 368 </a-row>
360 369  
361 370 <!-- 特殊查询组件 -->
362 371 <a-row :gutter="24">
363 372 <a-col :span="12">
364   - <a-form-item label="特殊查询组件">
  373 + <a-form-model-item label="特殊查询组件" prop="jInput">
365 374 <a-row>
366 375 <a-col :span="15">
367 376 <j-input v-model="formData.jInput" :type="jInput.type"/>
... ... @@ -371,27 +380,27 @@
371 380 <a-select v-model="jInput.type" :options="jInput.options"></a-select>
372 381 </a-col>
373 382 </a-row>
374   - </a-form-item>
  383 + </a-form-model-item>
375 384 </a-col>
376 385 <a-col :span="12">输入的值(v-model):{{ formData.jInput }}</a-col>
377 386 </a-row>
378 387 <a-row :gutter="24">
379 388 <a-col :span="15">
380   - <a-form-item label="MarkdownEditor" style="min-height: 300px">
381   - <j-markdown-editor v-model="content"></j-markdown-editor>
382   - </a-form-item>
  389 + <a-form-model-item label="MarkdownEditor" prop="content" style="min-height: 300px">
  390 + <j-markdown-editor v-model="formData.content"></j-markdown-editor>
  391 + </a-form-model-item>
383 392 </a-col>
384 393 <a-col :span="9">
385   - 输入的值(v-model):{{ content }}
  394 + 输入的值(v-model):{{ formData.content }}
386 395 </a-col>
387 396 </a-row>
388 397  
389 398 <!-- 省市县级联 -->
390 399 <a-row :gutter="24">
391 400 <a-col :span="12">
392   - <a-form-item label="省市县级联">
  401 + <a-form-model-item label="省市县级联" prop="areaLinkage1">
393 402 <j-area-linkage v-model="formData.areaLinkage1" type="cascader"/>
394   - </a-form-item>
  403 + </a-form-model-item>
395 404 </a-col>
396 405 <a-col :span="12">输入的值(v-model):{{ formData.areaLinkage1 }}</a-col>
397 406 </a-row>
... ... @@ -400,9 +409,9 @@
400 409 <!-- 省市县级联 -->
401 410 <a-row :gutter="24">
402 411 <a-col :span="12">
403   - <a-form-item label="省市县级联">
  412 + <a-form-model-item label="省市县级联" prop="areaLinkage2">
404 413 <j-area-linkage v-model="formData.areaLinkage2" type="select"/>
405   - </a-form-item>
  414 + </a-form-model-item>
406 415 </a-col>
407 416 <a-col :span="12">输入的值(v-model):{{ formData.areaLinkage2 }}</a-col>
408 417 </a-row>
... ... @@ -410,23 +419,23 @@
410 419 <!-- 功能示例:关闭当前页面 -->
411 420 <a-row :gutter="24">
412 421 <a-col :span="12">
413   - <a-form-item label="功能示例:关闭当前页面">
  422 + <a-form-model-item label="功能示例:关闭当前页面">
414 423 <a-button type="primary" @click="handleCloseCurrentPage">点击关闭当前页面</a-button>
415   - </a-form-item>
  424 + </a-form-model-item>
416 425 </a-col>
417 426 </a-row>
418 427  
419 428 <!-- JPopup示例 -->
420 429 <a-row :gutter="24">
421 430 <a-col :span="12">
422   - <a-form-item label="JPopup示例">
  431 + <a-form-model-item label="JPopup示例" prop="jPopup">
423 432 <j-popup v-model="formData.jPopup" code="demo" field="name" orgFields="name" destFields="name" :multi="true"/>
424   - </a-form-item>
  433 + </a-form-model-item>
425 434 </a-col>
426 435 <a-col :span="12">选择的值(v-model):{{ formData.jPopup }}</a-col>
427 436 </a-row>
428 437  
429   - </a-form>
  438 + </a-form-model>
430 439 </div>
431 440  
432 441 </a-card>
... ... @@ -490,49 +499,35 @@
490 499 formData: {
491 500 areaLinkage1: '110105',
492 501 areaLinkage2: '140221',
493   - sex: 1
494   - },
495   - form: this.$form.createForm(this),
496   - departId: '57197590443c44f083d42ae24ef26a2c,a7d7e77e06c84325a40932163adcdaa6',
497   - orgCodes: 'A02A01,A02A02',
498   - userIds: 'admin',
499   - multiUser: 'admin,jeecg',
500   - jcheckbox: {
501   - values: 'spring,jeecgboot',
502   - options: [
503   - { label: 'Jeecg', value: 'jeecg' },
504   - { label: 'Jeecg-Boot', value: 'jeecgboot' },
505   - { label: 'Spring', value: 'spring', disabled: true },
506   - { label: 'MyBaits', value: 'mybatis' }
507   - ]
508   - },
509   - jcodedditor: {
510   - value: `function sayHi(word) {
511   - alert(word)
512   -}
513   -sayHi('hello, world!')`
514   - },
515   - jdate: {
516   - value: '2019-5-10 15:33:06'
517   - },
518   - jeditor: {
519   - value: '<h2 style="text-align: center;">富文本编辑器</h2> <p>这里是富文本编辑器。</p>'
520   - },
521   - jellipsis: {
522   - value: '这是一串很长很长的文字段落。这是一串很长很长的文字段落。这是一串很长很长的文字段落。这是一串很长很长的文字段落。'
523   - },
524   - jslider: {
525   - value: false
526   - },
527   - jselectMultiple: {
528   - options: [
529   - { text: '字符串', value: 'String' },
530   - { text: '整数型', value: 'Integer' },
531   - { text: '浮点型', value: 'Double' },
532   - { text: '布尔型', value: 'Boolean' }
533   - ],
534   - value: 'Integer,Boolean'
  502 + sex: 1,
  503 + orgCodes: 'A02A01,A02A02',
  504 + departId: '57197590443c44f083d42ae24ef26a2c,a7d7e77e06c84325a40932163adcdaa6',
  505 + userIds: 'admin',
  506 + multiUser: 'admin,jeecg',
  507 + jCheckbox: 'spring,jeecgboot',
  508 + jCodeEditor: `function sayHi(word) {\n alert(word)\n}\nsayHi('hello, world!')`,
  509 + jDate: '2019-5-10 15:33:06',
  510 + jEditor: '<h2 style="text-align: center;">富文本编辑器</h2> <p>这里是富文本编辑器。</p>',
  511 + jEllipsis: '这是一串很长很长的文字段落。这是一串很长很长的文字段落。这是一串很长很长的文字段落。这是一串很长很长的文字段落。',
  512 + jSlider: false,
  513 + jSelectMultiple: 'Integer,Boolean',
  514 + imgList:[],
  515 + fileList:[],
  516 + content: '',
  517 + cronExpression: '* * * * * ? *',
535 518 },
  519 + jCheckboxOptions: [
  520 + {label: 'Jeecg', value: 'jeecg'},
  521 + {label: 'Jeecg-Boot', value: 'jeecgboot'},
  522 + {label: 'Spring', value: 'spring', disabled: true},
  523 + {label: 'MyBaits', value: 'mybatis'}
  524 + ],
  525 + jSelectMultipleOptions: [
  526 + {text: '字符串', value: 'String'},
  527 + {text: '整数型', value: 'Integer'},
  528 + {text: '浮点型', value: 'Double'},
  529 + {text: '布尔型', value: 'Boolean'}
  530 + ],
536 531 modal: {
537 532 title: '这里是标题',
538 533 visible: false,
... ... @@ -556,8 +551,6 @@ sayHi(&#39;hello, world!&#39;)`
556 551 },
557 552 ]
558 553 },
559   - fileList:[],
560   - imgList:[],
561 554 jInput: {
562 555 type: 'like',
563 556 options: [
... ... @@ -567,7 +560,6 @@ sayHi(&#39;hello, world!&#39;)`
567 560 { value: 'le', label: '小于等于(le)' },
568 561 ],
569 562 },
570   - content: '',
571 563 searchOptions:[{
572 564 text:"选项一",
573 565 value:"1"
... ... @@ -599,10 +591,10 @@ sayHi(&#39;hello, world!&#39;)`
599 591 handleChange() {
600 592 },
601 593 getDepartIdValue() {
602   - return this.form.getFieldValue('departId')
  594 + return this.formData.departId
603 595 },
604 596 getOrgCodesValue() {
605   - return this.form.getFieldValue('orgCodes')
  597 + return this.formData.orgCodes
606 598 },
607 599 changeMe() {
608 600 console.log('you so ... , change Me')
... ... @@ -626,12 +618,7 @@ sayHi(&#39;hello, world!&#39;)`
626 618 this.selectedDepUsers = selectedDepUsers
627 619 },
628 620 handleJSliderSuccess(value) {
629   - this.jslider.value = value
630   - },
631   - setCorn(data){
632   - this.$nextTick(() => {
633   - this.form.cronExpression = data;
634   - })
  621 + this.formData.jSlider = value
635 622 },
636 623  
637 624 handleCloseCurrentPage() {
... ...
ant-design-vue-jeecg/src/views/jeecg/ThirdAppMessageTest.vue 0 → 100644
  1 +<template>
  2 + <a-card :bordered="false">
  3 + <a-spin :spinning="loading">
  4 + <a-form-model ref="form" :model="model" :rules="rules">
  5 + <a-tabs>
  6 + <a-tab-pane tab="消息选项" key="1">
  7 + <a-form-model-item label="测试APP" prop="app" :labelCol="labelCol" :wrapperCol="wrapperCol">
  8 + <a-select v-model="model.app" placeholder="请选择测试APP" :options="appOptions"/>
  9 + </a-form-model-item>
  10 + <a-form-model-item label="发送给所有人" prop="sendAll" :labelCol="labelCol" :wrapperCol="wrapperCol">
  11 + <a-switch checkedChildren="是" unCheckedChildren="否" v-model="model.sendAll" @change="onSendAllChange"/>
  12 + </a-form-model-item>
  13 + <a-form-model-item label="接收人" prop="receiver" :labelCol="labelCol" :wrapperCol="wrapperCol">
  14 + <j-select-multi-user v-model="model.receiver" :disabled="model.sendAll" placeholder="请选择接收人"/>
  15 + </a-form-model-item>
  16 + <a-form-model-item label="消息内容" prop="content" :labelCol="labelCol" :wrapperCol="wrapperCol">
  17 + <a-textarea :rows="5" v-model="model.content" placeholder="请输入消息内容"/>
  18 + </a-form-model-item>
  19 + <div style="text-align: center;">
  20 + <a-button type="primary" size="large" @click="onSend" style="width: 120px;">发送</a-button>
  21 + </div>
  22 + </a-tab-pane>
  23 + </a-tabs>
  24 +
  25 + <a-tabs>
  26 + <a-tab-pane tab="测试结果(刷新自动清空)" key="1">
  27 + <a-table
  28 + rowKey="id"
  29 + bordered
  30 + size="middle"
  31 + :columns="columns"
  32 + :dataSource="dataSource"
  33 + >
  34 + <div slot="action" slot-scope="text, record">
  35 + <template v-if="record.app==='DINGTALK'">
  36 + <a-popconfirm v-if="!record.recalled" title="确定吗?" @confirm="handleRecall(record)">
  37 + <a @click="">撤回</a>
  38 + </a-popconfirm>
  39 + <span v-else>已撤回</span>
  40 + </template>
  41 + <template v-else>-</template>
  42 + </div>
  43 + </a-table>
  44 +
  45 + </a-tab-pane>
  46 + </a-tabs>
  47 + </a-form-model>
  48 + </a-spin>
  49 + </a-card>
  50 +</template>
  51 +
  52 +<script>
  53 +import { loadEnabledTypes } from '@/components/jeecgbiz/thirdApp/JThirdAppButton'
  54 +import { postAction } from '@/api/manage'
  55 +import { randomUUID } from '@/utils/util'
  56 +
  57 +export default {
  58 + name: 'ThirdAppMessageTest',
  59 + data() {
  60 + return {
  61 + loading: false,
  62 + labelCol: {span: 6},
  63 + wrapperCol: {span: 12},
  64 + model: {
  65 + sendAll: false,
  66 + },
  67 + enabledTypes: {},
  68 + columns: [
  69 + {
  70 + title: '#',
  71 + dataIndex: '',
  72 + key: 'rowIndex',
  73 + width: 60,
  74 + align: 'center',
  75 + customRender: (t, r, index) => {
  76 + return this.dataSource.length - index
  77 + }
  78 + },
  79 + {
  80 + title: '测试APP',
  81 + align: 'center',
  82 + dataIndex: 'app',
  83 + customRender: (t, r, index) => {
  84 + if (t === 'WECHAT_ENTERPRISE') {
  85 + return '企业微信'
  86 + }
  87 + if (t === 'DINGTALK') {
  88 + return '钉钉'
  89 + } else {
  90 + return t
  91 + }
  92 + }
  93 + },
  94 + {
  95 + title: '接收人',
  96 + align: 'center',
  97 + dataIndex: 'receiver',
  98 + customRender: (t, r, index) => {
  99 + return r.sendAll ? '【全体】' : t
  100 + }
  101 + },
  102 + {
  103 + title: '消息内容',
  104 + align: 'center',
  105 + dataIndex: 'content'
  106 + },
  107 + {
  108 + title: 'response',
  109 + align: 'center',
  110 + dataIndex: 'response'
  111 + },
  112 + {
  113 + title: '操作',
  114 + dataIndex: 'action',
  115 + align: 'center',
  116 + fixed: 'right',
  117 + width: 80,
  118 + scopedSlots: {customRender: 'action'}
  119 + }
  120 + ],
  121 + dataSource: [],
  122 + }
  123 + },
  124 + computed: {
  125 + rules() {
  126 + return {
  127 + app: [{required: true, message: '请选择测试APP'}],
  128 + url: [{required: this.show, message: '请输入菜单路径!'}],
  129 + receiver: [{required: !this.model.sendAll, message: '请选择接收人'}],
  130 + content: [{required: true, message: '消息内容不能为空'}]
  131 + }
  132 + },
  133 + appOptions() {
  134 + return [
  135 + {
  136 + label: `企业微信${this.enabledTypes.wechatEnterprise ? '' : '(已禁用)'}`,
  137 + value: 'WECHAT_ENTERPRISE',
  138 + disabled: !this.enabledTypes.wechatEnterprise
  139 + },
  140 + {
  141 + label: `钉钉${this.enabledTypes.dingtalk ? '' : '(已禁用)'}`,
  142 + value: 'DINGTALK',
  143 + disabled: !this.enabledTypes.dingtalk
  144 + },
  145 + ]
  146 + },
  147 + },
  148 + created() {
  149 + this.loadEnabledTypes()
  150 + },
  151 + methods: {
  152 +
  153 + // 获取启用的第三方App
  154 + async loadEnabledTypes() {
  155 + this.enabledTypes = await loadEnabledTypes()
  156 + },
  157 +
  158 + onSendAllChange() {
  159 + this.$refs.form.clearValidate('receiver')
  160 + },
  161 +
  162 + onSend() {
  163 + this.$refs.form.validate((ok, err) => {
  164 + if (ok) {
  165 + this.loading = true
  166 + postAction('/sys/thirdApp/sendMessageTest', this.model).then(({success, result, message}) => {
  167 + if (success) {
  168 + let response = ''
  169 + try {
  170 + response = JSON.stringify(result)
  171 + } catch (e) {
  172 + response = result
  173 + }
  174 + this.dataSource.unshift(Object.assign({id: randomUUID()}, this.model, {response}))
  175 + } else {
  176 + this.$message.warning(message)
  177 + }
  178 + }).finally(() => this.loading = false)
  179 + }
  180 + })
  181 + },
  182 +
  183 + handleRecall(record) {
  184 + try {
  185 + let response = JSON.parse(record.response)
  186 + postAction('/sys/thirdApp/recallMessageTest', {
  187 + app: record.app,
  188 + msg_task_id: response.result
  189 + }).then(res => {
  190 + if (res.success) {
  191 + this.$set(record, 'recalled', true)
  192 + this.$message.success(res.message)
  193 + } else {
  194 + this.$message.warning(res.message)
  195 + }
  196 + }).catch(e => this.$message.warning(e.message || e))
  197 + } catch (e) {
  198 + this.$message.warning(e.message || e)
  199 + }
  200 + },
  201 +
  202 + },
  203 +}
  204 +</script>
  205 +
  206 +<style scoped>
  207 +
  208 +</style>
0 209 \ No newline at end of file
... ...
ant-design-vue-jeecg/src/views/jeecg/helloworld.vue
1 1 <template>
2 2 <a-card :bordered="false">
3   - <a-form @submit="handleSubmit" :form="form">
  3 + <a-form-model ref="form" :model="model" :rules="rules" @submit="handleSubmit">
4 4 <a-row>
5 5 <a-col :md="24" :sm="24">
6   - <a-form-item label="Note" :labelCol="{ span: 7 }" :wrapperCol="{ span: 15 }">
7   - <a-input v-decorator="['note',{rules: [{ required: true, message: 'Please input your note!' }]}]"/>
8   - </a-form-item>
  6 + <a-form-model-item label="Note" prop="note" :labelCol="{ span: 7 }" :wrapperCol="{ span: 15 }">
  7 + <a-input v-model="model.note"/>
  8 + </a-form-model-item>
9 9 </a-col>
10 10 </a-row>
11 11 <a-row>
12 12 <a-col :md="24" :sm="24">
13   - <a-form-item label="Gender" :labelCol="{ span: 7 }" :wrapperCol="{ span: 15 }">
14   - <a-select v-decorator="['gender',{rules: [{ required: true, message: 'Please select your gender!' }]}]" placeholder="Select a option and change input text above" @change="this.handleSelectChange">
  13 + <a-form-model-item label="Gender" prop="gender" :labelCol="{ span: 7 }" :wrapperCol="{ span: 15 }">
  14 + <a-select v-model="model.gender" placeholder="Select a option and change input text above" @change="handleSelectChange">
15 15 <a-select-option value="male">male</a-select-option>
16 16 <a-select-option value="female">female</a-select-option>
17 17 </a-select>
18   - </a-form-item>
  18 + </a-form-model-item>
19 19 </a-col>
20 20 </a-row>
21 21 <a-row>
22 22 <a-col :md="24" :sm="24">
23   - <a-form-item label="Gender" :labelCol="{ span: 7 }" :wrapperCol="{ span: 15 }">
  23 + <a-form-model-item label="Gender" prop="cascader" :labelCol="{ span: 7 }" :wrapperCol="{ span: 15 }">
24 24 <a-cascader :options="areaOptions" @change="onChange" :showSearch="{filter}" placeholder="Please select" />
25   - </a-form-item>
  25 + </a-form-model-item>
26 26 </a-col>
27 27 </a-row>
28   - <a-form-item :wrapperCol="{ span: 12, offset: 5 }">
  28 + <a-form-model-item :wrapperCol="{ span: 12, offset: 5 }">
29 29 <a-col :md="24" :sm="24">
30   - <a-form-item :wrapperCol="{ span: 12, offset: 5 }">
  30 + <a-form-model-item :wrapperCol="{ span: 12, offset: 5 }">
31 31 <a-button type="primary" htmlType="submit">Submit</a-button>
32   - </a-form-item>
  32 + </a-form-model-item>
33 33 </a-col>
34   - </a-form-item>
35   - </a-form>
  34 + </a-form-model-item>
  35 + </a-form-model>
36 36 </a-card>
37 37 </template>
38 38  
... ... @@ -43,24 +43,27 @@
43 43 data () {
44 44 return {
45 45 formLayout: 'horizontal',
46   - form: this.$form.createForm(this),
  46 + model: {},
  47 + rules: {
  48 + note: [{required: true, message: 'Please input your note!'}],
  49 + gender:[{ required: true, message: 'Please select your gender!' }]
  50 + },
47 51 areaOptions:[]
48 52 }
49 53 },
50 54 methods: {
51 55 handleSubmit (e) {
52 56 e.preventDefault()
53   - this.form.validateFields((err, values) => {
54   - if (!err) {
55   - console.log('Received values of form: ', values)
  57 + this.$refs.form.validate((ok, err) => {
  58 + if (ok) {
  59 + console.log('Received values of form: ', this.model)
  60 + this.$message.success('succeed!')
56 61 }
57 62 })
58 63 },
59 64 handleSelectChange (value) {
60 65 console.log(value)
61   - this.form.setFieldsValue({
62   - note: `Hi, ${value === 'male' ? 'man' : 'lady'}!`,
63   - })
  66 + this.model.note = `Hi, ${value === 'male' ? 'man' : 'lady'}!`
64 67 },
65 68 onChange(value, selectedOptions) {
66 69 console.log(value, selectedOptions);
... ...
ant-design-vue-jeecg/src/views/jeecg/modules/JEditableTable/DefaultTable.vue
... ... @@ -99,7 +99,11 @@
99 99 placeholder: '点击上传',
100 100 token: true,
101 101 responseName: 'message',
102   - action: window._CONFIG['domianURL'] + '/sys/common/upload'
  102 + action: window._CONFIG['domianURL'] + '/sys/common/upload',
  103 + data: {
  104 + biz: 'temp',
  105 + // 更多扩展参数
  106 + },
103 107 },
104 108 {
105 109 title: '字段类型',
... ...
ant-design-vue-jeecg/src/views/jeecg/modules/VueCronModal.vue
1 1 <template>
2 2 <a-modal
3   - title="corn表达式"
  3 + title="cron表达式"
4 4 :width="modalWidth"
5 5 :visible="visible"
6 6 :confirmLoading="confirmLoading"
... ...
ant-design-vue-jeecg/src/views/system/DepartListSync.vue
... ... @@ -4,13 +4,14 @@
4 4 <a-card :bordered="false">
5 5  
6 6 <!-- 按钮操作区域 -->
7   - <a-row style="margin-left: 14px">
  7 + <a-row style="margin: 0 0 0 14px" class="table-operator">
8 8 <a-button @click="handleAdd(1)" type="primary">添加部门</a-button>
9 9 <a-button @click="handleAdd(2)" type="primary">添加下级</a-button>
10 10 <a-button type="primary" icon="download" @click="handleExportXls('部门信息')">导出</a-button>
11 11 <a-upload name="file" :showUploadList="false" :multiple="false" :headers="tokenHeader" :action="importExcelUrl" @change="handleImportExcel">
12 12 <a-button type="primary" icon="import">导入</a-button>
13 13 </a-upload>
  14 + <j-third-app-button biz-type="depart" :selected-row-keys="selectedRowKeys" syncToApp @sync-finally="onSyncFinally"/>
14 15 <a-button title="删除多条数据" @click="batchDel" type="default">批量删除</a-button>
15 16 </a-row>
16 17 <div style="background: #fff;padding-left:16px;height: 100%; margin-top: 5px">
... ... @@ -27,6 +28,7 @@
27 28 <a-dropdown :trigger="[this.dropTrigger]" @visibleChange="dropStatus">
28 29 <span style="user-select: none">
29 30 <a-tree
  31 + v-if="loading"
30 32 checkable
31 33 multiple
32 34 @select="onSelect"
... ... @@ -36,11 +38,10 @@
36 38 :checkedKeys="checkedKeys"
37 39 :treeData="departTree"
38 40 :checkStrictly="checkStrictly"
39   - :expandedKeys="iExpandedKeys"
  41 + :expandedKeys.sync="iExpandedKeys"
40 42 :load-data="loadSubTree"
41 43 @expand="onExpand"/>
42 44 </span>
43   - <!--新增右键点击事件,和增加添加和删除功能-->
44 45 <a-menu slot="overlay">
45 46 <a-menu-item @click="handleAdd(3)" key="1">添加</a-menu-item>
46 47 <a-menu-item @click="handleDelete" key="2">删除</a-menu-item>
... ... @@ -73,42 +74,27 @@
73 74 <a-tabs defaultActiveKey="1">
74 75 <a-tab-pane tab="基本信息" key="1" >
75 76 <a-card :bordered="false" v-if="selectedKeys.length>0">
76   - <a-form :form="form">
77   - <a-form-item
78   - :labelCol="labelCol"
79   - :wrapperCol="wrapperCol"
80   - label="机构名称">
81   - <a-input placeholder="请输入机构/部门名称" v-decorator="['departName', validatorRules.departName ]"/>
82   - </a-form-item>
83   - <a-form-item :labelCol="labelCol" :wrapperCol="wrapperCol" label="上级部门">
84   - <a-tree-select
85   - style="width:100%"
86   - :dropdownStyle="{maxHeight:'200px',overflow:'auto'}"
87   - :treeData="treeData"
88   - :disabled="disable"
89   - v-model="model.parentId"
90   - placeholder="无">
  77 + <a-form-model ref="form" :model="model" :rules="validatorRules">
  78 + <a-form-model-item :labelCol="labelCol" :wrapperCol="wrapperCol" label="机构名称" prop="departName" >
  79 + <a-input placeholder="请输入机构/部门名称" v-model="model.departName"/>
  80 + </a-form-model-item>
  81 + <a-form-model-item :labelCol="labelCol" :wrapperCol="wrapperCol" label="上级部门" prop="parentId">
  82 + <a-tree-select style="width:100%" :dropdownStyle="{maxHeight:'200px',overflow:'auto'}" :treeData="treeData" :disabled="disable" v-model="model.parentId" placeholder="无">
91 83 </a-tree-select>
92   - </a-form-item>
93   - <a-form-item
94   - :labelCol="labelCol"
95   - :wrapperCol="wrapperCol"
96   - label="机构编码">
97   - <a-input disabled placeholder="请输入机构编码" v-decorator="['orgCode', validatorRules.orgCode ]"/>
98   - </a-form-item>
99   - <a-form-item
100   - :labelCol="labelCol"
101   - :wrapperCol="wrapperCol"
102   - label="机构类型">
  84 + </a-form-model-item>
  85 + <a-form-model-item :labelCol="labelCol" :wrapperCol="wrapperCol" label="机构编码" prop="orgCode">
  86 + <a-input disabled placeholder="请输入机构编码" v-model="model.orgCode"/>
  87 + </a-form-model-item>
  88 + <a-form-model-item :labelCol="labelCol" :wrapperCol="wrapperCol" label="机构类型" prop="orgCategory">
103 89 <template v-if="orgCategoryDisabled">
104   - <a-radio-group v-decorator="['orgCategory',validatorRules.orgCategory]" placeholder="请选择机构类型">
  90 + <a-radio-group v-model="model.orgCategory" placeholder="请选择机构类型">
105 91 <a-radio value="1">
106 92 公司
107 93 </a-radio>
108 94 </a-radio-group>
109 95 </template>
110 96 <template v-else>
111   - <a-radio-group v-decorator="['orgCategory',validatorRules.orgCategory]" placeholder="请选择机构类型">
  97 + <a-radio-group v-model="model.orgCategory" placeholder="请选择机构类型">
112 98 <a-radio value="2">
113 99 部门
114 100 </a-radio>
... ... @@ -117,32 +103,20 @@
117 103 </a-radio>
118 104 </a-radio-group>
119 105 </template>
120   - </a-form-item>
121   - <a-form-item
122   - :labelCol="labelCol"
123   - :wrapperCol="wrapperCol"
124   - label="排序">
125   - <a-input-number v-decorator="[ 'departOrder',{'initialValue':0}]"/>
126   - </a-form-item>
127   - <a-form-item
128   - :labelCol="labelCol"
129   - :wrapperCol="wrapperCol"
130   - label="手机号">
131   - <a-input placeholder="请输入手机号" v-decorator="['mobile', {'initialValue':''}]"/>
132   - </a-form-item>
133   - <a-form-item
134   - :labelCol="labelCol"
135   - :wrapperCol="wrapperCol"
136   - label="地址">
137   - <a-input placeholder="请输入地址" v-decorator="['address', {'initialValue':''}]"/>
138   - </a-form-item>
139   - <a-form-item
140   - :labelCol="labelCol"
141   - :wrapperCol="wrapperCol"
142   - label="备注">
143   - <a-textarea placeholder="请输入备注" v-decorator="['memo', {'initialValue':''}]"/>
144   - </a-form-item>
145   - </a-form>
  106 + </a-form-model-item>
  107 + <a-form-model-item :labelCol="labelCol" :wrapperCol="wrapperCol" label="排序" prop="departOrder">
  108 + <a-input-number v-model="model.departOrder"/>
  109 + </a-form-model-item>
  110 + <a-form-model-item :labelCol="labelCol" :wrapperCol="wrapperCol" label="手机号" prop="mobile">
  111 + <a-input placeholder="请输入手机号" v-model="model.mobile"/>
  112 + </a-form-model-item>
  113 + <a-form-model-item :labelCol="labelCol" :wrapperCol="wrapperCol" label="地址" prop="address">
  114 + <a-input placeholder="请输入地址" v-model="model.address"/>
  115 + </a-form-model-item>
  116 + <a-form-model-item :labelCol="labelCol" :wrapperCol="wrapperCol" label="备注" prop="memo">
  117 + <a-textarea placeholder="请输入备注" v-model="model.memo"/>
  118 + </a-form-model-item>
  119 + </a-form-model>
146 120 <div class="anty-form-btn">
147 121 <a-button @click="emptyCurrForm" type="default" htmlType="button" icon="sync">重置</a-button>
148 122 <a-button @click="submitCurrForm" type="primary" htmlType="button" icon="form">保存</a-button>
... ... @@ -165,11 +139,12 @@
165 139 </template>
166 140 <script>
167 141 import DepartModal from './modules/DepartModal'
168   - import pick from 'lodash.pick'
169   - import {queryDepartTreeSync, searchByKeywords, deleteByDepartId} from '@/api/api'
170   - import {httpAction, deleteAction} from '@/api/manage'
171   - import {JeecgListMixin} from '@/mixins/JeecgListMixin'
  142 + import { deleteByDepartId, queryDepartTreeSync, searchByKeywords } from '@/api/api'
  143 + import { deleteAction, httpAction } from '@/api/manage'
  144 + import { JeecgListMixin } from '@/mixins/JeecgListMixin'
172 145 import DepartAuthModal from './modules/DepartAuthModal'
  146 + import { cloneObject } from '@/utils/util'
  147 + import JThirdAppButton from '@comp/jeecgbiz/thirdApp/JThirdAppButton'
173 148 // 表头
174 149 const columns = [
175 150 {
... ... @@ -213,13 +188,14 @@
213 188 name: 'DepartList',
214 189 mixins: [JeecgListMixin],
215 190 components: {
  191 + JThirdAppButton,
216 192 DepartAuthModal,
217 193 DepartModal
218 194 },
219 195 data() {
220 196 return {
221 197 iExpandedKeys: [],
222   - loading: false,
  198 + loading: true,
223 199 autoExpandParent: false,
224 200 currFlowId: '',
225 201 currFlowName: '',
... ... @@ -244,9 +220,8 @@
244 220 currSelected: {},
245 221  
246 222 allTreeKeys:[],
  223 + loadTreeKeys:[],
247 224 checkStrictly: true,
248   -
249   - form: this.$form.createForm(this),
250 225 labelCol: {
251 226 xs: {span: 24},
252 227 sm: {span: 5}
... ... @@ -260,10 +235,10 @@
260 235 edges: []
261 236 },
262 237 validatorRules: {
263   - departName: {rules: [{required: true, message: '请输入机构/部门名称!'}]},
264   - orgCode: {rules: [{required: true, message: '请输入机构编码!'}]},
265   - orgCategory: {rules: [{required: true, message: '请输入机构类型!'}]},
266   - mobile: {rules: [{validator: this.validateMobile}]}
  238 + departName: [{required: true, message: '请输入机构/部门名称!'}],
  239 + orgCode: [{required: true, message: '请输入机构编码!'}],
  240 + orgCategory: [{required: true, message: '请输入机构类型!'}],
  241 + mobile: [{validator: this.validateMobile}]
267 242 },
268 243 url: {
269 244 delete: '/sys/sysDepart/delete',
... ... @@ -294,6 +269,10 @@
294 269 that.departTree = []
295 270 //所有的树节点key信息
296 271 that.allIds = []
  272 +
  273 + that.iExpandedKeys = []
  274 +
  275 + that.loading = false
297 276 queryDepartTreeSync().then((res) => {
298 277 if (res.success) {
299 278 this.allTreeKeys = [];
... ... @@ -304,30 +283,38 @@
304 283 that.departTree.push(temp)
305 284 that.allIds.push(temp.key)
306 285 that.allTreeKeys.push(temp.key)
  286 + if(that.loadTreeKeys.indexOf(temp.key)>=0){
  287 + that.iExpandedKeys.push(temp.key)
  288 + }
307 289 }
308   - this.loading = false
  290 + that.$nextTick(()=>{
  291 + that.loading = true
  292 + })
309 293 }
310 294 })
311 295 },
312 296 loadSubTree(treeNode) {
313 297 var that = this;
314 298 return new Promise(resolve => {
315   - queryDepartTreeSync({pid:treeNode.dataRef.id}).then((res) => {
316   - if (res.success) {
317   - //判断chidlren是否为空,并修改isLeaf属性值
318   - if(res.result.length == 0){
319   - treeNode.dataRef['isLeaf']=true
320   - return;
321   - }else{
322   - treeNode.dataRef['children']= res.result;
323   - }
324   - for (let i = 0; i < res.result.length; i++) {
325   - let temp = res.result[i]
326   - that.allIds.push(temp.key)
  299 + queryDepartTreeSync({pid:treeNode.dataRef.id}).then((res) => {
  300 + if (res.success) {
  301 + //判断chidlren是否为空,并修改isLeaf属性值
  302 + if(res.result.length == 0){
  303 + treeNode.dataRef['isLeaf']=true
  304 + return;
  305 + }else{
  306 + treeNode.dataRef['children']= res.result;
  307 + }
  308 + for (let i = 0; i < res.result.length; i++) {
  309 + let temp = res.result[i]
  310 + that.allIds.push(temp.key)
  311 + if(that.loadTreeKeys.indexOf(temp.key)>0){
  312 + that.iExpandedKeys.push(temp.key)
327 313 }
328 314 }
329   - })
330   - resolve();
  315 + }
  316 + })
  317 + resolve();
331 318 });
332 319 //保存全部部门信息,方便后面搜索使用
333 320 that.departTreeAll=that.departTree
... ... @@ -340,8 +327,7 @@
340 327 rightHandle(node) {
341 328 this.dropTrigger = 'contextmenu'
342 329 console.log(node.node.eventKey)
343   - //注释:异步书加载key拼接__,以便于每次展开节点会刷新数据
344   - this.rightClickSelectedKey = node.node.eventKey.split('__')[0]
  330 + this.rightClickSelectedKey = node.node.eventKey
345 331 this.rightClickSelectedOrgCode = node.node.dataRef.orgCode
346 332 },
347 333 onExpand(expandedKeys) {
... ... @@ -349,6 +335,7 @@
349 335 this.iExpandedKeys = expandedKeys
350 336 this.autoExpandParent = false
351 337 this.allTreeKeys=expandedKeys
  338 + this.loadTreeKeys=expandedKeys
352 339 },
353 340 backFlowList() {
354 341 this.$router.back(-1)
... ... @@ -373,7 +360,7 @@
373 360 } else {
374 361 var ids = ''
375 362 for (var a = 0; a < this.checkedKeys.length; a++) {
376   - ids += this.checkedKeys[a].split('__')[0] + ','
  363 + ids += this.checkedKeys[a]+ ','
377 364 }
378 365 var that = this
379 366 this.$confirm({
... ... @@ -453,8 +440,7 @@
453 440 this.orgCategoryDisabled = false;
454 441 }
455 442 this.$nextTick(() => {
456   - this.form.getFieldDecorator('fax', {initialValue: ''})
457   - this.form.setFieldsValue(pick(record, 'departName','orgCategory', 'orgCode', 'departOrder', 'mobile', 'fax', 'address', 'memo'))
  443 + this.model = cloneObject(record)
458 444 })
459 445 },
460 446 getCurrSelectedTitle() {
... ... @@ -464,7 +450,7 @@
464 450 this.hiding = true
465 451 this.checkedKeys = []
466 452 this.currSelected = {}
467   - this.form.resetFields()
  453 + this.model = cloneObject(this.currSelected)
468 454 this.selectedKeys = []
469 455 this.$refs.departAuth.departId = ''
470 456 },
... ... @@ -478,14 +464,14 @@
478 464 this.currSelected.receiptTriggerType = value
479 465 },
480 466 submitCurrForm() {
481   - this.form.validateFields((err, values) => {
482   - if (!err) {
  467 + this.$refs.form.validate((ok, err) => {
  468 + if (ok) {
483 469 if (!this.currSelected.id) {
484 470 this.$message.warning('请点击选择要修改部门!')
485 471 return
486 472 }
487 473  
488   - let formData = Object.assign(this.currSelected, values)
  474 + let formData = Object.assign(this.currSelected, this.model)
489 475 console.log('Received values of form: ', formData)
490 476 httpAction(this.url.edit, formData, 'put').then((res) => {
491 477 if (res.success) {
... ... @@ -499,12 +485,12 @@
499 485 })
500 486 },
501 487 emptyCurrForm() {
502   - this.form.resetFields()
  488 + this.model = this.currSelected
503 489 },
504 490 nodeSettingFormSubmit() {
505   - this.form.validateFields((err, values) => {
506   - if (!err) {
507   - console.log('Received values of form: ', values)
  491 + this.$refs.form.validate((ok, err) => {
  492 + if (ok) {
  493 + console.log('Received values of form: ', this.model)
508 494 }
509 495 })
510 496 },
... ... @@ -521,7 +507,7 @@
521 507 this.$message.warning('请先点击选中上级部门!')
522 508 return false
523 509 }
524   - this.$refs.departModal.add(this.selectedKeys[0].split('__')[0])
  510 + this.$refs.departModal.add(this.selectedKeys[0])
525 511 this.$refs.departModal.title = '新增'
526 512 } else {
527 513 this.$refs.departModal.add(this.rightClickSelectedKey)
... ... @@ -541,7 +527,7 @@
541 527 that.$message.success('删除成功!')
542 528 that.loadTree()
543 529 //删除后同步清空右侧基本信息内容
544   - let orgCode=that.form.getFieldValue("orgCode");
  530 + let orgCode = that.model.orgCode
545 531 if(orgCode && orgCode === that.rightClickSelectedOrgCode){
546 532 that.onClearSelected()
547 533 }
... ... @@ -576,6 +562,7 @@
576 562 // <!---- author:os_chengtgen -- date:20190827 -- for:切换父子勾选模式 =======------>
577 563 expandAll () {
578 564 this.iExpandedKeys = this.allTreeKeys
  565 + //this.loadTree()
579 566 },
580 567 closeAll () {
581 568 this.iExpandedKeys = []
... ... @@ -604,9 +591,24 @@
604 591 this.getAllKeys(node.children[a])
605 592 }
606 593 }
607   - }
  594 + },
608 595 // <!---- author:os_chengtgen -- date:20190827 -- for:切换父子勾选模式 =======------>
609   -
  596 +
  597 + // 验证手机号
  598 + validateMobile(rule,value,callback){
  599 + if (!value || new RegExp(/^1([38][0-9]|4[579]|5[0-3,5-9]|6[6]|7[0135678]|9[89])\d{8}$/).test(value)){
  600 + callback();
  601 + }else{
  602 + callback("您的手机号码格式不正确!");
  603 + }
  604 +
  605 + },
  606 + onSyncFinally({isToLocal}) {
  607 + // 同步到本地时刷新下数据
  608 + if (isToLocal) {
  609 + this.loadData()
  610 + }
  611 + },
610 612 },
611 613 created() {
612 614 this.currFlowId = this.$route.params.id
... ... @@ -617,6 +619,9 @@
617 619 }
618 620 </script>
619 621 <style scoped>
  622 + @import '~@assets/less/common.less';
  623 +</style>
  624 +<style scoped>
620 625 .ant-card-body .table-operator {
621 626 margin: 15px;
622 627 }
... ... @@ -661,10 +666,6 @@
661 666 }
662 667  
663 668 /** Button按钮间距 */
664   - .ant-btn {
665   - margin-left: 3px
666   - }
667   -
668 669 .drawer-bootom-button {
669 670 /*position: absolute;*/
670 671 bottom: 0;
... ...
ant-design-vue-jeecg/src/views/system/DepartUserList.vue
... ... @@ -25,7 +25,7 @@
25 25 <div style="margin-top: 24px;" v-else-if="userIdentity === '2' && departTree.length==0">
26 26 <h3><span>您的部门下暂无有效部门信息</span></h3>
27 27 </div>
28   - <div style="margin-top: 24px;" v-else><h3>普通员工暂此权限</h3></div>
  28 + <div style="margin-top: 24px;" v-else><h3>普通员工暂此权限</h3></div>
29 29 </div>
30 30 </a-card>
31 31 </a-col>
... ... @@ -49,8 +49,8 @@
49 49 <script>
50 50 import DeptBaseInfo from './modules/DeptBaseInfo'
51 51 import DeptUserInfo from './modules/DeptUserInfo'
52   - import {queryMyDepartTreeList, searchByKeywords} from '@/api/api'
53   - import {JeecgListMixin} from '@/mixins/JeecgListMixin'
  52 + import { queryMyDepartTreeList, searchByKeywords } from '@/api/api'
  53 + import { JeecgListMixin } from '@/mixins/JeecgListMixin'
54 54 import DeptRoleInfo from './modules/DeptRoleInfo'
55 55  
56 56 export default {
... ...
ant-design-vue-jeecg/src/views/system/QuartzJobList.vue
... ... @@ -3,22 +3,22 @@
3 3  
4 4 <!-- 查询区域 -->
5 5 <div class="table-page-search-wrapper">
6   - <a-form layout="inline" @keyup.enter.native="searchQuery">
  6 + <a-form-model layout="inline" :model="queryParam" @keyup.enter.native="searchQuery">
7 7 <a-row :gutter="24">
8 8  
9 9 <a-col :md="6" :sm="10">
10   - <a-form-item label="任务类名">
  10 + <a-form-model-item label="任务类名" prop="jobClassName">
11 11 <a-input placeholder="请输入任务类名" v-model="queryParam.jobClassName"></a-input>
12   - </a-form-item>
  12 + </a-form-model-item>
13 13 </a-col>
14 14 <a-col :md="6" :sm="10">
15   - <a-form-item label="任务状态">
  15 + <a-form-model-item label="任务状态" prop="status">
16 16 <a-select style="width: 220px" v-model="queryParam.status" placeholder="请选择状态">
17 17 <a-select-option value="">全部</a-select-option>
18 18 <a-select-option value="0">正常</a-select-option>
19 19 <a-select-option value="-1">停止</a-select-option>
20 20 </a-select>
21   - </a-form-item>
  21 + </a-form-model-item>
22 22 </a-col>
23 23  
24 24 <a-col :md="6" :sm="10" >
... ... @@ -29,7 +29,7 @@
29 29 </a-col>
30 30  
31 31 </a-row>
32   - </a-form>
  32 + </a-form-model>
33 33 </div>
34 34  
35 35 <!-- 操作按钮区域 -->
... ... @@ -225,7 +225,7 @@
225 225 title:"确认暂停",
226 226 content:"是否暂停选中任务?",
227 227 onOk: function(){
228   - getAction(that.url.pause,{jobClassName:record.jobClassName}).then((res)=>{
  228 + getAction(that.url.pause,{id:record.id}).then((res)=>{
229 229 if(res.success){
230 230 that.$message.success(res.message);
231 231 that.loadData();
... ... @@ -245,7 +245,7 @@
245 245 title:"确认启动",
246 246 content:"是否启动选中任务?",
247 247 onOk: function(){
248   - getAction(that.url.resume,{jobClassName:record.jobClassName}).then((res)=>{
  248 + getAction(that.url.resume,{id:record.id}).then((res)=>{
249 249 if(res.success){
250 250 that.$message.success(res.message);
251 251 that.loadData();
... ...
ant-design-vue-jeecg/src/views/system/SysAnnouncementList.vue
... ... @@ -102,6 +102,11 @@
102 102  
103 103 <!-- 表单区域 -->
104 104 <sysAnnouncement-modal ref="modalForm" @ok="modalFormOk"></sysAnnouncement-modal>
  105 + <!-- 查看详情 -->
  106 + <j-modal class="detail-modal" title="查看详情" :visible.sync="detailModal.visible" :top="50" :width="600" switchFullscreen :footer="null">
  107 + <iframe v-if="detailModal.url" class="detail-iframe" :src="detailModal.url"/>
  108 + </j-modal>
  109 +
105 110 </a-card>
106 111 </template>
107 112  
... ... @@ -110,6 +115,7 @@
110 115 import {doReleaseData, doReovkeData} from '@/api/api'
111 116 import {getAction} from '@/api/manage'
112 117 import {JeecgListMixin} from '@/mixins/JeecgListMixin'
  118 + import { ACCESS_TOKEN } from '@/store/mutation-types'
113 119  
114 120 export default {
115 121 name: "SysAnnouncementList",
... ... @@ -237,6 +243,7 @@
237 243 scopedSlots: {customRender: 'action'},
238 244 }
239 245 ],
  246 + detailModal: {visible: false, url: '',},
240 247 url: {
241 248 list: "/sys/annountCement/list",
242 249 delete: "/sys/annountCement/delete",
... ... @@ -284,14 +291,42 @@
284 291 getAction("sys/annountCement/syncNotic",{anntId:anntId})
285 292 },
286 293 handleDetail:function(record){
287   - this.$refs.modalForm.edit(record);
288   - this.$refs.modalForm.title="详情";
289   - this.$refs.modalForm.disableSubmit = true;
290   - this.$refs.modalForm.disabled = true;
  294 + const domain = window._CONFIG['domianURL']
  295 + const token = this.$ls.get(ACCESS_TOKEN)
  296 + this.detailModal.url = `${domain}/sys/annountCement/show/${record.id}?token=${token}`
  297 + this.detailModal.visible = true
291 298 },
292 299 }
293 300 }
294 301 </script>
295   -<style scoped>
296   - @import '~@assets/less/common.less'
  302 +<style scoped lang="less">
  303 + @import '~@assets/less/common.less';
  304 +
  305 + /** 查看详情弹窗的样式 */
  306 + .detail-modal {
  307 + .detail-iframe {
  308 + border: 0;
  309 + width: 100%;
  310 + height: 88vh;
  311 + min-height: 600px;
  312 + }
  313 +
  314 + &.fullscreen .detail-iframe {
  315 + height: 100%;
  316 + }
  317 + }
  318 +
  319 + .detail-modal /deep/ .ant-modal {
  320 + top: 30px;
  321 +
  322 + .ant-modal-body {
  323 + font-size: 0;
  324 + padding: 0;
  325 + }
  326 + }
  327 +
  328 + .detail-modal.fullscreen /deep/ .ant-modal {
  329 + top: 0;
  330 + }
  331 +
297 332 </style>
298 333 \ No newline at end of file
... ...
ant-design-vue-jeecg/src/views/system/SysCheckRuleList.vue
... ... @@ -3,18 +3,18 @@
3 3  
4 4 <!-- 查询区域 -->
5 5 <div class="table-page-search-wrapper">
6   - <a-form layout="inline" @keyup.enter.native="searchQuery">
  6 + <a-form-model layout="inline" :model="queryParam" @keyup.enter.native="searchQuery">
7 7 <a-row :gutter="24">
8 8  
9 9 <a-col :md="6" :sm="8">
10   - <a-form-item label="规则名称">
  10 + <a-form-model-item label="规则名称" prop="ruleName">
11 11 <a-input placeholder="请输入规则名称" v-model="queryParam.ruleName"/>
12   - </a-form-item>
  12 + </a-form-model-item>
13 13 </a-col>
14 14 <a-col :md="6" :sm="8">
15   - <a-form-item label="规则Code">
  15 + <a-form-model-item label="规则Code" prop="ruleCode">
16 16 <a-input placeholder="请输入规则Code" v-model="queryParam.ruleCode"/>
17   - </a-form-item>
  17 + </a-form-model-item>
18 18 </a-col>
19 19 <template v-if="toggleSearchStatus">
20 20 </template>
... ... @@ -30,7 +30,7 @@
30 30 </a-col>
31 31  
32 32 </a-row>
33   - </a-form>
  33 + </a-form-model>
34 34 </div>
35 35  
36 36 <!-- 操作按钮区域 -->
... ...
ant-design-vue-jeecg/src/views/system/SysFillRuleList.vue
... ... @@ -3,17 +3,17 @@
3 3  
4 4 <!-- 查询区域 -->
5 5 <div class="table-page-search-wrapper">
6   - <a-form layout="inline" @keyup.enter.native="searchQuery">
  6 + <a-form-model layout="inline" :model="queryParam" @keyup.enter.native="searchQuery">
7 7 <a-row :gutter="24">
8 8 <a-col :md="6" :sm="8">
9   - <a-form-item label="规则名称">
  9 + <a-form-model-item label="规则名称" prop="ruleName">
10 10 <a-input placeholder="请输入规则名称" v-model="queryParam.ruleName"></a-input>
11   - </a-form-item>
  11 + </a-form-model-item>
12 12 </a-col>
13 13 <a-col :md="6" :sm="8">
14   - <a-form-item label="规则Code">
  14 + <a-form-model-item label="规则Code" prop="ruleCode">
15 15 <a-input placeholder="请输入规则Code" v-model="queryParam.ruleCode"></a-input>
16   - </a-form-item>
  16 + </a-form-model-item>
17 17 </a-col>
18 18 <a-col :md="6" :sm="8">
19 19 <span style="float: left;overflow: hidden;" class="table-page-search-submitButtons">
... ... @@ -22,7 +22,7 @@
22 22 </span>
23 23 </a-col>
24 24 </a-row>
25   - </a-form>
  25 + </a-form-model>
26 26 </div>
27 27  
28 28 <!-- 操作按钮区域 -->
... ...
ant-design-vue-jeecg/src/views/system/UserList.vue
... ... @@ -65,11 +65,12 @@
65 65  
66 66 <!-- 操作按钮区域 -->
67 67 <div class="table-operator" style="border-top: 5px">
68   - <a-button @click="handleAdd" type="primary" icon="plus">添加用户</a-button>
  68 + <a-button @click="handleAdd" type="primary" icon="plus" >添加用户</a-button>
69 69 <a-button type="primary" icon="download" @click="handleExportXls('用户信息')">导出</a-button>
70 70 <a-upload name="file" :showUploadList="false" :multiple="false" :headers="tokenHeader" :action="importExcelUrl" @change="handleImportExcel">
71 71 <a-button type="primary" icon="import">导入</a-button>
72 72 </a-upload>
  73 + <j-third-app-button biz-type="user" :selected-row-keys="selectedRowKeys" syncToApp syncToLocal @sync-finally="onSyncFinally"/>
73 74 <a-button type="primary" icon="hdd" @click="recycleBinVisible=true">回收站</a-button>
74 75 <a-dropdown v-if="selectedRowKeys.length > 0">
75 76 <a-menu slot="overlay" @click="handleMenuClick">
... ... @@ -120,9 +121,9 @@
120 121 </template>
121 122  
122 123 <span slot="action" slot-scope="text, record">
123   - <a @click="handleEdit(record)">编辑</a>
  124 + <a @click="handleEdit(record)" >编辑</a>
124 125  
125   - <a-divider type="vertical"/>
  126 + <a-divider type="vertical" />
126 127  
127 128 <a-dropdown>
128 129 <a class="ant-dropdown-link">
... ... @@ -154,6 +155,11 @@
154 155 <a>解冻</a>
155 156 </a-popconfirm>
156 157 </a-menu-item>
  158 +
  159 + <a-menu-item>
  160 + <a href="javascript:;" @click="handleAgentSettings(record.username)">代理人</a>
  161 + </a-menu-item>
  162 +
157 163 </a-menu>
158 164 </a-dropdown>
159 165 </span>
... ... @@ -167,6 +173,8 @@
167 173  
168 174 <password-modal ref="passwordmodal" @ok="passwordModalOk"></password-modal>
169 175  
  176 + <sys-user-agent-modal ref="sysUserAgentModal"></sys-user-agent-modal>
  177 +
170 178 <!-- 用户回收站 -->
171 179 <user-recycle-bin-modal :visible.sync="recycleBinVisible" @ok="modalFormOk"/>
172 180  
... ... @@ -179,14 +187,18 @@
179 187 import {putAction,getFileAccessHttpUrl} from '@/api/manage';
180 188 import {frozenBatch} from '@/api/api'
181 189 import {JeecgListMixin} from '@/mixins/JeecgListMixin'
  190 + import SysUserAgentModal from "./modules/SysUserAgentModal";
182 191 import JInput from '@/components/jeecg/JInput'
183 192 import UserRecycleBinModal from './modules/UserRecycleBinModal'
184 193 import JSuperQuery from '@/components/jeecg/JSuperQuery'
  194 + import JThirdAppButton from '@/components/jeecgbiz/thirdApp/JThirdAppButton'
185 195  
186 196 export default {
187 197 name: "UserList",
188 198 mixins: [JeecgListMixin],
189 199 components: {
  200 + JThirdAppButton,
  201 + SysUserAgentModal,
190 202 UserModal,
191 203 PasswordModal,
192 204 JInput,
... ... @@ -366,9 +378,19 @@
366 378 handleChangePassword(username) {
367 379 this.$refs.passwordmodal.show(username);
368 380 },
  381 + handleAgentSettings(username){
  382 + this.$refs.sysUserAgentModal.agentSettings(username);
  383 + this.$refs.sysUserAgentModal.title = "用户代理人设置";
  384 + },
369 385 passwordModalOk() {
370 386 //TODO 密码修改完成 不需要刷新页面,可以把datasource中的数据更新一下
371   - }
  387 + },
  388 + onSyncFinally({isToLocal}) {
  389 + // 同步到本地时刷新下数据
  390 + if (isToLocal) {
  391 + this.loadData()
  392 + }
  393 + },
372 394 }
373 395  
374 396 }
... ...
ant-design-vue-jeecg/src/views/system/modules/AddressListRight.vue
1 1 <template>
2 2 <a-card class="j-address-list-right-card-box" :loading="cardLoading" :bordered="false">
3 3 <div class="table-page-search-wrapper">
4   - <a-form layout="inline">
  4 + <a-form-model layout="inline" :model="queryParam">
5 5 <a-row :gutter="10">
6 6  
7 7 <a-col :md="6" :sm="12">
8   - <a-form-item label="姓名" style="margin-left:8px">
  8 + <a-form-model-item label="姓名" prop="realname" style="margin-left:8px">
9 9 <a-input placeholder="请输入姓名查询" v-model="queryParam.realname"></a-input>
10   - </a-form-item>
  10 + </a-form-model-item>
11 11 </a-col>
12 12  
13 13  
14 14 <a-col :md="6" :sm="12">
15   - <a-form-item label="工号" style="margin-left:8px">
  15 + <a-form-model-item label="工号" prop="workNo" style="margin-left:8px">
16 16 <a-input placeholder="请输入工号查询" v-model="queryParam.workNo"></a-input>
17   - </a-form-item>
  17 + </a-form-model-item>
18 18 </a-col>
19 19  
20 20 <span style="float: left;overflow: hidden;" class="table-page-search-submitButtons">
... ... @@ -24,7 +24,7 @@
24 24 </a-col>
25 25 </span>
26 26 </a-row>
27   - </a-form>
  27 + </a-form-model>
28 28 </div>
29 29  
30 30 <a-table
... ...