import ButtonConfirm from '@/components/ButtomConfirm'; import EllipsisDiv from '@/components/Div/EllipsisDiv'; import { RESPONSE_CODE } from '@/constants/enum'; import {} from '@/pages/Invoice/constant'; import { postCanrdApiUserDetail, postResearchGroupMemberRequestsDelete, postResearchGroupMemberRequestsList, postResearchGroupsDelete, postResearchGroupsList, } from '@/services'; import { formatDateTime } from '@/utils'; import { PlusOutlined } from '@ant-design/icons'; import { ActionType, ProTable } from '@ant-design/pro-components'; import { Button, Col, Divider, Image, Popconfirm, Row, Space, Spin, Table, Tabs, Tag, message, } from 'antd'; import React, { useRef, useState } from 'react'; import AuditModal from './components/AuditModal'; import ImportModal from './components/ImportModal'; import ResearchGroupAddModal from './components/ResearchGroupAddModal'; import ResearchGroupMemberRequestAddModal from './components/ResearchGroupMemberRequestAddModal'; import { RESEARCH_GROUP_COLUMNS, RESEARCH_GROUP_MEMBER_REQUEST_COLUMNS, } from './constant'; import './index.less'; const PrepaidPage = () => { const researchGroupActionRef = useRef<ActionType>(); const memberApplyActionRef = useRef<ActionType>(); const [researchGroupAddModalVisible, setResearchGroupAddModalVisible] = useState(false); const [importModalVisible, setImportModalVisible] = useState(false); const [auditIds, setAuditIds] = useState<any[]>([]); const [auditModalVisible, setAuditModalVisible] = useState(false); const [ researchGroupMemberRequestAddModalVisible, setResearchGroupMemberRequestAddModalVisible, ] = useState(false); const [auditType, setAuditType] = useState(''); // const [checkVisible, setCheckVisible] = useState(false); const [accountInfo, setAccountInfo] = useState({ realName: '', phone: '', nowMoney: '', uid: '', }); const [accountInfoLoading, setAccountInfoLoading] = useState(false); const [perms, setPerms] = useState<string[]>([]); const [optRecordId, setOptRecordId] = useState<any>(null); const reloadResearchGroupTable = () => { researchGroupActionRef.current?.reload(); }; const reloadMemberApplyTable = () => { memberApplyActionRef.current?.reload(); }; // const getTableCellText = (target: any) => { // if (!target) { // return ''; // } // if (target.props) { // return target.props.text; // } // return target; // }; const renderMembersCell = (value: any) => { if (!value) { return <span></span>; } let tags = value.map((item: any) => { let memberName = item.memberName; let memberPhone = item.memberPhone; return ( <Tag className="mt-1 mb-0" key={item.id} color="cyan" title={memberName + ' | ' + memberPhone} > {memberName} </Tag> ); }); return <div className="whitespace-normal">{tags}</div>; }; /** * 获取预存账号信息 * @param accountId */ const loadAccountInfo = async (accountId: any, phone: any) => { setAccountInfoLoading(true); let res = await postCanrdApiUserDetail({ data: { uid: accountId, phone: phone }, }); if (res && res.result === RESPONSE_CODE.SUCCESS && res.data !== null) { setAccountInfo(res.data); } else { setAccountInfo({ realName: '加载失败', phone: '加载失败', nowMoney: '加载失败', uid: '加载失败', }); } setAccountInfoLoading(false); }; const renderAccountsCell = (value: any) => { if (!value) { return <span></span>; } return ( <div className="whitespace-normal"> {value.map((item: any) => { let accountPhone = item.accountPhone; let accountName = item.accountName; let accountId = item.accountId; return ( <Popconfirm key={item.id} title="账号详情" description={ <div className="w-[170px]"> {accountInfoLoading ? ( <div> <Spin /> </div> ) : ( <div> <Row gutter={4}> <Col span={10}> <div>编号:</div> </Col> <Col span={14}> <div>{accountInfo.uid}</div> </Col> </Row> <Row gutter={4}> <Col span={10}> <div>名称:</div> </Col> <Col span={14}> <div> {accountInfo.realName === '' ? '用户' : accountInfo.realName} </div> </Col> </Row> <Row gutter={4}> <Col span={10}> <div>手机号:</div> </Col> <Col span={14}> <EllipsisDiv text={accountInfo.phone} /> </Col> </Row> <Row gutter={4}> <Col span={10}> <div>余额:</div> </Col> <Col span={14}> <div>{accountInfo.nowMoney}</div> </Col> </Row> </div> )} </div> } cancelButtonProps={{ hidden: true, }} okButtonProps={{ hidden: true, }} > <Tag className="mt-1 mb-0 hover:cursor-pointer" color="geekblue" title={accountName + ' | ' + accountPhone} onClick={() => { loadAccountInfo(accountId, accountPhone); }} > {accountName === '' ? '用户' : accountName} </Tag> </Popconfirm> ); })} </div> ); }; /** * 删除课题组信息 * @param ids */ const doDeleteResearchGroup = async (ids: any[]) => { let res = await postResearchGroupsDelete({ data: { ids: ids }, }); if (res && res.result === RESPONSE_CODE.SUCCESS) { message.success(res.message); reloadResearchGroupTable(); } }; /** * 删除课题组信息 * @param ids */ const doDeleteRequest = async (ids: any[]) => { let res = await postResearchGroupMemberRequestsDelete({ data: { ids: ids }, }); if (res && res.result === RESPONSE_CODE.SUCCESS) { message.success(res.message); reloadMemberApplyTable(); } }; /** * 加载课题组列表表格的各个列格式 */ const researchGroupColumnsInit = () => { let columns = RESEARCH_GROUP_COLUMNS.map((item) => { let newItem = { ...item }; let dataIndex = item.dataIndex; if (!newItem.render) { newItem.render = (text, record, index) => { let textValue = record[dataIndex]; if (dataIndex.endsWith('Time')) { textValue = formatDateTime(textValue); } if (dataIndex === 'members') { return renderMembersCell(textValue); } if (dataIndex === 'accounts') { return renderAccountsCell(textValue); } if (dataIndex === 'index') { textValue = index + 1; } if ( dataIndex === 'proofImages' && textValue !== null && textValue !== undefined ) { return ( <Image.PreviewGroup className="mr-10" preview={{ onChange: (current, prev) => console.log( `current index: ${current}, prev index: ${prev}`, ), }} > {textValue.map((item, index) => ( <React.Fragment key={index}> {index > 0 ? <Divider type="vertical" /> : ''} <Image className="max-h-[35px] max-w-[45px]" src={item} title={item} />{' '} </React.Fragment> ))} </Image.PreviewGroup> ); } return <EllipsisDiv text={textValue} />; }; } return newItem; }); columns.push({ title: '操作', valueType: 'option', key: 'option', fixed: 'right', width: 120, render: (text, record) => { let btns = []; if (perms?.includes('modify')) { btns.push( <Button className="p-0" key="modify" type="link" onClick={() => { setResearchGroupAddModalVisible(true); setOptRecordId(record?.id); }} > 编辑 </Button>, ); } if (perms?.includes('delete')) { btns.push( <ButtonConfirm key="delete" className="p-0" title={'确认删除这个课题组吗?'} text="删除" onConfirm={async () => { doDeleteResearchGroup([record.id]); }} />, ); } if (record.paths?.includes('ADD_AUDIT')) { btns.push( <Button key="audit" className="p-0" type="link" onClick={async () => { setAuditIds([record.id]); setAuditModalVisible(true); setAuditType('research_groups_add_audit'); }} > 审核 </Button>, ); } return btns; }, }); return columns; }; /** * 加载申请列表表格的各个列格式 */ const memberApplyColumnsInit = () => { let columns = RESEARCH_GROUP_MEMBER_REQUEST_COLUMNS.map((item) => { let newItem = { ...item }; let dataIndex = item.dataIndex; newItem.render = (text, record, index) => { let textValue = record[dataIndex]; if (dataIndex.endsWith('Time')) { textValue = formatDateTime(textValue); } if (dataIndex === 'members') { return renderMembersCell(textValue); } if (dataIndex === 'accounts') { return renderAccountsCell(textValue); } if (dataIndex === 'index') { textValue = index + 1; } if ( dataIndex === 'proofImages' && textValue !== null && textValue !== undefined ) { return ( <Image.PreviewGroup className="mr-10" preview={{ onChange: (current, prev) => console.log(`current index: ${current}, prev index: ${prev}`), }} > {textValue.map((item, index) => ( <React.Fragment key={index}> {index > 0 ? <Divider type="vertical" /> : ''} <Image className="max-h-[35px] max-w-[45px]" src={item} title={item} />{' '} </React.Fragment> ))} </Image.PreviewGroup> ); } return <EllipsisDiv text={textValue} />; }; return newItem; }); columns.push({ title: '操作', valueType: 'option', key: 'option', fixed: 'right', width: 120, render: (text, record) => { let btns = []; if (record.permissions?.includes('modify')) { btns.push( <Button className="p-0" key="modify" type="link" onClick={() => { setResearchGroupMemberRequestAddModalVisible(true); setOptRecordId(record?.id); }} > 编辑 </Button>, ); } if (record.permissions?.includes('delete')) { btns.push( <ButtonConfirm key="delete" className="p-0" title={'确认删除这个申请吗?'} text="删除" onConfirm={async () => { doDeleteRequest([record.id]); }} />, ); } if (record.permissions?.includes('audit')) { btns.push( <Button key="audit" className="p-0" type="link" onClick={async () => { setAuditIds([record.id]); setAuditType('research_group_member_request_audit'); setAuditModalVisible(true); }} > 审核 </Button>, ); } return btns; }, }); return columns; }; const tabsItems = [ { key: 1, label: '课题组列表', children: ( <ProTable columns={researchGroupColumnsInit()} actionRef={researchGroupActionRef} cardBordered pagination={{ pageSize: 10, }} request={async (params) => { const res = await postResearchGroupsList({ data: { ...params }, }); setPerms(res.data.specialPath); return { data: res?.data?.data || [], total: res?.data?.total || 0, }; }} columnsState={{ persistenceKey: 'pro-table-singe-research-group', persistenceType: 'localStorage', defaultValue: { option: { fixed: 'right', disable: true }, }, // onChange(value) { // console.log('value: ', value); // }, }} rowKey="id" search={{ labelWidth: 'auto', }} options={{ setting: { listsHeight: 400, }, }} form={{}} dateFormatter="string" headerTitle="课题组列表" scroll={{ x: 1400 }} toolBarRender={() => { let btns = []; if (perms?.includes('add')) { btns.push( <Button key="button" icon={<PlusOutlined />} onClick={() => { setResearchGroupAddModalVisible(true); }} type="primary" > 新建 </Button>, ); } if (perms?.includes('import')) { btns.push( <Button key="button" icon={<PlusOutlined />} onClick={() => { setImportModalVisible(true); }} type="primary" > 批量导入 </Button>, ); } return btns; }} rowSelection={{ // 自定义选择项参考: https://ant.design/components/table-cn/#components-table-demo-row-selection-custom // 注释该行则默认不显示下拉选项 selections: [Table.SELECTION_ALL, Table.SELECTION_INVERT], defaultSelectedRowKeys: [], alwaysShowAlert: true, }} tableAlertOptionRender={({ selectedRows, onCleanSelected }) => { let ids = selectedRows.map((item: any) => { return item.id; }); let canAudit = selectedRows.length > 0 && selectedRows.every((item) => { return item.paths?.includes('ADD_AUDIT'); }); return ( <Space size={16}> <ButtonConfirm title="确认删除所选中的课题组信息吗?" text="批量删除" onConfirm={() => { doDeleteResearchGroup(ids); onCleanSelected(); }} /> <Button type="link" onClick={onCleanSelected}> 取消选中 </Button> { <Button key="audit" type="link" disabled={!canAudit} onClick={async () => { setAuditIds(ids); setAuditModalVisible(true); setAuditType('research_groups_add_audit'); }} > 审核 </Button> } </Space> ); }} /> ), }, { key: 2, label: '申请列表', children: ( <ProTable columns={memberApplyColumnsInit()} actionRef={memberApplyActionRef} cardBordered pagination={{ pageSize: 10, }} request={async (params) => { const res = await postResearchGroupMemberRequestsList({ data: { ...params }, }); setPerms(res.data.specialPath); return { data: res?.data?.data || [], total: res?.data?.total || 0, }; }} columnsState={{ persistenceKey: 'pro-table-singe-research-group', persistenceType: 'localStorage', defaultValue: { option: { fixed: 'right', disable: true }, }, onChange(value) { console.log('value: ', value); }, }} rowKey="id" search={{ labelWidth: 'auto', }} options={{ setting: { listsHeight: 400, }, }} form={{}} dateFormatter="string" headerTitle="申请列表" scroll={{ x: 1400 }} toolBarRender={() => { let btns = []; btns.push( <Button key="button" icon={<PlusOutlined />} onClick={() => { setResearchGroupMemberRequestAddModalVisible(true); }} type="primary" > 新建 </Button>, ); return btns; }} rowSelection={{ // 自定义选择项参考: https://ant.design/components/table-cn/#components-table-demo-row-selection-custom // 注释该行则默认不显示下拉选项 selections: [Table.SELECTION_ALL, Table.SELECTION_INVERT], defaultSelectedRowKeys: [], alwaysShowAlert: true, }} tableAlertOptionRender={({ selectedRows, onCleanSelected }) => { let ids = selectedRows.map((item: any) => { return item.id; }); let canAudit = selectedRows.length > 0 && selectedRows.every((item) => { return item.permissions?.includes('audit'); }); return ( <Space size={16}> <ButtonConfirm title="确认删除所选中的课题组信息吗?" text="批量删除" onConfirm={() => { doDeleteRequest(ids); onCleanSelected(); }} /> <Button key="delete" className="p-0" type="link" disabled={!canAudit} onClick={async () => { setAuditIds(ids); setAuditType('research_group_member_request_audit'); setAuditModalVisible(true); }} > 批量审核 </Button> <Button type="link" onClick={onCleanSelected}> 取消选中 </Button> </Space> ); }} /> ), }, ]; return ( <div className="research-group-index"> <Tabs defaultActiveKey="1" items={tabsItems} onChange={(value) => { if (value === 1) { reloadResearchGroupTable(); } else { reloadMemberApplyTable(); } }} /> {researchGroupAddModalVisible && ( <ResearchGroupAddModal setVisible={(val: boolean) => { setResearchGroupAddModalVisible(val); if (!val) { setOptRecordId(null); } }} researchGroupId={optRecordId} onClose={() => { setResearchGroupAddModalVisible(false); setOptRecordId(null); reloadResearchGroupTable(); }} /> )} {researchGroupMemberRequestAddModalVisible && ( <ResearchGroupMemberRequestAddModal setVisible={(val: boolean) => { setResearchGroupMemberRequestAddModalVisible(val); if (!val) { setOptRecordId(null); } }} requestId={optRecordId} onClose={() => { setResearchGroupMemberRequestAddModalVisible(false); setOptRecordId(null); reloadMemberApplyTable(); }} /> )} {auditModalVisible && ( <AuditModal setVisible={(val: boolean) => { setAuditModalVisible(val); if (!val) { setOptRecordId(null); } }} ids={auditIds} onClose={() => { setAuditModalVisible(false); setAuditIds([]); reloadMemberApplyTable(); researchGroupActionRef.current?.reload(); }} auditType={auditType} /> )} {importModalVisible && ( <ImportModal onClose={() => { setImportModalVisible(false); reloadMemberApplyTable(); }} /> )} </div> ); }; export default PrepaidPage;