index.js 10 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400
  1. import PageContent from '@/components/PageContent';
  2. import TabsContent from '@/components/TabsContent';
  3. import { queryMainChartList } from '@/services/StorageManagement';
  4. import {
  5. queryDeviceList,
  6. queryMaintainRecord,
  7. queryRepairRecord,
  8. } from '@/services/device';
  9. import { UnityAction } from '@/utils/utils';
  10. import { RightOutlined } from '@ant-design/icons';
  11. import { useNavigate, useParams, useRequest } from '@umijs/max';
  12. import { Collapse, List, Space, Table } from 'antd';
  13. import dayjs from 'dayjs';
  14. import { useEffect, useMemo, useState } from 'react';
  15. import styles from './index.less';
  16. const deviceIcon = require('@/assets/deviceManager/deviceIcon.png');
  17. const spareIcon = require('@/assets/deviceManager/spareIcon.png');
  18. // const chartIcon = require('@/assets/deviceManager/chartIcon.png');
  19. const DeviceManager = () => {
  20. const { projectId } = useParams();
  21. const [defaultActiveKey, setDefaultActiveKey] = useState(
  22. localStorage.deviceTab || '1',
  23. );
  24. const onChange = (tab) => {
  25. setDefaultActiveKey(tab);
  26. };
  27. useEffect(() => {
  28. // 重置默认显示tab
  29. localStorage.deviceTab = '1';
  30. }, []);
  31. return (
  32. <PageContent tabs>
  33. <TabsContent
  34. defaultActiveKey={defaultActiveKey}
  35. onChange={onChange}
  36. items={[
  37. {
  38. label: `设备管理`,
  39. key: '1',
  40. children: <Device projectId={projectId} />,
  41. },
  42. {
  43. label: `备品管理`,
  44. key: '2',
  45. children: <SparePart projectId={projectId} />,
  46. },
  47. ]}
  48. />
  49. </PageContent>
  50. );
  51. };
  52. const Device = ({ projectId }) => {
  53. const [type, setType] = useState(0); //0 全部 1维修 2保养
  54. const [activeCode, setActiveCode] = useState();
  55. const columnsRepair = [
  56. {
  57. title: '设备位号',
  58. dataIndex: 'DeviceCode',
  59. key: 'DeviceCode',
  60. align: 'center',
  61. },
  62. {
  63. title: '设备名称',
  64. dataIndex: 'DeviceName',
  65. key: 'DeviceName',
  66. align: 'center',
  67. },
  68. {
  69. title: '维修时间',
  70. dataIndex: 'RepairTime',
  71. key: 'RepairTime',
  72. align: 'center',
  73. render: (text) => {
  74. return text ? dayjs(text).format('YYYY-MM-DD HH:mm') : null;
  75. },
  76. },
  77. {
  78. title: '维修状态',
  79. dataIndex: 'AcceptanceStatus',
  80. render: (text) => {
  81. switch (text) {
  82. case 0:
  83. return '维修中';
  84. case 1:
  85. return '已提交';
  86. case 2:
  87. return '已维修';
  88. default:
  89. return '';
  90. }
  91. },
  92. },
  93. ];
  94. const columns = [
  95. {
  96. title: '设备位号',
  97. dataIndex: 'DeviceCode',
  98. },
  99. {
  100. title: '设备名称',
  101. dataIndex: 'DeviceName',
  102. },
  103. {
  104. title: '保养日期',
  105. dataIndex: 'MaintainTime',
  106. render: (text) => {
  107. return text ? dayjs(text).format('YYYY-MM-DD HH:mm') : null;
  108. },
  109. },
  110. {
  111. title: '保养人',
  112. dataIndex: 'Operators',
  113. width: 300,
  114. render: (text) => {
  115. let arr = [];
  116. if (text && text.length > 0) {
  117. text.map((item) => {
  118. if (item && item.Operator && item.Operator.CName) {
  119. arr.push(item.Operator.CName);
  120. }
  121. });
  122. }
  123. return arr && arr.join(',');
  124. },
  125. },
  126. ];
  127. //请求 全部设备列表
  128. const {
  129. data,
  130. run: runDevice,
  131. loading: loadingDevice,
  132. } = useRequest(queryDeviceList, {
  133. defaultParams: [projectId],
  134. });
  135. const allData = useMemo(() => {
  136. const total = data?.reduce((total, item) => item.Count, 0);
  137. const items = data?.map((item, idx) => {
  138. const itemLen = item?.List?.length;
  139. return {
  140. key: `${idx + 1}`,
  141. label: (
  142. <div className={styles.lineContent}>
  143. <span>{item.Type}</span>
  144. <span>{itemLen}个</span>
  145. </div>
  146. ),
  147. children: (
  148. <div style={{ position: 'relative' }}>
  149. <List
  150. header={null}
  151. footer={null}
  152. dataSource={item.List}
  153. renderItem={(cur) => (
  154. <List.Item
  155. className={`${styles.itemText} ${
  156. activeCode == cur.Code ? styles.itemTextActive : ''
  157. }`}
  158. onClick={() => handleItemClick(cur.Code)}
  159. >
  160. <span style={{ width: '30%', textAlign: 'left' }}>
  161. {cur.Code}
  162. </span>
  163. <span> {cur.Name} </span>
  164. </List.Item>
  165. )}
  166. />
  167. </div>
  168. ),
  169. };
  170. });
  171. return { total, items };
  172. }, [data, activeCode]);
  173. //请求维修中设备列表queryRepairRecord
  174. const {
  175. data: repairData,
  176. run: runRepair,
  177. loading: repairLoading,
  178. } = useRequest(
  179. () =>
  180. queryRepairRecord({
  181. // acceptanceStatus: 0,
  182. pageSize: 9999,
  183. recordId: Number(projectId),
  184. }),
  185. {
  186. manual: true,
  187. },
  188. );
  189. //请求保养记录
  190. const {
  191. data: maintainData,
  192. run: runMaintain,
  193. loading: maintaiLoading,
  194. } = useRequest(
  195. () =>
  196. queryMaintainRecord({
  197. pageSize: 9999,
  198. recordId: Number(projectId),
  199. }),
  200. {
  201. manual: true,
  202. },
  203. );
  204. const handleItemClick = (code) => {
  205. UnityAction.sendMsg('deviceCode', code);
  206. console.log(code);
  207. setActiveCode(code);
  208. };
  209. const renderChildlen = (item) => {
  210. console.log(activeCode);
  211. return (
  212. <div style={{ position: 'relative' }}>
  213. <List
  214. header={null}
  215. footer={null}
  216. dataSource={item.List}
  217. renderItem={(cur) => (
  218. <List.Item
  219. className={`${styles.listText} ${
  220. activeCode == cur.Code ? styles.lineTextActive : ''
  221. }`}
  222. onClick={() => handleItemClick(cur.Code)}
  223. >
  224. <span style={{ marginRight: '166px' }}> {cur.Code} </span>
  225. <span> {cur.Name} </span>
  226. </List.Item>
  227. )}
  228. />
  229. </div>
  230. );
  231. };
  232. const handleBtnClick = (type) => {
  233. setType(type);
  234. switch (type) {
  235. case 0:
  236. runDevice(projectId);
  237. break;
  238. case 1:
  239. runRepair();
  240. break;
  241. case 2:
  242. runMaintain();
  243. break;
  244. }
  245. };
  246. const onChange = () => {};
  247. return (
  248. <div className={styles.sparePart}>
  249. <div className={`card-box ${styles.titleContent}`}>
  250. <img className={styles.img} src={deviceIcon} />
  251. <div>
  252. <div className={styles.num}>{allData?.total}</div>
  253. <div className={styles.text}>设备总数(个)</div>
  254. </div>
  255. </div>
  256. <Space className={styles.btns} size={28}>
  257. <div
  258. className={`${styles.btn} ${type == 0 ? styles.active : ''}`}
  259. onClick={() => handleBtnClick(0)}
  260. >
  261. 全部
  262. </div>
  263. <div
  264. className={`${styles.btn} ${type == 1 ? styles.active : ''}`}
  265. onClick={() => handleBtnClick(1)}
  266. >
  267. 维修
  268. </div>
  269. <div
  270. className={`${styles.btn} ${type == 2 ? styles.active : ''}`}
  271. onClick={() => handleBtnClick(2)}
  272. >
  273. 保养
  274. </div>
  275. </Space>
  276. {type == 0 && (
  277. <Collapse bordered={false} onChange={onChange} items={allData?.items} />
  278. )}
  279. {type == 1 && (
  280. <Table
  281. loading={repairLoading}
  282. style={{ marginTop: '10px' }}
  283. dataSource={repairData?.filter((item) => item.DeviceCode)}
  284. columns={columnsRepair}
  285. pagination={false}
  286. />
  287. )}
  288. {type == 2 && (
  289. <Table
  290. loading={maintaiLoading}
  291. style={{ marginTop: '10px' }}
  292. dataSource={maintainData?.filter((item) => item.DeviceCode)}
  293. columns={columns}
  294. pagination={false}
  295. />
  296. )}
  297. </div>
  298. );
  299. };
  300. const SparePart = ({ projectId }) => {
  301. const navigate = useNavigate();
  302. const year = dayjs().format('YYYY');
  303. const params = {
  304. project_id: Number(projectId),
  305. month: 0,
  306. year: Number(year),
  307. };
  308. //请求备品列表
  309. const { data } = useRequest(() => queryMainChartList(params));
  310. const PageType = {
  311. in: 0, //入库管理
  312. out: 1, //出库管理
  313. scrap: 2, //报废处置
  314. existing: 3, //基础库存
  315. };
  316. const changePage = (type) => {
  317. navigate(`/device/detail/${projectId}/${type}`);
  318. // 设置默认显示tab为备品管理
  319. localStorage.deviceTab = '2';
  320. };
  321. const handletotalPage = () => {
  322. navigate(`/device/storage/${projectId}`);
  323. // 设置默认显示tab为备品管理
  324. localStorage.deviceTab = '2';
  325. };
  326. const list = useMemo(() => {
  327. const result = [
  328. {
  329. title: '入库数量',
  330. type: PageType.in,
  331. num: data?.in_amount || 0,
  332. },
  333. {
  334. title: '出库数量',
  335. type: PageType.out,
  336. num: data?.out_amount || 0,
  337. },
  338. {
  339. title: '报废数量',
  340. type: PageType.scrap,
  341. num: data?.scrap_amount || 0,
  342. },
  343. {
  344. title: '报警数量',
  345. type: PageType.existing,
  346. num: data?.warning_stat || 0,
  347. },
  348. ];
  349. return result;
  350. }, [data]);
  351. return (
  352. <Space direction="vertical" size={16} className={styles.sparePart}>
  353. <div className={`card-box ${styles.titleContent}`}>
  354. <img className={styles.img} src={spareIcon} />
  355. <div>
  356. <div className={styles.num}>{data?.on_amount || 0}</div>
  357. <div className={styles.text}>在库数量(个)</div>
  358. </div>
  359. {/* <img
  360. className={styles.rightIcon}
  361. src={chartIcon}
  362. onClick={handletotalPage}
  363. /> */}
  364. <div onClick={handletotalPage} className={styles.iconFundFilled}></div>
  365. </div>
  366. {list.map((item) => (
  367. <div
  368. className={`card-box ${styles.cardItem}`}
  369. onClick={() => changePage(item.type)}
  370. >
  371. <span className={styles.spareText}>{item.title}</span>
  372. <Space size={30}>
  373. <span className={styles.spareText}>{item.num}个</span>
  374. <RightOutlined style={{ fontSize: '28px' }} />
  375. </Space>
  376. </div>
  377. ))}
  378. </Space>
  379. );
  380. };
  381. export default DeviceManager;