kn-cli 1.0.106 → 1.0.108

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (70) hide show
  1. package/build/webpack.config.js +2 -1
  2. package/package.json +1 -1
  3. package/templates/template_admin/cli.config.js +1 -0
  4. package/templates/template_admin/package.json +1 -1
  5. package/templates/template_admin/public/src/_mixin.less +38 -0
  6. package/templates/template_admin/public/src/_reset.less +0 -7
  7. package/templates/template_admin/public/src/assets/images/permission/403.png +0 -0
  8. package/templates/template_admin/public/src/assets/images/permission/404.png +0 -0
  9. package/templates/template_admin/public/src/assets/images/permission/503.png +0 -0
  10. package/templates/template_admin/public/src/components/antd/index.jsx +145 -0
  11. package/templates/template_admin/public/src/components/antd/tooltip/detail/index.jsx +70 -0
  12. package/templates/template_admin/public/src/components/antd/tooltip/detail/index.less +12 -0
  13. package/templates/template_admin/public/src/components/antd/tooltip/index.jsx +69 -0
  14. package/templates/template_admin/public/src/components/antd/tooltip/index.less +28 -0
  15. package/templates/template_admin/public/src/components/auth/index.jsx +60 -3
  16. package/templates/template_admin/public/src/components/auth/navCheck.jsx +27 -0
  17. package/templates/template_admin/public/src/components/button/index.jsx +17 -0
  18. package/templates/template_admin/public/src/components/debug/index.jsx +1 -1
  19. package/templates/template_admin/public/src/components/error/index.jsx +39 -0
  20. package/templates/template_admin/public/src/components/image/index.jsx +1 -1
  21. package/templates/template_admin/public/src/components/image/preview.jsx +1 -1
  22. package/templates/template_admin/public/src/components/layout/provider/index.jsx +2 -2
  23. package/templates/template_admin/public/src/components/leftMenu/index.jsx +31 -6
  24. package/templates/template_admin/public/src/components/menuIcon/index.jsx +33 -0
  25. package/templates/template_admin/public/src/components/menuIcon/index.less +49 -0
  26. package/templates/template_admin/public/src/components/react/index.jsx +7 -0
  27. package/templates/template_admin/public/src/components/select/defaultServicesSelect/index.jsx +182 -0
  28. package/templates/template_admin/public/src/components/select/dictSelect/index.jsx +84 -0
  29. package/templates/template_admin/public/src/components/select/index.jsx +7 -0
  30. package/templates/template_admin/public/src/components/select/useSelectList.jsx +217 -0
  31. package/templates/template_admin/public/src/components/table/index.jsx +1 -1
  32. package/templates/template_admin/public/src/components/text/index.jsx +1 -1
  33. package/templates/template_admin/public/src/components/topMenu/index.jsx +6 -1
  34. package/templates/template_admin/public/src/components/topMenu/index.less +10 -1
  35. package/templates/template_admin/public/src/components/topMenu/topBar/index.jsx +6 -1
  36. package/templates/template_admin/public/src/components/topMenu/topBar/index.less +9 -0
  37. package/templates/template_admin/public/src/config.js +28 -0
  38. package/templates/template_admin/public/src/declarations.d.ts +1 -0
  39. package/templates/template_admin/public/src/dictionary/dictionary.js +289 -0
  40. package/templates/template_admin/public/src/dictionary/index.js +22 -126
  41. package/templates/template_admin/public/src/hooks/useRouteMenu.jsx +25 -3
  42. package/templates/template_admin/public/src/hooks/useThrottole.jsx +68 -0
  43. package/templates/template_admin/public/src/index.jsx +33 -15
  44. package/templates/template_admin/public/src/menuConfig.jsx +152 -0
  45. package/templates/template_admin/public/src/pages/auth/user/create/index.jsx +1 -9
  46. package/templates/template_admin/public/src/pages/auth/user/dialog/index.jsx +1 -1
  47. package/templates/template_admin/public/src/pages/auth/user/index.jsx +3 -60
  48. package/templates/template_admin/public/src/pages/components/select/user.jsx +18 -0
  49. package/templates/template_admin/public/src/pages/demo/page1.jsx +21 -0
  50. package/templates/template_admin/public/src/pages/demo/page2.jsx +21 -0
  51. package/templates/template_admin/public/src/pages/demo/page3.jsx +21 -0
  52. package/templates/template_admin/public/src/pages/error/403.jsx +15 -0
  53. package/templates/template_admin/public/src/pages/error/404.jsx +15 -0
  54. package/templates/template_admin/public/src/pages/error/503.jsx +15 -0
  55. package/templates/template_admin/public/src/pages/error/permission.jsx +40 -0
  56. package/templates/template_admin/public/src/pages/error/permission.less +16 -0
  57. package/templates/template_admin/public/src/pages/home.jsx +15 -4
  58. package/templates/template_admin/public/src/pages/login/index.jsx +3 -2
  59. package/templates/template_admin/public/src/pages/pageTemplate.jsx +28 -0
  60. package/templates/template_admin/public/src/provider/app.jsx +86 -55
  61. package/templates/template_admin/public/src/provider/menu.jsx +75 -108
  62. package/templates/template_admin/public/src/route.jsx +55 -35
  63. package/templates/template_admin/public/src/services/index.js +28 -4
  64. package/templates/template_admin/public/src/services/socket/index.jsx +1 -1
  65. package/templates/template_admin/public/src/utils/storage.js +30 -0
  66. package/templates/template_admin/webpack.api.js +24 -0
  67. package/templates/template_admin/public/src/pages/components/select/account/index.jsx +0 -114
  68. package/templates/template_admin/public/src/pages/components/select/device/index.jsx +0 -83
  69. package/templates/template_admin/public/src/pages/components/select/groupUser/index.jsx +0 -172
  70. package/templates/template_admin/public/src/pages/components/select/user/index.jsx +0 -119
