2025-06-13 19:18:28 +08:00

1346 lines
52 KiB
TypeScript
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

/*
* @Author: cclu 1106109051@qq.com
* @Date: 2024-02-22 15:53:07
* @LastEditors: cclu 1106109051@qq.com
* @LastEditTime: 2024-08-21 14:53:15
* @FilePath: \cloud-platform\src\pages\reports\settlementDetail\index.tsx
* @Description: 这是默认设置,请设置`customMade`, 打开koroFileHeader查看配置 进行设置: https://github.com/OBKoro1/koro1FileHeader/wiki/%E9%85%8D%E7%BD%AE
*/
import React, { useRef } from "react";
import type { CurrentUser } from "umi";
import { connect } from "umi";
import type { ConnectState } from "@/models/connect";
import { useState } from "react";
import ProCard from "@ant-design/pro-card";
import { MenuFoldOutlined } from "@ant-design/icons";
import type { FormInstance } from "antd";
import { Input, Tooltip } from "antd";
import { Space } from "antd";
import { Popconfirm } from "antd";
import { Menu } from "antd";
import SubMenu from 'antd/lib/menu/SubMenu';
import { Drawer, Modal } from "antd";
import { Button, message, Select, Avatar, Typography } from "antd";
import { fmoney, getServerpartTree, getSPRegionShopTree } from "@/services/options";
import useRequest from "@ahooksjs/use-request";
import ReactHTMLTableToExcel from "react-html-table-to-excel";
import moment from "moment";
import type { ActionType } from "@ant-design/pro-table";
import ProTable from "@ant-design/pro-table";
import ProDescriptions from "@ant-design/pro-descriptions";
import { handleGetTableBasicData, handleGetTableMonthlyReconciliation } from "@/pages/reports/ShopExpenseDetail/service";
import { wrapTreeNode } from "@/utils/format";
import { getProjectList, handleAgain, handleGetSplitRes } from "@/pages/BussinessProject/service";
import ProjectDetail from "@/pages/BussinessProject/detail";
import type { BusinessProjectModel } from "@/pages/BussinessProject/data";
import './style.less'
import RevenueList from "@/pages/BussinessProject/components/RevenueList";
import ProjectSplitShow from "@/pages/BussinessProject/components/ProjectSplitShow";
import { handleCreateSettlement } from "@/pages/reports/settlementDetail/service";
import numeral from "numeral";
import SHOPEXPENSETable from "@/pages/reports/ShopExpenseDetail/detail";
import SettlementDetails from "./component/settlementDetails";
const settlementDetail: React.FC<{ currentUser: CurrentUser }> = (props) => {
const { currentUser } = props
const actionRef = useRef<ActionType>();
const actionModalRef = useRef<ActionType>();
const actionSecondRef = useRef<ActionType>();
const formRef = useRef<FormInstance>();
const formModalRef = useRef<FormInstance>();
const formSecondRef = useRef<FormInstance>();
const downloadBtnRef = useRef<any>()
const settlementDetailsRef = useRef<any>()
const [otherData, setOtherData] = useState<any>();// 显示表格上方内容
const [reqDetailList, setReqDetailList] = useState<any>(); // 合计项数据源
const [printOut, setPrintOut] = useState<any>(); // 打印数据的内容
const [showSmallDetail, setShowSmallDetail] = useState<boolean>(false) // 是否显示具体日期详情
const [currentSmallRow, setCurrentSmallRow] = useState<BusinessProjectModel | any>(undefined) // 选中的当前行
// 树相关的属性和方法
const [selectedId, setSelectedId] = useState<string>()
const [collapsible, setCollapsible] = useState<boolean>(false)
// 是否是第一次进入到页面
const [isFirst, setIsFirst] = useState<boolean>(true)
// 是否显示打印的表格
const [showExportTable, setShowExportTable] = useState<boolean>(false)
const [secondShowLoading, setSecondShowLoading] = useState<boolean>(false)
const [otherObj, setOtherObj] = useState<any>()
// 统计月份
const [searchMonth, setSearchMonth] = useState<any>()
// 加载服务区树
const { loading: treeLoading, data: treeView = [] } = useRequest(async () => {
const data = await getServerpartTree(currentUser?.ProvinceCode, currentUser?.CityAuthority, true, true, true)
return data
})
const [currenMenu, setCurrenMenu] = useState<any>(); // 当前选中左侧菜单的服务区节点
// 显示悬浮框
const [isShowModal, setIsShowModal] = useState<boolean>(false)
const { TextArea } = Input;
// 显示备注说明的弹出框
const [showDescModal, setShowDescModal] = useState<boolean>(false)
const [descText, setDescText] = useState<string>()
// 选择的项目
const [projectId, setProjectId] = useState<any>()
// 选择的项目行
const [selectProject, setSelectProject] = useState<any>()
const [selectRealProject, setSelectRealProject] = useState<any>()
const [currentRow, setCurrentRow] = useState<BusinessProjectModel | any>(undefined) // 选中的当前行
const [currentRecord, setCurrentRecord] = useState<any>()
const [showDetail, setShowDetail] = useState<boolean>(false) // 是否显示详情
const [showShare, setShowShare] = useState<boolean>(false) // 是否显示详情
// 下面那表格的数据
const [secondTableData, setSecondTableData] = useState<any>()
// 表格加载效果
const [tableLoading, setTableLoading] = useState<boolean>(false)
// 项目列表
const { loading: projectLoading, data: projectList } = useRequest(async () => {
const data = await handleGetTableBasicData({})
const list: any = []
if (data.data && data.data.length > 0) {
data.data.forEach((item: any) => {
list.push({ label: item.BUSINESSPROJECT_NAME, value: item.BUSINESSPROJECT_ID })
})
}
return list
})
const [tableAllData, setTableAllData] = useState<any>()
const columns: any = [
{
title: '项目名称',
dataIndex: 'projectName',
hideInTable: true,
valueType: 'select',
hideInSearch: true,
// valueEnum: projectList,
// fieldProps:{
// showSearch: true,
// filterOption:(input, option) => (option?.label ?? '').toLowerCase().includes(input.toLowerCase()),
// },
// renderFormItem:()=>{
// return <div style={{display:'flex',alignItems:'center'}}>
// <span>{selectRealProject?.BUSINESSPROJECT_NAME || ''}</span>
// <Button type={'primary'} style={{marginLeft:'8px'}} onClick={()=>{
// setIsShowModal(true)
// }}>选择项目</Button>
// {/* <Button type={'primary'} style={{marginLeft:'8px'}} onClick={()=>{ */}
// {/* if (selectRealProject?.BUSINESSPROJECT_ID){ */}
// {/* console.log('selectRealProject',selectRealProject) */}
// {/* setCurrentRow(selectRealProject) */}
// {/* setShowDetail(true) */}
// {/* }else{ */}
// {/* message.error('还未选择项目!') */}
// {/* } */}
// {/* }}>查看项目</Button> */}
// </div>
// // <Select
// // showSearch={true}
// // filterOption={(input, option) => (option?.label ?? '').toLowerCase().includes(input.toLowerCase())}
// // options={projectList}
// // loading={projectLoading}
// // allowClear
// // onChange={(e: any)=>{
// // if (e){
// // setProjectId(e)
// // }else{
// // setProjectId(undefined)
// // }
// // }}
// // >
// // </Select>
// }
},
{
title: '期限',
dataIndex: '',
hideInSearch: true,
children: [
{
title: <div style={{ textAlign: 'center' }}></div>,
dataIndex: 'PeriodIndexStr',
align: 'left',
width: 120,
hideInSearch: true,
render: (_, record) => {
return <span style={{ color: record?.PeriodIndexStr === '项目开始前' ? '#faad14' : '' }}>{record.PeriodIndexStr}</span>
}
},
{
title: <div style={{ textAlign: 'center' }}></div>,
dataIndex: 'PeriodDesc',
align: 'left',
width: 200,
hideInSearch: true,
render: (_, record) => {
return record?.PeriodDesc !== '合计' ?
<a style={{
color: new Date(record.EndDate).getTime() < new Date().getTime() ? '#1890ff' : '#000000',
cursor: new Date(record.EndDate).getTime() < new Date().getTime() ? 'pointer' : ''
}} onClick={() => {
console.log('record', record)
// StartDate
if (new Date(record.EndDate).getTime() < new Date().getTime()) {
const obj: any = {
...record,
...otherData,
BUSINESSPROJECT_ID: selectRealProject.BUSINESSPROJECT_ID,
STARTDATE: record.StartDate
}
console.log('obj', obj)
setCurrentRow(obj)
setShowDetail(true)
}
}}>
{`${record?.StartDate}-${record?.EndDate}`}
</a> :
<span>{`${record?.PeriodDesc}`}</span>
}
// render:(_,record)=>{
// return record?.IndexStr && record?.IndexDesc!=='合计'?
// <a onClick={()=>{
// setCurrentRecord(record)
// setCurrentRow(selectRealProject)
// setShowShare(true)
// }}>{`${record?.StartDate}-${record?.EndDate}` }</a>:
// <span>{record?.IndexDesc}</span>
// }
},
]
},
{
title: '租金信息',
dataIndex: '',
hideInSearch: true,
children: [
{
title: <div style={{ textAlign: 'center' }}>/</div>,
dataIndex: 'MinturnOver',
valueType: 'digit',
align: 'right',
width: 170,
hideInSearch: true,
render: (_, record) => {
return record?.MinturnOver ? numeral(record.MinturnOver).format('0,0.00') : '-'
}
},
{
title: <div style={{ textAlign: 'center' }}></div>,
dataIndex: 'GuaranteeRatio',
hideInSearch: true,
align: 'right',
width: 120,
render: (_, record) => {
return record?.GuaranteeRatio ? `${record?.GuaranteeRatio}%` : ''
}
}
]
},
{
title: '营业额',
dataIndex: '',
hideInSearch: true,
children: [
{
title: <div style={{ textAlign: 'center' }}></div>,
dataIndex: 'CashAmount',
valueType: 'digit',
align: 'right',
width: 100,
hideInSearch: true,
render: (_, record) => {
return record?.CashAmount ? numeral(record.CashAmount).format('0,0.00') : '-'
}
},
{
title: <div style={{ textAlign: 'center' }}></div>,
dataIndex: 'MobilePayAmount',
valueType: 'digit',
align: 'right',
width: 100,
hideInSearch: true,
render: (_, record) => {
return record?.MobilePayAmount ? numeral(record.MobilePayAmount).format('0,0.00') : '-'
}
},
{
title: <div style={{ textAlign: 'center' }}></div>,
dataIndex: 'RevenueAmount',
valueType: 'digit',
align: 'right',
width: 100,
hideInSearch: true,
render: (_, record) => {
const str: any = `微支付(${record.MobilePayAmount || 0}) + 现金(${record.CashAmount || 0})`
return <Tooltip title={str}>
<span>{record?.RevenueAmount ? numeral(record.RevenueAmount).format('0,0.00') : '-'}</span>
</Tooltip>
}
}
]
},
{
title: <div style={{ textAlign: 'center' }}></div>,
dataIndex: 'RoyaltyAmount',
valueType: 'digit',
width: 100,
align: 'right',
hideInSearch: true,
render: (_, record) => {
return record?.RoyaltyAmount || record?.RoyaltyAmount === 0 ? numeral(record.RoyaltyAmount).format('0,0.00') : '-'
}
},
{
title: '应收费用',
dataIndex: '',
hideInSearch: true,
children: [
{
title: <div style={{ textAlign: 'center' }}></div>,
dataIndex: 'GuaranteeFee',
valueType: 'digit',
align: 'right',
width: 100,
hideInSearch: true,
render: (_, record) => {
const str: string = record.GuaranteeRatio ?
(record?.RevenueAmount * (Number(record?.GuaranteeRatio) / 100)) > Number(record?.MinturnOver) ?
`营业额(${record?.RevenueAmount})*提成比例(${(record?.GuaranteeRatio ? `${record?.GuaranteeRatio}%` : '')})`
: `保底租金(${record?.MinturnOver})`
: ''
return record?.PeriodDesc !== '合计' ? <Tooltip title={str}>
<a onClick={() => {
console.log('record', record)
setCurrentRow(record)
setPropertyShow(true)
}}>
{record?.GuaranteeFee || record?.GuaranteeFee === 0 ? numeral(record.GuaranteeFee).format('0,0.00') : '-'}
</a></Tooltip> : <span>{record?.GuaranteeFee || record?.GuaranteeFee === 0 ? numeral(record.GuaranteeFee).format('0,0.00') : '-'}</span>
}
},
{
title: <div style={{ textAlign: 'center' }}></div>,
dataIndex: 'PropertyFee',
valueType: 'digit',
align: 'right',
width: 100,
hideInSearch: true,
render: (_, record) => {
return record?.PeriodDesc !== '合计' ? <a onClick={() => {
setCurrentRow(record)
setPropertyShow(true)
}}>
{record?.PropertyFee || record?.PropertyFee === 0 ? numeral(record.PropertyFee).format('0,0.00') : '-'}
</a> : <span>{record?.PropertyFee || record?.PropertyFee === 0 ? numeral(record.PropertyFee).format('0,0.00') : '-'}</span>
}
},
{
title: <div style={{ textAlign: 'center' }}></div>,
dataIndex: 'HouseRent',
valueType: 'digit',
align: 'right',
width: 100,
hideInSearch: true,
render: (_, record) => {
return record?.PeriodDesc !== '合计' ? <a onClick={() => {
setCurrentRow(record)
setPropertyShow(true)
}}>
{record?.HouseRent || record?.HouseRent === 0 ? numeral(record.HouseRent).format('0,0.00') : '-'}
</a> : <span>{record?.HouseRent || record?.HouseRent === 0 ? numeral(record.HouseRent).format('0,0.00') : '-'}</span>
}
},
{
title: <div style={{ textAlign: 'center' }}></div>,
dataIndex: 'BreachPenalty',
valueType: 'digit',
align: 'right',
width: 100,
hideInSearch: true,
render: (_, record) => {
return record?.PeriodDesc !== '合计' ? <a onClick={() => {
setCurrentRow(record)
setPropertyShow(true)
}}>
{record?.BreachPenalty || record?.BreachPenalty === 0 ? numeral(record.BreachPenalty).format('0,0.00') : '-'}
</a> : <span>{record?.BreachPenalty || record?.BreachPenalty === 0 ? numeral(record.BreachPenalty).format('0,0.00') : '-'}</span>
}
},
{
title: <div style={{ textAlign: 'center' }}></div>,
dataIndex: 'ElectricityCharge',
valueType: 'digit',
align: 'right',
width: 100,
hideInSearch: true,
render: (_, record) => {
return record?.PeriodDesc !== '合计' ? <a onClick={() => {
setCurrentRow(record)
setPropertyShow(true)
}}>
{record?.ElectricityCharge || record?.ElectricityCharge === 0 ? numeral(record.ElectricityCharge).format('0,0.00') : '-'}
</a> : <span>{record?.ElectricityCharge || record?.ElectricityCharge === 0 ? numeral(record.ElectricityCharge).format('0,0.00') : '-'}</span>
}
},
{
title: <div style={{ textAlign: 'center' }}></div>,
dataIndex: 'WaterCharge',
valueType: 'digit',
align: 'right',
width: 100,
hideInSearch: true,
render: (_, record) => {
return record?.PeriodDesc !== '合计' ? <a onClick={() => {
setCurrentRow(record)
setPropertyShow(true)
}}>
{record?.WaterCharge || record?.WaterCharge === 0 ? numeral(record.WaterCharge).format('0,0.00') : '-'}
</a> : <span>{record?.WaterCharge || record?.WaterCharge === 0 ? numeral(record.WaterCharge).format('0,0.00') : '-'}</span>
}
},
{
title: <div style={{ textAlign: 'center' }}></div>,
dataIndex: 'OtherFee',
valueType: 'digit',
align: 'right',
width: 100,
hideInSearch: true,
render: (_, record) => {
return record?.PeriodDesc !== '合计' ? <a onClick={() => {
setCurrentRow(record)
setPropertyShow(true)
}}>
{record?.OtherFee || record?.OtherFee === 0 ? numeral(record.OtherFee).format('0,0.00') : '-'}
</a> : <span>{record?.OtherFee || record?.OtherFee === 0 ? numeral(record.OtherFee).format('0,0.00') : '-'}</span>
}
},
{
title: <div style={{ textAlign: 'center' }}></div>,
dataIndex: 'ReceivableAmount',
valueType: 'digit',
align: 'right',
width: 100,
hideInSearch: true,
render: (_, record) => {
const str: string = `${record?.GuaranteeFee ? `租金(${record?.GuaranteeFee})` : 0}${record?.PropertyFee ? `+物业费(${record?.PropertyFee})` : ''}${record?.HouseRent ? `+房租(${record?.HouseRent})` : ''}${record?.BreachPenalty ? `+罚款(${record?.BreachPenalty})` : ''}${record?.ElectricityCharge ? `+电费(${record?.ElectricityCharge})` : ''}${record?.WaterCharge ? `+水费(${record?.WaterCharge})` : ''}${record?.OtherFee ? `+其他(${record?.OtherFee})` : ''}`
return record?.PeriodDesc !== '合计' ? <Tooltip title={str}><a onClick={() => {
setCurrentRow(record)
setPropertyShow(true)
}}>
{record?.ReceivableAmount ? numeral(record.ReceivableAmount).format('0,0.00') : '-'}
</a></Tooltip> : <Tooltip title={str}><span>{record?.ReceivableAmount ? numeral(record.ReceivableAmount).format('0,0.00') : '-'}</span></Tooltip>
}
},
]
},
{
title: <div style={{ textAlign: 'center' }}>
<Tooltip title={'业主收款金额-应收费用合计'}>
退
</Tooltip>
</div>,
dataIndex: 'RefundSupplement',
valueType: 'digit',
align: 'right',
width: 100,
hideInSearch: true,
render: (_, record) => {
const str: string = record?.PeriodDesc === '合计' ? `${otherObj?.Remark ? otherObj?.Remark : ''}` : `业主收款(${record?.RoyaltyAmount}) - 应收费用(${record?.ReceivableAmount})`
return record?.RefundSupplement ? <Tooltip title={str}>{numeral(record.RefundSupplement).format('0,0.00')}</Tooltip> : record?.RefundSupplement === 0 ? <Tooltip title={str}>{'0.00'}</Tooltip> : '-'
}
},
// {
// dataIndex: 'option',
// title: <div style={{textAlign:'center'}}>操作</div>,
// width: 120,
// valueType: 'option',
// align: 'center',
// fixed:'right',
// hideInSearch: true,
// render: (_,record)=>{
// return (
// record.PeriodDesc!=='合计' && new Date(record?.EndDate).getTime()<new Date().getTime() && record?.AllowApply?
// <Space>
// <a onClick={()=>{
// console.log('record',record)
// setShowDescModal(true)
// setCurrentRow(record)
// }}>结算</a>
// {/* <Popconfirm */}
// {/* title="确认结算?" */}
// {/* onConfirm={async()=>{ */}
// {/* setTableLoading(true) */}
// {/* const req = { */}
// {/* OPERATION_TYPE: 11, */}
// {/* BUSINESSPROCESS_ID:selectRealProject?.BUSINESSPROJECT_ID, */}
// {/* PROINST_ID:record?.SHOPROYALTY_ID, */}
// {/* SERVERPART_ID:selectRealProject?.SERVERPART_IDS || '416', */}
// {/* SERVERPART_IDS:selectRealProject?.SERVERPART_IDS || '416', */}
// {/* BUSINESSPROCESS_NAME:`${selectRealProject?.BUSINESSPROJECT_NAME}【${record?.IndexDesc}】年度结算`, */}
// {/* BUSINESS_STARTDATE: moment().format('YYYY-MM-DD'), */}
// {/* BUSINESSAPPROVAL_STATE:1000 */}
// {/* } */}
// {/* const data = await handleCreateSettlement(req) */}
// {/* if (data.Result_Code===100){ */}
// {/* message.success(data.Result_Desc) */}
// {/* }else{ */}
// {/* message.error(data.Result_Desc) */}
// {/* } */}
// {/* setTableLoading(false) */}
// {/* actionRef.current?.reload() */}
// {/* }} */}
// {/* > */}
// {/* <a>结算</a> */}
// {/* </Popconfirm> */}
// </Space>
// :''
// )
// // {
// // record?.IndexDesc!=='合计'?
// // return (
// //
// // <Space>
// // <Popconfirm
// // title="确认结算?"
// // onConfirm={async()=>{
// //
// // }}
// // >
// // <a>结算</a>
// // </Popconfirm>
// // </Space>:''
// // }
// // )
// }
// }
]
const columnsModal: any = [
{
title: '有效项目',
dataIndex: 'ProjectStateSearch',
hideInTable: true,
valueType: 'select',
valueEnum: {
'': { text: '全部' },
0: { text: '历史项目' },
1: { text: '在营项目' },
},
initialValue: '1'
},
{
title: '项目名称',
dataIndex: 'BUSINESSPROJECT_NAME',
hideInSearch: true,
ellipsis: true,
onCell: (record) => ({
style: {
backgroundColor: new Date(record.PROJECT_ENDDATE).getTime() < new Date().getTime() ? '#fafafa' : '#fff'
}
})
},
{
title: '经营商户',
dataIndex: 'MERCHANTS_NAME',
hideInSearch: true,
ellipsis: true,
onCell: (record) => ({
style: {
backgroundColor: new Date(record.PROJECT_ENDDATE).getTime() < new Date().getTime() ? '#fafafa' : '#fff'
}
})
},
{
title: '门店名称',
dataIndex: 'SERVERPARTSHOP_NAME',
hideInSearch: true,
ellipsis: true,
onCell: (record) => ({
style: {
backgroundColor: new Date(record.PROJECT_ENDDATE).getTime() < new Date().getTime() ? '#fafafa' : '#fff'
}
})
},
{
title: '项目时间',
dataIndex: '',
hideInSearch: true,
sorter: (a, b) => new Date(a.PROJECT_STARTDATE).getTime() - new Date(b.PROJECT_STARTDATE).getTime(),
render: (_, record) => {
return `${moment(record?.PROJECT_STARTDATE).format('YYYY-MM-DD')}-${moment(record?.PROJECT_ENDDATE).format('YYYY-MM-DD')}`
},
onCell: (record) => ({
style: {
backgroundColor: new Date(record.PROJECT_ENDDATE).getTime() < new Date().getTime() ? '#fafafa' : '#fff'
}
})
},
]
// 导出excel方法
const exportTable = (e) => {
e.stopPropagation(); // 防止Collapse组件收起
const main = document.getElementsByClassName('settlementDetailsHideBox')[0]
const topBox = main.getElementsByClassName('tableTop')[0]
const topContent = topBox.querySelector('tbody').cloneNode(true) // 表格头上的东西
const tempTable = document.createElement('table');
tempTable.appendChild(topContent);
const tableContent = main.getElementsByClassName('ant-table-content')[0]
const thead = tableContent.querySelector('thead').cloneNode(true); // 深克隆DOM节点
const tbody = tableContent.querySelector('tbody').cloneNode(true); // 深克隆DOM节点
const container = document.querySelector('#hiddenBox');
tempTable.appendChild(thead);
tempTable.appendChild(tbody);
tempTable.setAttribute('id', 'table-to-xls-settlementDetails'); // 给table添加id值与按钮上的table字段对应
container.appendChild(tempTable); // 把创建的节点添加到页面容器中
downloadBtnRef.current.handleDownload();
tempTable.remove() // 防止重复打印一个内容
setShowExportTable(false)
}
// 生成左侧菜单
const getMenuDom = (data: any[], callback: (item: any) => void) => {
return (data.map((element: any) => {
// 绑定嵌套树的子节点
if (element.children && element.children.length > 0) {
return (
<SubMenu title={<span>{element.label}</span>}
icon={element.ico ? <Avatar src={element.ico} size={16} style={{ marginRight: 4 }} shape="square" /> : null}
key={`${element.key || element.value}`}
onTitleClick={(item) => {
// 选中一级菜单
if (!currenMenu || item.key !== `${currenMenu?.key}`) {
callback.call(callback, item)
}
item.domEvent.stopPropagation();
}}
>
{element.children && element.children.length > 0 && getMenuDom(element.children, callback)}
</SubMenu>
)
}
return (<Menu.Item icon={element.ico ? <Avatar src={element.ico} size={16} shape="square" /> : null}
key={`${element.key || element.value}`}>{element.label}</Menu.Item>)
}))
}
const loadSelectedId = (item: any) => {
// 选中的子菜单key
const [type, value] = item.key.split('-')
if (type === '1') {
setSelectedId(value)
setCurrenMenu('')
actionModalRef?.current?.reload()
} else {
setSelectedId('')
setCurrenMenu('')
}
}
const [propertyShow, setPropertyShow] = useState<boolean>(false)
// 外面表格的请求数据的方法
const handleGetTableData = async (id?: any) => {
if (isFirst) {
setIsFirst(false)
return
}
if (!selectRealProject && !id) {
message.error('请选择项目!')
return []
}
setTableLoading(true)
const req = {
BUSINESSPROJECT_ID: id
}
const data = await handleGetTableMonthlyReconciliation(req)
console.log('data2', data)
let res: any = {}
let list: any = []
let otherMessage: any = {}
if (data.List && data.List.length > 0) {
res = data.List[0]
console.log('res', res)
setTableAllData(res)
if (data.List[0].ProjectPeriodList) {
otherMessage = data.List[0].ProjectPeriodList.node
console.log('otherMessage', otherMessage)
setOtherObj(otherMessage)
const resObj: any = data.List[0].ProjectPeriodList
if (resObj.children && resObj.children.length > 0) {
list = wrapTreeNode(resObj.children)
console.log('list', list)
}
list.forEach((item: any) => {
item.children = undefined
})
}
}
list.unshift({
PeriodIndexStr: '',
PeriodDesc: '合计',
MinturnOver: otherMessage?.MinturnOver,
GuaranteeRatio: otherMessage?.GuaranteeRatio,
CashAmount: otherMessage?.CashAmount,
MobilePayAmount: otherMessage?.MobilePayAmount,
RevenueAmount: otherMessage?.RevenueAmount,
RoyaltyAmount: otherMessage?.RoyaltyAmount,
GuaranteeFee: otherMessage?.GuaranteeFee,
PropertyFee: otherMessage?.PropertyFee,
HouseRent: otherMessage?.HouseRent,
BreachPenalty: otherMessage?.BreachPenalty,
ElectricityCharge: otherMessage?.ElectricityCharge,
WaterCharge: otherMessage?.WaterCharge,
OtherFee: otherMessage?.OtherFee,
ReceivableAmount: otherMessage?.ReceivableAmount,
RefundSupplement: otherMessage?.RefundSupplement,
})
console.log('list22222', list)
setReqDetailList(list)
setOtherData({
...data.OtherData,
Dates: `${moment(data?.OtherData?.PROJECT_STARTDATE).format('YYYY/MM/DD')}-${moment(data?.OtherData?.PROJECT_ENDDATE).format('YYYY/MM/DD')}`
})
// setOtherData({
// SPREGIONTYPE_NAME: res?.SpregionType_Name,
// SERVERPART_NAME: res?.ServerPart_Name,
// SERVERPARTSHOP_NAME: res?.ServerPartShop_Name,
// MERCHANTS_NAME: res?.Merchants_Name,
// Dates: res?.Dates,
// })
setTableLoading(false)
}
const secondColumns: any = [
{
title: '开始日期',
dataIndex: 'STARTDATE',
valueType: "date",
width: 110,
align: 'center',
sorter: (a, b) => (new Date(a.STARTDATE).getTime() || 0) - (new Date(b.STARTDATE).getTime() || 0),
defaultSortOrder: 'descend'
},
{
title: '结束日期',
dataIndex: 'ENDDATE',
valueType: "date",
width: 110,
align: 'center'
},
{
title: '保底租金',
dataIndex: 'MINTURNOVER',
valueType: "money",
width: 140,
align: "center",
render: (_, record) => {
return <span style={{ color: record.MINTURNOVER ? '' : '#faad14' }}>{record.MINTURNOVER ? `¥${fmoney(record.MINTURNOVER, 2)}` : '合同期外'}</span>
}
},
{
title: '实际营业额',
dataIndex: 'REVENUE_AMOUNT',
valueType: "money",
width: 140,
align: "right",
render: (_, record) => {
return <a onClick={() => { // 点击实际营业额时 打开抽屉 展示每日营收数据
console.log('record', record)
setCurrentRow({
...record,
ShopRoyalty_Id: record.SHOPROYALTY_ID,
StartDate: record.STARTDATE
})
setShowDetail(true)
}}>{record.REVENUE_AMOUNT ? fmoney(record.REVENUE_AMOUNT, 2) : '-'}</a>
},
},
{
title: '合同提成',
dataIndex: 'GUARANTEERATIO',
valueType: 'digit',
align: "center",
hideInTable: selectRealProject?.BUSINESS_TYPE === 2000,
width: 110,
render: (_, record) => {
return `${record.GUARANTEERATIO || '-'}%`
},
},
{
title: '真实提成',
dataIndex: '',
valueType: 'digit',
align: "center",
hideInTable: selectRealProject?.BUSINESS_TYPE === 2000,
width: 110,
render: (_, record) => {
return <span style={{
color: record.REVENUE_AMOUNT ?
((record.ROYALTY_THEORY / record.REVENUE_AMOUNT) * 100) >= record.GUARANTEERATIO ? 'red' : 'green'
: ''
}}>
{record.REVENUE_AMOUNT ? `${((record.ROYALTY_THEORY / record.REVENUE_AMOUNT) * 100).toFixed(2)}%` : '-'}
</span>
},
},
{
title: '甲方入账',
dataIndex: 'ROYALTY_THEORY',
valueType: "money",
align: "right",
width: 140,
render: (_, record) => {
return <span>{record.ROYALTY_THEORY ? `¥${fmoney(record.ROYALTY_THEORY, 2)}` : '-'}</span>
}
},
{
title: '乙方入账',
dataIndex: 'SUBROYALTY_THEORY',
valueType: "money",
align: "right",
width: 140,
render: (_, record) => {
return <span>{record.SUBROYALTY_THEORY ? `¥${fmoney(record.SUBROYALTY_THEORY, 2)}` : '-'}</span>
}
},
{
title: '备注说明',
dataIndex: 'BIZPSPLITMONTH_DESC',
ellipsis: true,
},
{
title: '商家欠款',
dataIndex: '',
ellipsis: true,
render: (_, record) => {
return <span style={{ color: 'red' }}>{record?.SUBROYALTY_PRICE === record?.SUBROYALTY_THEORY ? '-' : fmoney(record?.SUBROYALTY_PRICE - record?.SUBROYALTY_THEORY, 2)}</span>
}
},
{
title: '操作',
valueType: 'option',
width: 80,
render: (_, record,) => (
new Date(record?.STARTDATE).getTime() < new Date().getTime() ?
<Space>
<a
key="revenue"
onClick={async () => {
// const amount1000 = await handleAddUpdate(1000,
// record?.SHOPROYALTY_ID ? record?.SHOPROYALTY_ID : 0)
// if (amount1000) {
// actionRef.current?.reload()
// }
setSecondShowLoading(true)
let req = {}
const yesterday = moment().subtract(1, 'day').startOf('day').format('YYYY-MM-DD')
if (new Date(yesterday).getTime() < new Date(moment(record.ENDDATE).format('YYYY-MM-DD')).getTime()) {
req = {
StartDate: moment(record.STARTDATE).format('YYYY-MM-DD'),
EndDate: moment(yesterday).format('YYYY-MM-DD'),
ProjectId: selectRealProject?.BUSINESSPROJECT_ID,
// OutBusinessType:props.BUSINESS_TYPE
}
} else {
req = {
StartDate: moment(record.STARTDATE).format('YYYY-MM-DD'),
EndDate: moment(record.ENDDATE).format('YYYY-MM-DD'),
ProjectId: selectRealProject?.BUSINESSPROJECT_ID,
// OutBusinessType:props.BUSINESS_TYPE
}
}
const data = await handleAgain(req)
console.log('data', data)
setTableLoading(false)
if (data.Result_Code === 100) {
handleSecondTableData(selectRealProject?.BUSINESSPROJECT_ID)
message.success(data.Result_Desc)
} else {
message.error(data.Result_Desc)
}
setSecondShowLoading(false)
}}
>
</a>
</Space> : ''
),
},
]
const handleSecondTableData = async (id?: any) => {
if (!id) {
return
}
setSecondShowLoading(true)
const req = {
BusinessProjectId: id,
DataType: 2,
}
const data = await handleGetSplitRes(req)
setSecondTableData(data.data)
setSecondShowLoading(false)
}
// 新建结算申请
const handleCreateSettlementApplication = async () => {
console.log('selectRealProject', selectRealProject)
console.log('currentRow', currentRow)
const obj: any = {
BUSINESSPROJECT_ID: selectRealProject?.BUSINESSPROJECT_ID,
SHOPROYALTY_ID: currentRow?.ShopRoyalty_Id,
SERVERPARTSHOP_ID: selectRealProject?.SERVERPARTSHOP_ID,
BUSINESS_STARTDATE: currentRow?.StartDate,
BUSINESS_ENDDATE: currentRow?.EndDate,
GUARANTEE_AMOUNT: currentRow?.MinturnOver,
GUARANTEERATIO: currentRow?.GuaranteeRatio,
ACTUAL_REVENUE: currentRow?.RevenueAmount,
PARTYA_SHAREPROFIT: currentRow?.RoyaltyTheory,
PARTYB_SHAREPROFIT: currentRow?.SubroyaltyTheory,
LIQUIDATION_AMOUNT: currentRow?.RefundSupplement,
ROYALTY_PRICE: currentRow?.RoyaltyAmount,
SUBROYALTY_PRICE: currentRow?.SubroyaltyAmount,
MOBILEPAY_AMOUNT: currentRow?.MobilePayAmount,
CASHPAY_AMOUNT: currentRow?.CashAmount,
MERCHANTS_ID: tableAllData?.Merchants_Id,
MERCHANTS_NAME: tableAllData?.Merchants_Name
}
const req = {
BusinessapprovalModel: {
OPERATION_TYPE: 11,
BUSINESSPROCESS_ID: selectRealProject?.BUSINESSPROJECT_ID,
PROINST_ID: currentRow?.ShopRoyalty_Id,
SERVERPART_ID: tableAllData?.ServerPart_Ids || '',
SERVERPART_IDS: tableAllData?.ServerPart_Ids || '',
BUSINESSPROCESS_NAME: `${selectRealProject?.BusinessProject_Name}${currentRow?.PeriodDesc}】年度结算`,
BUSINESS_STARTDATE: moment().format('YYYY-MM-DD'),
BUSINESSAPPROVAL_STATE: 1000,
BUSINESSAPPROVAL_DESC: descText || '',
STAFF_NAME: currentUser.Name,
STAFF_ID: currentUser?.ID,
Serverpart_Name: selectRealProject?.SERVERPART_NAME
},
RevenueconfirmModel: obj
}
console.log('req', req)
const data = await handleCreateSettlement(req)
console.log('data', data)
if (data.Result_Code === 100) {
message.success(data.Result_Desc)
} else {
message.error(data.Result_Desc)
}
setDescText('')
setShowDescModal(false)
handleGetTableData(selectProject?.BUSINESSPROJECT_ID)
}
return (
<div ref={(el) => {
// 打印报表
if (!reqDetailList || reqDetailList.length === 0) return;
setPrintOut(el);
}}>
<div className={'settlementDetailsHideBox'} style={{ position: 'fixed', zIndex: -1, top: 0, left: 0 }}>
{
showExportTable && reqDetailList && reqDetailList.length > 0 ?
<ProTable
columns={columns}
dataSource={reqDetailList}
pagination={false}
expandable={{
defaultExpandAllRows: true
}}
tableExtraRender={() => {
return <div className={'tableTop'} style={{ paddingLeft: 24 }}>
<ProDescriptions column={7} className="commity-sale-description" labelStyle={{ color: "#00000073" }}>
<ProDescriptions.Item span={1} label="片区">{otherData?.SPREGIONTYPE_NAME}</ProDescriptions.Item>
<ProDescriptions.Item span={1} label="服务区">{otherData?.SERVERPART_NAME}</ProDescriptions.Item>
<ProDescriptions.Item span={2} label="门店名称">{otherData?.SERVERPARTSHOP_NAME}</ProDescriptions.Item>
<ProDescriptions.Item span={2} label="合作单位名称">{otherData?.MERCHANTS_NAME}</ProDescriptions.Item>
<ProDescriptions.Item span={1} label="合同期">{otherData?.Dates}</ProDescriptions.Item>
</ProDescriptions>
</div>
}}
/> : ''
}
</div>
<div id='hiddenBox' style={{ position: 'fixed', zIndex: -1, top: 0, left: 0 }} />
<div style={{ backgroundColor: '#fff', display: 'flex' }}>
<ProCard
style={{ width: !collapsible ? "300px" : "60px" }}
className="pageTable-leftnav"
bodyStyle={{ padding: 0, paddingTop: 20, paddingLeft: 20, width: !collapsible ? "300px" : "60px" }}
extra={<MenuFoldOutlined onClick={() => {
setCollapsible(!collapsible)
}} />}
colSpan={!collapsible ? "300px" : "60px"}
title={!collapsible ? "请选择服务区" : ""}
headerBordered
collapsed={collapsible}
>
{!treeLoading && <Menu
mode="inline"
selectedKeys={[`1-${selectedId}`]}
style={{ width: '100%', height: 'calc(100vh - 300px)', overflowY: 'auto', overflowX: 'hidden' }}
onSelect={(item: any) => {
loadSelectedId(item)
setIsShowModal(true)
}}
onClick={(item: any) => {
const [type, value] = item.key.split('-')
if (value === selectedId) {
if (type === '1') {
setSelectedId(value)
setCurrenMenu('')
actionModalRef.current?.reload()
}
setIsShowModal(true)
}
}}
>
{getMenuDom(treeView, loadSelectedId)}
</Menu>}
</ProCard>
<div style={{
width: !collapsible ? 'calc(100% - 300px)' : 'calc(100% - 60px)',
paddingTop: 0,
paddingBottom: 0,
paddingRight: 0
}}>
{/* <ProTable
rowKey={(record) => {
return `${record?.SHOPROYALTY_ID}-${record?.PeriodIndexStr}-${record?.PeriodDesc}`
}}
actionRef={actionRef}
formRef={formRef}
columns={columns}
bordered
search={false}
// search={{
// span: 12,
// optionRender: () => {
// return []
// }
// }}
loading={tableLoading}
request={async (params: any) => {
handleGetTableData()
}}
scroll={{ x: 1800 }}
headerTitle={`合作商户合同期结算明细表`} // 列表表头
dataSource={reqDetailList}
pagination={false}
toolbar={{
actions: [
<span style={{ visibility: 'hidden' }}>
<ReactHTMLTableToExcel
buttonText={'导出excel'}
ref={downloadBtnRef}
table="table-to-xls-settlementDetails"
filename={`合作商户合同期结算明细表_${moment().format('YYYY_MM_DD')}`}
sheet="sheet1"
/>
</span>,
<Typography.Text type="secondary">单位:元</Typography.Text>,
<Button
key="new"
type="primary"
onClick={(e) => {
if (reqDetailList && reqDetailList.length > 0) {
setShowExportTable(true)
setTimeout(() => {
exportTable(e)
}, 100)
} else {
message.error('暂无数据可导出!')
}
}}
>
导出excel
</Button>
]
}}
tableExtraRender={() => {
return <div style={{ paddingLeft: 24, paddingTop: 24 }} className={'showTableExtraRender'}>
<ProDescriptions column={8} className="commity-sale-description" labelStyle={{ color: "#00000073" }}>
<ProDescriptions.Item span={1} label="片区">
<Tooltip title={otherData?.SPREGIONTYPE_NAME}>
{otherData?.SPREGIONTYPE_NAME}
</Tooltip>
</ProDescriptions.Item>
<ProDescriptions.Item span={1} label="服务区">
<Tooltip title={otherData?.SERVERPART_NAME}>
{otherData?.SERVERPART_NAME}
</Tooltip>
</ProDescriptions.Item>
<ProDescriptions.Item span={2} label="门店名称">
<Tooltip title={otherData?.SERVERPARTSHOP_NAME}>
{otherData?.SERVERPARTSHOP_NAME}
</Tooltip>
</ProDescriptions.Item>
<ProDescriptions.Item span={2} label="合作单位名称">
<Tooltip title={otherData?.MERCHANTS_NAME}>
{otherData?.MERCHANTS_NAME}
</Tooltip></ProDescriptions.Item>
<ProDescriptions.Item span={2} label="合同期">
<Tooltip title={otherData?.Dates}>
{otherData?.Dates}
</Tooltip></ProDescriptions.Item>
</ProDescriptions>
</div>
}}
>
</ProTable> */}
{/* id={id} */}
<SettlementDetails onRef={settlementDetailsRef} selectRealProject={selectRealProject} setTableAllData={setTableAllData} setOtherObj={setOtherObj} setReqDetailList={setReqDetailList} toolbar={{
actions: [
<span style={{ visibility: 'hidden' }}>
<ReactHTMLTableToExcel
buttonText={'导出excel'}
ref={downloadBtnRef}
table="table-to-xls-settlementDetails"
filename={`合作商户合同期结算明细表_${moment().format('YYYY_MM_DD')}`}
sheet="sheet1"
/>
</span>,
<Typography.Text type="secondary"></Typography.Text>,
<Button
key="new"
type="primary"
onClick={(e) => {
if (reqDetailList && reqDetailList.length > 0) {
setShowExportTable(true)
setTimeout(() => {
exportTable(e)
}, 100)
} else {
message.error('暂无数据可导出!')
}
}}
>
</Button>
]
}} setOtherData={setOtherData} otherData={otherData} setCurrentRow={setCurrentRow} setShowDetail={setShowDetail} setPropertyShow={setPropertyShow} otherObj={otherObj}
isFirst={isFirst} setIsFirst={setIsFirst}/>
<ProTable
rowKey="REVENUECONFIRM_ID"
formRef={formSecondRef}
loading={secondShowLoading}
actionRef={actionSecondRef}
style={{ background: '#fff', paddingTop: '30px' }}
search={false}
options={false}
pagination={false}
headerTitle={<span style={{ color: "#1890ff", fontSize: 14, fontWeight: 600 }}>{`项目分润拆分表`}</span>} // 列表表头
columns={secondColumns}
bordered
request={async (params) => {
handleSecondTableData()
}}
dataSource={secondTableData}
/>
</div>
</div>
<Modal
title="项目列表"
open={isShowModal}
width={1300}
onOk={() => {
setSelectRealProject(selectProject)
// handleGetTableData(selectProject?.BUSINESSPROJECT_ID)
settlementDetailsRef.current?.actionRef.current?.reload()
handleSecondTableData(selectProject?.BUSINESSPROJECT_ID)
setIsShowModal(false)
}}
onCancel={() => {
setIsShowModal(false)
}}>
<div style={{ display: 'flex', background: '#fff', height: '650px' }}>
{/* <ProCard */}
{/* className="pageTable-leftnav pageTable-leftnavs" */}
{/* bodyStyle={{padding: 0, paddingTop: 20, paddingLeft: 20, height: '100%'}} */}
{/* extra={<MenuFoldOutlined onClick={() => { */}
{/* setCollapsible(!collapsible) */}
{/* }}/>} */}
{/* colSpan={!collapsible ? "300px" : "60px"} */}
{/* title={!collapsible ? "请选择服务区" : ""} */}
{/* headerBordered */}
{/* collapsed={collapsible} */}
{/* > */}
{/* {!treeLoading && <Menu */}
{/* mode="inline" */}
{/* selectedKeys={[`2-${selectedId}`]} */}
{/* style={{width: '100%',height: 'calc(100% - 50px)', overflowY: 'auto', overflowX: 'hidden'}} */}
{/* onSelect={(item: any)=>{ */}
{/* loadSelectedId(item) */}
{/* }} */}
{/* > */}
{/* {getMenuDom(treeView, loadSelectedId)} */}
{/* </Menu>} */}
{/* </ProCard> */}
<div style={{
paddingTop: 0,
paddingBottom: 0,
paddingRight: 0
}}>
<ProTable
rowKey={(record) => record?.BUSINESSPROJECT_ID}
actionRef={actionModalRef}
formRef={formModalRef}
columns={columnsModal}
tableStyle={{
width: '1200px'
}}
bordered
search={{ span: 6 }}
scroll={{ y: 470 }}
pagination={false}
request={async (params: any) => {
if (!selectedId) {
return
}
const req = {
current: 1,
pageSize: 9999,
PROJECT_VALID: 1,
ProjectStateSearch: params.ProjectStateSearch ? Number(params.ProjectStateSearch) : '',
pagesize: 9999,
SERVERPART_IDS: selectedId || ''
}
const data = await getProjectList(req)
console.log('data', data)
return { data: data.data, success: true }
}}
tableAlertRender={false}
rowSelection={{
type: "radio",
defaultSelectedRowKeys: selectRealProject,
onChange: (_, selectedRows) => {
// setSelectedRowKeys(selectedRowKeys)
setSelectProject(selectedRows[0])
}
}}
>
</ProTable>
</div>
</div>
</Modal>
{/* 查看项目详情 右侧弹出的抽屉 */}
<Drawer
width="80%"
className="project-drawer"
visible={showDetail} // 抽屉弹框是否显示状态
onClose={() => { // 关闭抽屉 则在清空选中行数据 并 设置抽屉状态为关闭
setCurrentRow(undefined);
setShowDetail(false);
}}
bodyStyle={{ backgroundColor: "#f9f9f9", padding: 0 }}
closable={false}
>
{/* 抽屉打开时 加载项目详情组件 */}
{showDetail && <RevenueList BusinessProjectId={currentRow.BUSINESSPROJECT_ID} propsBP={otherData} propsRC={currentRow}
ShopRoyaltyId={currentRow?.ShopRoyalty_Id ? currentRow?.ShopRoyalty_Id : 0}
ShopIds={selectRealProject?.SERVERPARTSHOP_ID ? selectRealProject?.SERVERPARTSHOP_ID : ''}
StartDate={moment(currentRow?.StartDate).format('YYYY-MM-DD')}
EndDate={moment(currentRow?.EndDate).format('YYYY-MM-DD')}></RevenueList>}
</Drawer>
{/* 合作分润 右侧弹出的抽屉 */}
<Drawer
width="80%"
className="project-drawer"
visible={showShare} // 抽屉弹框是否显示状态
onClose={() => { // 关闭抽屉 则在清空选中行数据 并 设置抽屉状态为关闭
setCurrentRow(undefined);
setCurrentRecord(undefined);
setShowShare(false);
}}
bodyStyle={{ backgroundColor: "#f9f9f9", padding: 0 }}
closable={false}
>
{/* currentRow */}
{/* 抽屉打开时 加载项目详情组件 */}
{showShare && <RevenueList BusinessProjectId={currentRow.BUSINESSPROJECT_ID} propsBP={otherData} propsRC={currentRecord}
ShopRoyaltyId={currentRecord?.ShopRoyalty_Id ? currentRecord?.ShopRoyalty_Id : 0}
ShopIds={currentRow?.SERVERPARTSHOP_ID ? currentRow?.SERVERPARTSHOP_ID : ''}
StartDate={moment(currentRecord?.StartDate).format('YYYY-MM-DD')}
EndDate={moment(currentRecord?.EndDate).format('YYYY-MM-DD')}></RevenueList>}
</Drawer>
{/* 显示具体日期的 */}
<Drawer
width="83%"
className="project-drawer2"
visible={showSmallDetail} // 抽屉弹框是否显示状态
onClose={() => { // 关闭抽屉 设置抽屉状态为关闭
setShowSmallDetail(false);
setCurrentSmallRow(undefined)
}}
closable={false}
destroyOnClose
>
<ProjectSplitShow projectDetail={selectRealProject} isComponents={true} componentsType={true} startDate={currentSmallRow?.StartDate} endDate={currentSmallRow?.EndDate} />
</Drawer>
{/* 结算输入备注说明的悬浮框 */}
<Modal
title="备注说明"
open={showDescModal}
width={700}
onOk={() => {
handleCreateSettlementApplication()
console.log('descText', descText)
}}
onCancel={() => {
setShowDescModal(false)
setDescText('')
}}>
<TextArea row={4} value={descText} placeholder={'请输入备注说明'} onChange={(e: any) => {
setDescText(e.target.value)
}} />
</Modal>
<Drawer
width="80%"
className="project-drawer3"
visible={propertyShow} // 抽屉弹框是否显示状态
onClose={() => { // 关闭抽屉 设置抽屉状态为关闭
setPropertyShow(false);
setCurrentRow(undefined)
}}
destroyOnClose
closable={false}
>
<SHOPEXPENSETable isComponent={true} serviceShopId={selectRealProject?.SERVERPARTSHOP_ID.split(',')[0]} time={[moment(currentRow?.StartDate).format("YYYY-MM-DD"), moment(currentRow?.EndDate).format("YYYY-MM-DD")]} />
</Drawer>
</div>
)
}
export default connect(({
user
}: ConnectState) => ({
currentUser: user.currentUser
}))(settlementDetail);