@@ -4,10 +4,8 @@ import React, { useEffect, useState } from 'react';
4
4
  import {useNavigate,} from 'react-router-dom';
5
5
 
6
6
  // @ts-ignore
7
- import { Menu } from 'antd';
7
+ import { Menu } from '@/components/antd';
8
8
  import Badge from '@/components/badge'
9
- // @ts-ignore
10
- import { AppstoreOutlined, MailOutlined, SettingOutlined } from '@ant-design/icons';
11
9
 
12
10
  import {useLoading} from '@/hooks/index';
13
11
  import ProviderMenu from '@/provider/menu';
@@ -30,6 +28,8 @@ const LeftMenu=(props)=>{
30
28
  const loader = useLoading();
31
29
  const [menus,setMenus] = useState([]);
32
30
  const nav = useNavigate();
31
+ const [openKeys,setOpenKeys] = useState([])
32
+
33
33
 
34
34
  const translateMenu=(list)=>{
35
35
  if(!list||list.length<=0)return [];
@@ -37,7 +37,10 @@ const LeftMenu=(props)=>{
37
37
  const {key,name:label,icon,url,msgCount}=menu;
38
38
 
39
39
  let item={
40
- key,label,icon,url
40
+ key,
41
+ label: menu.children?.length > 0 ? label: <a href={'/#'+url}>{label}</a>,
42
+ icon,
43
+ url
41
44
  }
42
45
  if(msgCount&&msgCount>0){
43
46
  item.label=<span className={styles.menuLabel}>{label}
@@ -52,24 +55,46 @@ const LeftMenu=(props)=>{
52
55
  return req;
53
56
  }
54
57
 
58
+ const onOpenChange=(keys)=>{
59
+ setOpenKeys(keys);
60
+ }
61
+
55
62
  useEffect(()=>{
56
63
  let menuList = translateMenu(providerMenu.leftMenu);
57
64
  setMenus(menuList);
58
65
  },[providerMenu.leftMenu])
59
66
 
67
+ useEffect(()=>{
68
+ if(openKeys.length != providerMenu.selectMenus.keys.length){
69
+ setOpenKeys(providerMenu.selectMenus.keys)
70
+ }else{
71
+ let notSome= openKeys.some(key=>{
72
+ if( providerMenu.selectMenus.keys.includes(key) ){
73
+ return false;
74
+ }else{
75
+ return true;
76
+ }
77
+ })
78
+ if(notSome){
79
+ setOpenKeys(providerMenu.selectMenus.keys)
80
+ }
81
+ }
82
+ },[providerMenu.selectMenus.keys])
83
+
60
84
 
61
85
  const onClickMenuItem=(e)=>{
62
86
  const { item, key, keyPath, domEvent } = e;
63
87
  let menu = providerMenu.findMenuData(key);
64
88
  nav(menu.url);
65
89
  }
90
+ if(!menus||menus.length<=0)return <></>;
66
91
 
67
92
  return (
68
93
  <section className={styles.nav} data-nav-hide={!menus||menus.length<=0}>
69
94
  <Menu
70
95
  selectedKeys={providerMenu.selectMenus.keys}
71
- // openKeys={openKeys}
72
- // onOpenChange={onOpenChange}
96
+ openKeys={openKeys}
97
+ onOpenChange={onOpenChange}
73
98
  onClick={onClickMenuItem}
74
99
  mode="inline"
75
100
  items={loader.loading?[]:menus}
@@ -0,0 +1,33 @@
1
+
2
+ import React,{ useState, useEffect } from 'react';
3
+ // @ts-ignore
4
+ import styles from './index.less';
5
+
6
+ const MenuIcon=(props)=>{
7
+
8
+ const [icon,setIcon]= useState('');
9
+ const [iconActive,setIconActive]= useState('');
10
+
11
+ const getIcon= async (iconName)=>{
12
+ const req = await new Promise(resolve=>{
13
+ let iconActive =import(`@/assets/images/nav/${iconName}-active.png`);
14
+ let icon = import(`@/assets/images/nav/${iconName}.png`);
15
+ Promise.all([icon,iconActive]).then(values=>{
16
+ setIcon(values[0].default);
17
+ setIconActive(values[1].default)
18
+ })
19
+ })
20
+ }
21
+ useEffect(()=>{
22
+ getIcon(props.name);
23
+ },[])
24
+
25
+ return (
26
+ <div className={styles.iconGroup}>
27
+ <img className={styles.icon} src={icon} />
28
+ <img className={styles.iconActive} src={iconActive} />
29
+ </div>
30
+ )
31
+
32
+ }
33
+ export default MenuIcon;
@@ -0,0 +1,49 @@
1
+
2
+
3
+
4
+ .iconGroup{
5
+ width: 17px;
6
+ height: 100%;
7
+ margin-right: 12px;
8
+ display: inline-flex;
9
+ align-items: center;
10
+ margin-left:-12px;
11
+
12
+ img{width: 100%;}
13
+ .icon{
14
+ display: inline-block;
15
+ }
16
+ .iconActive{
17
+ display: none;
18
+ }
19
+ }
20
+
21
+ :global(.ant-menu-title-content){
22
+ font-size: 14px;
23
+ }
24
+
25
+ :global(.ant-menu-submenu-selected),
26
+ :global(.ant-menu-item-selected),
27
+ :global(.ant-menu-submenu-active),
28
+ :global(.ant-menu-item-active){
29
+ .iconGroup .iconActive{
30
+ display: inline-block;
31
+ }
32
+ .iconGroup .icon{
33
+ display: none;
34
+ }
35
+ :global(.ant-menu-submenu-title .ant-menu-title-content),
36
+ :global(.ant-menu-item-selected .ant-menu-title-content){
37
+ font-weight: bold;
38
+ a{
39
+ font-weight: inherit;
40
+ color: #0974F2;
41
+ }
42
+ }
43
+ :global(.ant-menu-submenu-arrow) {
44
+ color: #0974F2
45
+ }
46
+ }
47
+ :global(.ant-menu-inline.ant-menu-root .ant-menu-item > .ant-menu-title-content){
48
+ margin-left: -8px;
49
+ }
@@ -0,0 +1,7 @@
1
+ import ReactDom from 'react-dom';
2
+
3
+ export const ReactRender=(component,targetDom)=>{
4
+ ReactDom.render(component,targetDom);
5
+ }
6
+
7
+ export default {ReactRender}
@@ -0,0 +1,182 @@
1
+
2
+ import React, { useEffect, useRef, forwardRef, useImperativeHandle, useState } from 'react';
3
+ // @ts-ignore
4
+ import { Select } from "@/components/antd";
5
+ import useSelectList from '../useSelectList';
6
+
7
+ /**
8
+ * @typedef SelectItemOption
9
+ * @property {string} label - 显示的名称
10
+ * @property {string} value - 唯一值
11
+ * @property {object} [data] - 原始数据
12
+ *
13
+ */
14
+
15
+ /**
16
+ * @typedef DefaultServicesSelectProps
17
+ * @property {string} [name] - 调试用的名称
18
+ * @property {object} services - api接口 符合输出的结果为{id:'',name:''}结构
19
+ * @property {object} [servicesProps={}] - 接口传参
20
+ * @property {(item:object)=>SelectItemOption} [formatOptionItem] - 用户格式化接口返回的数据成标准option数据
21
+ * @property {(list:object[]|object)=>SelectItemOption[]} [formatOptionList] - 对整个response处理返回option
22
+ */
23
+
24
+ /**
25
+ * 从字典生成下拉框
26
+ * @param {import('../useSelectList').SelectListProps & DefaultServicesSelectProps} props
27
+ * @returns {JSX.Element}
28
+ */
29
+ const DefaultServicesSelect=(props,ref)=>{
30
+ const {
31
+ mode='single',
32
+ value:_value,
33
+ style:_style={},
34
+ placeholder='请选择',
35
+ onChange,
36
+ canChange,
37
+ disabled=false,
38
+ services,
39
+ servicesProps={},
40
+ formatOptionItem=(item)=>{
41
+ const {id,name} = item;
42
+ return {
43
+ label:`${name}`,
44
+ value:`${id}`,
45
+ data:item
46
+ }
47
+ },
48
+ formatOptionList,
49
+ onDefaultSelect,
50
+ onListUpdate,
51
+ name,
52
+ required=false
53
+ } = props;
54
+
55
+ // 单选框默认带一键删除
56
+ const allowClear = props.allowClear??((required==false)?true:false);
57
+
58
+ const refDestory = useRef(false);
59
+ const selectList = useSelectList(props);
60
+ const [requestParams,setRequestParams] = useState(servicesProps)
61
+ const refInitList=useRef([]);
62
+
63
+ // 初始化加载下拉框数据
64
+ const init = async ()=>{
65
+ const req = await services(servicesProps);
66
+ if(refDestory.current){return;}
67
+ let values=[];
68
+ if(req?.code==0){
69
+ let data=[];
70
+ if(formatOptionList){
71
+ data = formatOptionList(req.data);
72
+ }else{
73
+ data= req.data.map(item=>{
74
+ return formatOptionItem(item)
75
+ })
76
+ }
77
+ values=data;
78
+ }
79
+ if(onListUpdate){
80
+ onListUpdate(values);
81
+ }
82
+ if(onDefaultSelect){
83
+ let defaultItem = onDefaultSelect(values);
84
+ if(defaultItem){
85
+ onValueChange(defaultItem.value,defaultItem,true)
86
+ }
87
+ }
88
+ const t= await selectList.init(values);
89
+ if(refDestory.current){return;}
90
+ refInitList.current.shift();
91
+ if( refInitList.current.length >0 ){
92
+ let fn = refInitList.current[0]
93
+ fn();
94
+ }
95
+ return t;
96
+ }
97
+ const onFilter=(input,option)=>{
98
+ const {label,value}= option;
99
+ if( `${label}`.toLocaleLowerCase().indexOf(input.toLocaleLowerCase()) >=0 ){
100
+ return true;
101
+ }
102
+ return false;
103
+ }
104
+
105
+ const onValueChange= async (newValue,options,force=false)=>{
106
+ if(!force && canChange){
107
+ let req = await canChange(newValue,options);
108
+ if(!req)return;
109
+ }
110
+ if(onChange)onChange(newValue,options);
111
+ }
112
+
113
+
114
+ useEffect(()=>{
115
+ if(refInitList.current.length<=0){
116
+ refInitList.current.push(init)
117
+ init();
118
+ }else{
119
+ refInitList.current.push(init);
120
+ }
121
+ },[requestParams,services]);
122
+
123
+ useEffect(()=>{
124
+ let keys = Object.keys(servicesProps)
125
+ if(keys.length<=0)return;
126
+ let changes = keys.some(key=>{
127
+ if(servicesProps[key] != requestParams[key]){
128
+ return true;
129
+ }
130
+ return false;
131
+ })
132
+ if(changes){
133
+ setRequestParams(servicesProps)
134
+ }
135
+
136
+ },[servicesProps])
137
+ useEffect(()=>{
138
+ return ()=>{
139
+ refDestory.current=true
140
+ }
141
+ },[])
142
+
143
+
144
+ useImperativeHandle(ref, () => ({
145
+ getSelectList:()=>{
146
+ return selectList;
147
+ },
148
+ }));
149
+
150
+ let className=''
151
+ if(selectList.props.className){
152
+ className = selectList.props.className;
153
+ }
154
+ if(selectList.props.maxTagCount){
155
+ if(Array.isArray(className)){
156
+ className.push('antd-show-tag')
157
+ }else{
158
+ className+= ' antd-show-tag';
159
+ }
160
+ }
161
+ return (
162
+ <Select
163
+ // getPopupContainer={trigger => trigger?.parentElement||document.body}
164
+ loading={selectList.list===null}
165
+ disabled={selectList.list===null || disabled}
166
+ style={{..._style}}
167
+ placeholder={placeholder}
168
+ allowClear={allowClear}
169
+ // @ts-ignore
170
+ mode={mode}
171
+ showSearch
172
+ value={selectList.value}
173
+ options={selectList.list}
174
+ onChange={onValueChange}
175
+ filterOption={onFilter}
176
+ {...selectList.props}
177
+ className={className}
178
+ />
179
+ );
180
+ }
181
+
182
+ export default forwardRef(DefaultServicesSelect);
@@ -0,0 +1,84 @@
1
+
2
+ import React, { useEffect, useRef } from 'react';
3
+ // @ts-ignore
4
+ import { Select } from "@/components/antd";
5
+ import useSelectList from '../useSelectList';
6
+
7
+ /**
8
+ * @typedef DictSelectProps
9
+ * @property {object} emDict - 字典对象
10
+ */
11
+
12
+ /**
13
+ * 从字典生成下拉框
14
+ * @param {import('../useSelectList').SelectListProps & DictSelectProps} props
15
+ * @returns {JSX.Element}
16
+ */
17
+ const DictSelect=(props)=>{
18
+ const {
19
+ mode='single',
20
+ value:_value,
21
+ style:_style={},
22
+ placeholder='请选择',
23
+ onChange,
24
+ disabled=false,
25
+ emDict,
26
+ required=false,
27
+ } = props;
28
+
29
+ const allowClear = props.allowClear??((mode=='single'&&required==false)?true:false);
30
+
31
+ const refDestory = useRef(false);
32
+ const selectList = useSelectList(props);
33
+
34
+ // 初始化加载下拉框数据
35
+ const init = async ()=>{
36
+ if(refDestory.current)return;
37
+ let values=[];
38
+ const data = emDict.list.map(item=>{
39
+ return {
40
+ label:item.label,
41
+ value:`${item.id}`,
42
+ data:item
43
+ }
44
+ })
45
+ values=data;
46
+ return await selectList.init(values);
47
+ }
48
+ const onFilter=(input,option)=>{
49
+ const {label,value}= option;
50
+ if( `${label}`.indexOf(input) >=0 ){
51
+ return true;
52
+ }
53
+ return false;
54
+ }
55
+ const onValueChange=(newValue,options)=>{
56
+ if(onChange)onChange(newValue,options);
57
+ }
58
+
59
+ useEffect(()=>{
60
+ init();
61
+ return ()=>{refDestory.current=true}
62
+ },[])
63
+
64
+
65
+ return (
66
+ <Select
67
+ loading={selectList.list===null}
68
+ disabled={selectList.list===null || disabled}
69
+ style={{..._style}}
70
+ placeholder={placeholder}
71
+ allowClear={allowClear?true:false}
72
+ // @ts-ignore
73
+ mode={mode}
74
+ showSearch
75
+ value={selectList.value}
76
+ options={selectList.list}
77
+ onChange={onValueChange}
78
+ filterOption={onFilter}
79
+ {...selectList.props}
80
+ />
81
+ );
82
+ }
83
+
84
+ export default DictSelect;
@@ -0,0 +1,7 @@
1
+ import DictSelect from './dictSelect';
2
+ import DefaultServicesSelect from './defaultServicesSelect';
3
+
4
+ export {DictSelect};
5
+ export {DefaultServicesSelect};
6
+
7
+ export default {DictSelect,DefaultServicesSelect};
@@ -0,0 +1,217 @@
1
+ import React, { useEffect, useState } from 'react';
2
+ // @ts-ignore
3
+ import {Tooltip} from "@/components/antd";
4
+
5
+
6
+
7
+ /**
8
+ * 各类选择框组件
9
+ * @typedef SelectListProps
10
+ * @property {string} [name] - 调试名称
11
+ * @property {'single'|'multiple'} [mode='single'] - 单选/多选模式
12
+ * @property {(value:string|string[],items:object|object[])=>void} [onChange] - 选择发生变化时的回调
13
+ * @property {string|string[]} [value] - 选择发生变化时的回调
14
+ * @property {object} [style={}] - 样式
15
+ * @property {string} [placeholder] - 提示
16
+ * @property {boolean} [allowClear=false] - 一键删除按钮
17
+ * @property {boolean} [showAll=false] - 是否第一个展示全部选项
18
+ * @property {string} [allValue=''] - 定义全部选项的值是哪种类型,''代表空字符串
19
+ * @property {(id:string)=>SelectItem} [onNoMatchData] - 当没有匹配到数据时的回调
20
+ * @property {{id:number|string,label:string}[]} [noMatchList] - 为匹配到数据时的备用匹配数据
21
+ * @property {string} [onNoMatchDataLabel] - 当单选时,默认选中的数据没有匹配到合法数据时展示的label
22
+ * @property {object} [params={}] - 扩展参数
23
+ * @property {boolean} [disabled=false] - 是否禁止编辑
24
+ * @property {boolean} [noCheckNotFound=false] 是否禁止做不匹配数据的检查补全
25
+ * @property {string} [className='']
26
+ * @property {number} [maxTagCount] - 多选时最多支持的标签数量
27
+ * @property {JSX.Element|string} [suffixIcon] 选择框尾部的icon
28
+ * @property {(value:string|string[],items:object|object[])=>Promise<boolean>} [canChange] - 用于在切换选项时拦截决定是否允许变更
29
+ * @property {boolean} [required=false] - 是否为必选,必选的话不允许allowClear
30
+ * @property {(list:SelectItem[])=>object} [onDefaultSelect] - 初始化后如果需要有默认选中项的计算的话,可以通过这里拦截
31
+ * @property {(list:SelectItem[])=>void} [onListUpdate] - 每当列表内的数据更新时回调
32
+ *
33
+ */
34
+
35
+ /**
36
+ * @typedef SelectItem
37
+ * @property {string} label - 文本下拉框里展示的文本
38
+ * @property {string} value - 文本下拉框里选项的值
39
+ * @property {any} data - 文本下拉框里选项对应的原始数据
40
+ *
41
+ */
42
+
43
+ /**
44
+ * @typedef UseSelectList
45
+ * @property {(list:SelectItem[])=>Promise<boolean>} init - 初始化函数
46
+ * @property {string|number|string[]|number[]} value - 值发生变化时的回调
47
+ * @property {SelectItem[]} list - 选择的数据列表
48
+ * @property {(value)=>void} setValue - 设置当前值
49
+ * @property {object} props - 继承给Select组件的通用属性
50
+ * @property {(value:string|string[])=>object[]} getItemByValue - 通过ID获取到所有匹配的对象数据
51
+ *
52
+ */
53
+
54
+ /**
55
+ * 通用的管理选择下拉框数据的hooks
56
+ * @param {SelectListProps} props
57
+ * @returns {UseSelectList}
58
+ */
59
+ const useSelectList=(props)=>{
60
+ const {
61
+ mode='single',
62
+ value:_value,
63
+ style:_style={},
64
+ showAll=false,
65
+ allValue='',
66
+ onNoMatchData,
67
+ onNoMatchDataLabel,
68
+ noCheckNotFound=false,
69
+ noMatchList=[],
70
+ } = props;
71
+
72
+ const [list,setList]= useState(null);
73
+ const [value,setValue]=useState(mode=='single'?'':[]);
74
+ const [maxTagCount] = useState(()=>{
75
+ if(mode=='multiple'){
76
+ if(props.maxTagCount == 0){
77
+ return undefined;
78
+ }
79
+ if(props.maxTagCount){
80
+ return props.maxTagCount;
81
+ }
82
+ return 'responsive';
83
+ }
84
+ return undefined;
85
+ })
86
+
87
+ const [suffixIcon] = useState(props.suffixIcon||undefined)
88
+
89
+ /**
90
+ * 初始化加载下拉框数据
91
+ * @param {{label:string,value:string,data:any}[]} values
92
+ */
93
+ const init = async (values)=>{
94
+ if(showAll && values?.length>0){
95
+ let value =allValue;
96
+ values =[{label:'全部',value,data:values},...values]
97
+ }
98
+ setList(values);
99
+ return true;
100
+ }
101
+
102
+ /**
103
+ * 通过值获取到选项对象
104
+ * @param {string|string[]} value
105
+ * @returns {object[]}
106
+ */
107
+ const getItemByValue=(value)=>{
108
+ if(!value)return [];
109
+ let finder = [];
110
+ if(Array.isArray(value)==false){
111
+ finder = [value];
112
+ }else{
113
+ finder= [...value];
114
+ }
115
+ let req=[];
116
+ list.filter(item=>{
117
+ for(let i=0;i<finder.length;i++){
118
+ if(finder[i]==item.value){
119
+ req.push(item.data);
120
+ finder.splice(i,1);
121
+ break;
122
+ }
123
+ }
124
+ })
125
+ return req;
126
+ }
127
+ /**
128
+ * 在备用数据内匹配数据
129
+ * @param {number} id
130
+ */
131
+ const matchBackupList=(id)=>{
132
+ if(!noMatchList||noMatchList.length<=0){return null}
133
+ let matchData = noMatchList.filter(data=>data.id==id);
134
+ if(matchData&&matchData[0]){
135
+ return {value:''+id,label:matchData[0].label,data:null}
136
+ }
137
+ return null;
138
+ }
139
+
140
+ // 当数据变动时,检查当前选择值是否有匹配不到的数据,并处理
141
+ const checkNoFindData=()=>{
142
+ if(noCheckNotFound)return;
143
+ if(list === null)return;
144
+ if( [undefined,null].includes(value))return;
145
+ let noFindItems=[];
146
+ if(!Array.isArray(value)){
147
+ if(value==='')return;
148
+ noFindItems = [value]
149
+ }else{
150
+ noFindItems = [...value];
151
+ }
152
+ if(noFindItems.length<=0)return;
153
+
154
+ for(let i=0;i<list.length;i++){
155
+ let id = list[i].value;
156
+ let idx = noFindItems.indexOf(id);
157
+ // 找到了则移除
158
+ if( idx >= 0 ){
159
+ noFindItems.splice(idx,1);
160
+ }
161
+ }
162
+ if(noFindItems.length<=0)return;
163
+ noFindItems.forEach(id=>{
164
+ let matchData = matchBackupList(id);
165
+ if(matchData){
166
+ list.push(matchData);
167
+ return;
168
+ }
169
+ if(onNoMatchData){
170
+ let data = onNoMatchData(id);
171
+ if(data){
172
+ list.splice(0,0,data);
173
+ return;
174
+ }
175
+ }
176
+ if(onNoMatchDataLabel){
177
+ list.splice(0,0,{value:id,label:onNoMatchDataLabel,data:null});
178
+ return;
179
+ }
180
+ list.splice(0,0,{value:id,label:`${id}[不可用]`,data:null});
181
+ })
182
+ setList([...list]);
183
+ }
184
+
185
+ useEffect(()=>{
186
+ if(_value==null||_value==undefined){
187
+ setValue(undefined);
188
+ return;
189
+ }
190
+ let req;
191
+ if(mode=='multiple' && Array.isArray(_value)){
192
+ req= _value.map(id=>`${id}`)
193
+ }else{
194
+ req = `${_value}`
195
+ }
196
+ setValue(req);
197
+ },[_value]);
198
+
199
+ useEffect(()=>{
200
+ checkNoFindData();
201
+ },[value,list,noMatchList])
202
+
203
+ return {init,value,list,setValue,getItemByValue,props:{maxTagCount,suffixIcon,
204
+ maxTagPlaceholder:(omittedValues) => (
205
+ <Tooltip
206
+ overlayStyle={{
207
+ pointerEvents: 'none',
208
+ }}
209
+ title={omittedValues.map(({ label }) => label).join(', ')}
210
+ >
211
+ <span className='antd-show-tag-more-label'><i></i><i></i><i></i></span>
212
+ </Tooltip>
213
+ )
214
+
215
+ }}
216
+ }
217
+ export default useSelectList;
@@ -1,6 +1,6 @@
1
1
  import React,{useCallback} from 'react';
2
2
  // @ts-ignore
3
- import { Table } from 'antd';
3
+ import { Table } from '@/components/antd';
4
4
  // @ts-ignore
5
5
  import styles from './index.less';
6
6
  import Column from './column';
@@ -1,6 +1,6 @@
1
1
  import React, { useEffect, useState, useRef } from 'react';
2
2
  // @ts-ignore
3
- import { Tooltip } from 'antd';
3
+ import { Tooltip } from '@/components/antd';
4
4
  import { getStrByteLen } from '@/utils';
5
5
  // @ts-ignore
6
6
  import styles from './index.less';