Commit 1f6f178b authored by 前端-黄佳鑫's avatar 前端-黄佳鑫

Merge branch 'dev-srm' of http://10.0.0.22:3000/lingxi/lingxi-business-paltform into dev-srm

parents f68b18bb f3de12d3
......@@ -67,6 +67,14 @@ export const purchaseBidRoute = [
name: '待竞价',
component: '@/pages/transaction/purchaseAbility/purchaseBid/readyBid'
},
// 竞价管理
{
path: '/memberCenter/procurementAbility/purchaseBid/readyBid/management',
name: '竞价管理',
component: '@/pages/transaction/purchaseAbility/purchaseBid/readyBid/management',
hideInMenu: true,
noMargin: true,
},
// 待提交审核竞价结果
{
path: '/memberCenter/procurementAbility/purchaseBid/readySubmitExamineResult',
......
<?xml version="1.0" encoding="UTF-8"?>
<svg width="14px" height="13px" viewBox="0 0 14 13" version="1.1" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink">
<title>message-square</title>
<defs>
<path d="M8,6 C8.368,6 8.66666667,6.29866667 8.66666667,6.66666667 C8.66666667,7.03466667 8.368,7.33333333 8,7.33333333 C7.632,7.33333333 7.33333333,7.03466667 7.33333333,6.66666667 C7.33333333,6.29866667 7.632,6 8,6 Z M10.6666667,6 C11.0346667,6 11.3333333,6.29866667 11.3333333,6.66666667 C11.3333333,7.03466667 11.0346667,7.33333333 10.6666667,7.33333333 C10.2986667,7.33333333 10,7.03466667 10,6.66666667 C10,6.29866667 10.2986667,6 10.6666667,6 Z M5.33333333,6 C5.70133333,6 6,6.29866667 6,6.66666667 C6,7.03466667 5.70133333,7.33333333 5.33333333,7.33333333 C4.96533333,7.33333333 4.66666667,7.03466667 4.66666667,6.66666667 C4.66666667,6.29866667 4.96533333,6 5.33333333,6 Z M13.3333333,10 C13.3333333,10.3673333 13.034,10.6666667 12.6666667,10.6666667 L5.70266667,10.6666667 C5.34066667,10.6666667 4.98466667,10.7653333 4.67333333,10.952 L2.66666667,12.156 L2.66666667,3.33333333 C2.66666667,2.966 2.966,2.66666667 3.33333333,2.66666667 L12.6666667,2.66666667 C13.034,2.66666667 13.3333333,2.966 13.3333333,3.33333333 L13.3333333,10 Z M12.6666667,1.33333333 L3.33333333,1.33333333 C2.23066667,1.33333333 1.33333333,2.23066667 1.33333333,3.33333333 L1.33333333,13.3333333 C1.33333333,13.5733333 1.46266667,13.7953333 1.67133333,13.9133333 C1.77333333,13.9713333 1.88666667,14 2,14 C2.11866667,14 2.23733333,13.9686667 2.34333333,13.9046667 L5.35933333,12.0953333 C5.46333333,12.0326667 5.582,12 5.70266667,12 L12.6666667,12 C13.7693333,12 14.6666667,11.1026667 14.6666667,10 L14.6666667,3.33333333 C14.6666667,2.23066667 13.7693333,1.33333333 12.6666667,1.33333333 L12.6666667,1.33333333 Z" id="path-1"></path>
</defs>
<g id="控件" stroke="none" stroke-width="1" fill="none" fill-rule="evenodd">
<g id="聊天" transform="translate(-5.000000, -6.000000)">
<g id="message-square" transform="translate(4.000000, 5.000000)">
<mask id="mask-2" fill="white">
<use xlink:href="#path-1"></use>
</mask>
<use id="🎨-Icon-Сolor" fill="#00B37A" xlink:href="#path-1"></use>
</g>
</g>
</g>
</svg>
\ No newline at end of file
// @统一处理 业务表格内不嵌套NiceForm组件的高级筛选 间距异常问题
.god-schema-form {
& > .ant-form-item {
margin-bottom: 0 !important;
}
& > .ant-row-end {
margin-top: 24px !important;
}
}
import React from 'react'
import {history} from 'umi'
import { formatTimeString } from '@/utils'
import EyePreview from '@/components/EyePreview'
import { PlayCircleOutlined, PoweroffOutlined } from '@ant-design/icons'
import CustomTag from '@/pages/procurement/components/CustomTag'
import CustomBadge from '@/pages/procurement/components/customBadge'
import { CALLFORBID_TYPE, PURCHASE_TYPE } from '@/constants'
// 招投标内部状态
export const insideStatusText = [
"待提交审核",
"审核通过",
"报名审核通过",
"资格预审审核通过",
"待开标",
"待评标",
"待提交审核定标",
"定标审核通过(二级)",
"完成招标",
"已废标",
]
// 招投标外部状态
export const outStatusText = [
"待提交招标",
"待平台审核招标",
"待招标报名",
"待资格预审",
"待开标",
"待评标",
"待定标",
"待中标公示",
"完成招标",
"已废标",
]
// 评标中的环节状态
export const remarkProcessStatus = [
"未报名",
"已评标",
"未评标",
"未报名",
"未报价",
"报名审核未通过",
"资格审核未通过",
]
// 招标表格基本列
export const baseBidListColumns: any[] = [
{
title: '招标编号/项目',
align: 'left',
dataIndex: 'code',
key: 'code',
render: (text, record) => <>
<EyePreview url={`${history.location.pathname}/detail?id=${record.id}`}>
{text}
</EyePreview>
<div>{record['projectName']}</div>
</>
},
{
title: '采购类型',
align: 'left',
dataIndex: 'purchaseType',
key: 'purchaseType',
render: (t) => PURCHASE_TYPE[t]
},
{
title: '招标方式',
align: 'left',
dataIndex: 'inviteTenderType',
key: 'inviteTenderType',
render: (t) => CALLFORBID_TYPE[t]
},
{
title: '发布时间',
align: 'left',
dataIndex: 'createTime',
key: 'createTime',
render: (text, record) => formatTimeString(record.createTime),
width: 200
},
{
title: '投标开始/截止时间',
align: 'left',
dataIndex: 'createTime',
key: 'createTime',
render: (text, record) => <>
<div><PlayCircleOutlined />&nbsp;{formatTimeString(record.inviteTenderStartTime)}</div>
<div><PoweroffOutlined />&nbsp;{formatTimeString(record.inviteTenderEndTime)}</div>
</>,
width: 200
},
{
title: '外部状态',
align: 'left',
dataIndex: 'tenderOutStatus',
key: 'tenderOutStatus',
render: text => <CustomTag status={text} type='out' />
},
{
title: '内部状态',
align: 'left',
dataIndex: 'inviteTenderInStatus',
key: 'inviteTenderInStatus',
render: (text) => <CustomBadge status={text} type='inside' />
},
]
// 投标表格基本列
export const baseTenderListColumns: any[] = [
{
title: '投标编号/项目',
align: 'left',
dataIndex: 'id',
key: 'id',
render: (text, record) => <>
{record.code ? <EyePreview url={`/memberCenter/procurementAbility/tender/tenderSearch/detail?id=${record.id}`}>
{record.code}
</EyePreview> : null}
<div>{record.inviteTender.projectName}</div>
</>
},
{
title: '招标编号/会员',
align: 'left',
dataIndex: 'memberId',
key: 'memberId',
render: (text, record) => <>
<EyePreview url={`/memberCenter/procurementAbility/tender/callForBidsSearch/detail?id=${record.inviteTender.id}`}>
{record.inviteTender.code}
</EyePreview>
<div>{record.inviteTender.memberName}</div>
</>
},
{
title: '投标开始/截止时间',
align: 'left',
dataIndex: 'inviteTender',
key: 'inviteTender',
render: (text, record) => <>
<div><PlayCircleOutlined />&nbsp;{formatTimeString(record.inviteTender.inviteTenderStartTime)}</div>
<div><PoweroffOutlined />&nbsp;{formatTimeString(record.inviteTender.inviteTenderEndTime)}</div>
</>,
width: 200
},
{
title: '外部状态',
align: 'left',
dataIndex: 'tenderOutStatus',
key: 'tenderOutStatus',
render: text => <CustomTag status={text} type='out' />
},
{
title: '内部状态',
align: 'left',
dataIndex: 'submitTenderInStatus',
key: 'submitTenderInStatus',
render: (text) => <CustomBadge status={text} type='tenderInside' />
},
]
......@@ -10,6 +10,7 @@ import { PublicApi } from '@/services/api';
const Option = Select.Option;
const { Link } = Anchor;
import { history } from 'umi'
const { Text } = Typography;
const activeAnchorClassName = 'ant-anchor-link-active'
......@@ -35,6 +36,9 @@ const Details = (props: any) => {
})
const [payPlanList, setpayPlanList] = useState<any>([])
const [data, setdata] = useState<any>([])
const [contractNo, setcontractNo] = useState();
const [basics, setbasics] = useState({})
const [contractAbstract, setcontractAbstract] = useState();
const [tabPane] = useState([
{ id: 'process', title: '基本流程' },
{ id: 'conditions', title: '付款计划' },
......@@ -61,6 +65,9 @@ const Details = (props: any) => {
PublicApi.getContractExecuteGetDetail({ contractId }).then(res => {
if (res.code === 1000) {
let { basics, payPlanList } = res.data
setcontractNo(basics.contractNo)
setcontractAbstract(basics.contractAbstract)
setbasics(basics)
const basicInfo = {
col1: [
{ label: '合同编号:', extra: basics.contractNo ? basics.contractNo : '' },
......@@ -82,7 +89,7 @@ const Details = (props: any) => {
const data = {
contractId,
orderNo: basics.sourceNo ? basics.sourceNo : '',
orderAbstract: basics.contractAbstract,
orderAbstract: '',
startTime: basics.startTime,
endTime: basics.endTime,
current: 1,
......@@ -207,10 +214,13 @@ const Details = (props: any) => {
})
})
}
const onConfirm = () => {
setVisible(false)
console.log('确定')
/* 非手工单进入请款 */
const like = (sourceType) => {
// basics.
sessionStorage.setItem('basics', JSON.stringify(basics));
history.push('/memberCenter/contract/funds/addbill/Add?applyId=' + contractId + '&sourceType=' + sourceType)
}
return (
<div className={style.anchorWrap}>
<Anchor
......@@ -227,6 +237,7 @@ const Details = (props: any) => {
}}
>
<ArrowLeftOutlined
onClick={() => history.goBack()}
style={{
fontSize: '14px',
color: '#909399',
......@@ -240,7 +251,7 @@ const Details = (props: any) => {
marginLeft: '8px',
}}
>
进口头层黄牛皮荔枝纹 | SPTY12
{contractAbstract} | {contractNo}
</span>
</div>
......@@ -312,7 +323,7 @@ const Details = (props: any) => {
<div className={style.proportion}>{item.payRatio}%</div>
<div style={{ display: 'flex', justifyContent: 'space-between', alignItems: 'center' }}>
<div className={style.Price}>¥{item.payAmount}</div>
<div style={{ cursor: 'pointer', fontSize: 12, backgroundColor: '#00B37A', color: '#fff', padding: '4px 8px' }}>请款</div>
<div onClick={() => like(1)} style={{ cursor: 'pointer', fontSize: 12, backgroundColor: '#00B37A', color: '#fff', padding: '4px 8px' }}>请款</div>
</div>
<div className={style.warp_List}>
<div className={style.warp_ListItem}>
......
import React, { useState, useRef } from 'react'
import React, { useState, useRef, useEffect } from 'react'
import { history } from 'umi';
import { PageHeaderWrapper } from '@ant-design/pro-layout';
import { Card, Tabs, Button } from 'antd';
......@@ -10,13 +10,17 @@ import ReutrnEle from '@/components/ReturnEle';
import AddInfo from './components/info'
import InfoTable from './components/table'
import { PublicApi } from '@/services/api';
const formActions = createFormActions();
const { TabPane } = Tabs;
const Add: React.FC<{}> = () => {
const Add: React.FC<{}> = (props) => {
const { location: { query: { sourceType } } } = props;
console.log(sourceType)
const currentBasic = useRef<any>({});
const [basic, setbasic] = useState<any>({});
const detailData = useRef<any>({});
const [flag, setflag] = useState<any>(false);
const [id, setid] = useState('');
......@@ -26,6 +30,7 @@ const Add: React.FC<{}> = () => {
setid(data.selectRow.id)
console.log(data)
}
const TabList = [
{
name: '基本信息', components:
......@@ -34,21 +39,43 @@ const Add: React.FC<{}> = () => {
getcontractId={getflag}
/>
},
{ name: '请款明细', components: <InfoTable flag={flag} id={id} /> },
{
name: '请款明细', components:
<InfoTable
flag={flag}
id={id}
currentRef={detailData}
/>
},
]
const submit = async () => {
const basicsVO = await currentBasic.current.get();
console.log(basicsVO)
// const detailList = await detailData.current.get();
let detailList = [
{
id: 0,
applyAmount: 100,
orderId: 41,
orderNO: 'JJHJ23484',
isHasTax: 1,
taxRate: 10
}
]
console.log(basicsVO, detailList)
basicsVO.data.sourceType = sourceType ? sourceType : 3;
let data = {
basics: basicsVO.data,
detailList: []
detailList: detailList,
}
PublicApi.postContractApplyAmountSave(data).then(res => {
console.log(res);
if (res.code === 1000) {
history.push('/memberCenter/contract/funds/addbill')
}
})
}
return (
<PageHeaderWrapper
title="新建请款单"
......
......@@ -24,6 +24,7 @@ const AddInfo = (props: any) => {
const [visible, setvisible] = useState<boolean>(false);
const [rowSelection, RowCtl] = useRowSelectionTable({ customKey: 'id', type: 'radio' });
const [account, setaccount] = useState<string>('');
const [isFalg, setisFalg] = useState(false);
/* 初始值 */
const [basics, setBasics] = useState<any>({
......@@ -121,34 +122,46 @@ const AddInfo = (props: any) => {
/* 确认回显数据 */
const Confirm = () => {
let selectRow = RowCtl.selectRow[0];
getAmountOrder(selectRow)
setvisible(!visible);
}
/* 查询银行卡新 */
const getAmountOrder = (selectRow) => {
PublicApi.getContractManageGetContractInfoByApplyAmountOrder({ contractId: selectRow.id }).then(res => {
const expectPayTime = new Date(res.data.payPlanList[0].expectPayTime).getTime();
const basicsData = basics;
const info = Info;
basicsData.payeeName = res.data.corporateAccountConfig.name;
basicsData.bankAccount = res.data.corporateAccountConfig.bankAccount;
basicsData.bankDeposit = res.data.corporateAccountConfig.bankDeposit;
basicsData.payPlanId = res.data.payPlanList[0].id;
basicsData.payRatio = res.data.payPlanList[0].payRatio;
basicsData.expectPayTime = moment(expectPayTime),
basicsData.payWay = res.data.payPlanList[0].payWay
basicsData.contractNo = selectRow.contractNo;
basicsData.contractId = selectRow.id;
info.startTime = selectRow.startTime;
info.status = "同意签订合同";
// basicsData.applyAmount = res.data.payPlanList[0].applyAmount;
setpayPlanList(res.data.payPlanList)
setInfo(info)
getcontractId({ flag: true, selectRow })
const auth = JSON.parse(localStorage.getItem('auth'));
setaccount(auth.account);
setBasics(basicsData)
attrValueForm.setFieldsValue(basicsData);
if (res.code == 1000) {
const expectPayTime = new Date(res.data.payPlanList[0].expectPayTime).getTime();
const basicsData = basics;
const info = Info;
basicsData.payeeName = res.data.corporateAccountConfig.name;
basicsData.bankAccount = res.data.corporateAccountConfig.bankAccount;
basicsData.bankDeposit = res.data.corporateAccountConfig.bankDeposit;
basicsData.payPlanId = res.data.payPlanList[0].id;
basicsData.payRatio = res.data.payPlanList[0].payRatio;
basicsData.expectPayTime = moment(expectPayTime),
basicsData.payWay = res.data.payPlanList[0].payWay
basicsData.contractNo = selectRow.contractNo;
basicsData.contractId = selectRow.id;
info.startTime = selectRow.startTime;
info.status = "同意签订合同";
// basicsData.applyAmount = res.data.payPlanList[0].applyAmount;
setpayPlanList(res.data.payPlanList)
setInfo(info)
getcontractId({ flag: true, selectRow })
const auth = JSON.parse(localStorage.getItem('auth'));
setaccount(auth.account);
setBasics(basicsData)
attrValueForm.setFieldsValue(basicsData);
}
})
setvisible(!visible);
}
useEffect(() => {
let basics = JSON.parse(sessionStorage.getItem('basics'))
if (basics) {
getAmountOrder(basics);
setisFalg(true)
}
}, [])
useEffect(() => {
currentRef.current = {
get: () => new Promise((resolve: any) => {
attrValueForm.validateFields().then(res => {
......@@ -199,9 +212,9 @@ const AddInfo = (props: any) => {
<div style={{
flex: 1,
}}>
<Form.Item label="请款单号" labelAlign="left" labelCol={{ span: 4 }} wrapperCol={{ span: 18 }}>
{/* <Form.Item label="请款单号" labelAlign="left" labelCol={{ span: 4 }} wrapperCol={{ span: 18 }}>
<span>{basics.applyAbstract}</span>
</Form.Item>
</Form.Item> */}
<Form.Item
label="请款单摘要"
labelAlign="left"
......@@ -224,7 +237,12 @@ const AddInfo = (props: any) => {
name="contractNo"
wrapperCol={{ span: 18 }}
>
<Search placeholder="最长60个字符,30个汉字" readOnly enterButton={<div onClick={() => setvisible(!visible)}><LinkOutlined /> 选择</div>} />
{
isFalg ?
<Input placeholder='最长60个字符,30个汉字' disabled />
:
<Search placeholder="最长60个字符,30个汉字" readOnly enterButton={<div onClick={() => setvisible(!visible)} ><LinkOutlined /> 选择</div>} />
}
</Form.Item>
<Form.Item label="收款方" labelAlign="left" labelCol={{ span: 4 }} wrapperCol={{ span: 18 }}>
<span>{account}</span>
......@@ -351,12 +369,12 @@ const AddInfo = (props: any) => {
>
<TextArea placeholder='最长160字符,80个汉字' maxLength={160} style={{ height: 72 }} />
</Form.Item>
<Form.Item label="发票编号" labelAlign="left" labelCol={{ span: 4 }} wrapperCol={{ span: 18 }}>
{/* <Form.Item label="发票编号" labelAlign="left" labelCol={{ span: 4 }} wrapperCol={{ span: 18 }}>
<span>{Info.number}</span>
</Form.Item>
<Form.Item label="开票日期" labelAlign="left" labelCol={{ span: 4 }} wrapperCol={{ span: 18 }}>
<span>{Info.time}</span>
</Form.Item>
</Form.Item> */}
<Form.Item label="单据时间" labelAlign="left" labelCol={{ span: 4 }} wrapperCol={{ span: 18 }}>
<span>{Info.startTime}</span>
</Form.Item>
......
import React, { useState, useRef } from 'react';
import React, { useState, useRef, useEffect } from 'react';
import { Button, Table, Input, Space, Drawer, Typography } from 'antd'
import styles from './index.less'
import { useRowSelectionTable } from '@/hooks/useRowSelectionTable';
......@@ -18,38 +18,65 @@ import { PublicApi } from '@/services/api';
const { Text } = Typography;
const table = (props: any) => {
const { flag, id } = props;
const { flag, id, currentRef } = props;
const refs = useRef({});
const [visible, setvisible] = useState<boolean>(false);
const [rowSelection, RowCtl] = useRowSelectionTable({ customKey: 'id', type: 'radio' });
const [rowSelection, RowCtl] = useRowSelectionTable({ customKey: 'orderId', type: 'radio' });
const [toorderAmount, settoorderAmount] = useState<number>(0);
const [PlanList, setPlanList] = useState<any>([
]);
const tabcolumns: any = [
{
title: '单据号/摘要', dataIndex: 'payNum', align: 'center',
title: '单据编号/摘要', dataIndex: 'applyNo', align: 'center',
render: (text, record) =>
<div>
<p> {text}</p>
{/* <p>{record.applyAbstract}</p> */}
</div>
},
{
title: '单据类型', dataIndex: 'payStage', align: 'center',
title: '订单类型', dataIndex: 'orderTypeName', align: 'center',
render: (text) =>
<div>
<p>{text}</p>
</div>
},
{
title: '单据状态', dataIndex: 'expectPayTime', align: 'center',
title: '单据状态', dataIndex: 'outerStatus', align: 'center',
render: (text) =>
<div>
<p>{text}</p>
</div>
},
{
title: '单据时间', dataIndex: 'payRatio', align: 'center',
title: '单据时间', dataIndex: 'orderTime', align: 'center',
},
{
dataIndex: 'payAmount', align: 'center',
title: (
<Space direction='vertical'>
<Text>单据金额</Text>
<Text>合计: ¥156.000.00</Text>
<Text>合计: ¥{toorderAmount}</Text>
</Space>
),
dataIndex: 'orderAmount', align: 'center',
render: (text, record) =>
<div>
<p>{text}</p>
</div>
},
{
title: '含税/税率', dataIndex: 'payWay', align: 'left',
title: '含税/税率', dataIndex: 'taxRate', align: 'left',
render: (text, record) =>
<div>
<p>{text ? '是' : '否'}</p>
<p>%{text}</p>
</div>
},
{
......@@ -60,15 +87,23 @@ const table = (props: any) => {
<Text>合计: ¥156.000.00</Text>
</Space>
),
render: (text, record) =>
<div>
<p>{text ? text : 0}</p>
</div>
},
{
dataIndex: 'payAmount', align: 'center',
dataIndex: 'unPayApplyAmount', align: 'center',
title: (
<Space direction='vertical'>
<Text>已请款待付款</Text>
<Text>合计: ¥156.000.00</Text>
</Space>
),
render: (text, record) =>
<div>
<p>{text ? text : 0}</p>
</div>
},
{
dataIndex: 'payAmount', align: 'center',
......@@ -78,28 +113,103 @@ const table = (props: any) => {
<Text>合计: ¥156.000.00</Text>
</Space>
),
render: (_, item, index) =>
<Input
addonBefore="¥"
style={{
width: 130,
}}
placeholder=""
onChange={(e) => onSelectChange(e, 'payAmount', index)}
/>
},
{
title: '操作',
dataIndex: '',
align: 'center',
key: 'x',
render: (_, item, index) => <a onClick={() => Delete(item, index)}>删除</a>,
},
];
const [PlanList, setPlanList] = useState<any>([
{
payNum: '1',
payStage: '',
expectPayTime: '',
payRatio: '',
payAmount: '',
payWay: '1',
payParam: '',
},
]);
const onSelectChange = (e, name, idx) => {
}
/* 计算金额 */
const Amount = () => {
// bidCount
let tobidCount = 0;
let toorderAmount = 0;
PlanList.map(item => {
toorderAmount += item.orderAmount;
})
settoorderAmount(toorderAmount)
}
/* 删除 */
const Delete = (elm, idx) => {
// const dataSource = [...PlanList];
// const arr = [...payNumArr]
// let List = dataSource.filter((item, index) => index !== idx);
// let numberArr = arr.filter((item, index) => elm.payNum !== item);
// console.log(numberArr);
// setpayNumArr(numberArr)
// setPlanList(List)
};
const columnsList: any = [
{
title: '单据编号/摘要',
dataIndex: 'applyNo',
align: 'center',
render: (text, record) =>
<div>
<p> {text}</p>
<p>{record.applyAbstract}</p>
</div>
},
{
title: '单据类型',
dataIndex: 'orderTypeName',
align: 'center',
render: (text, record) =>
<div>
<p>{text}</p>
</div>
},
{
title: '单据时间',
dataIndex: 'orderTime',
align: 'center',
},
{
title: '单据状态',
dataIndex: 'outerStatus',
align: 'center',
render: (text) =>
<div>
<p>{text}</p>
</div>
},
{
title: '单据金额',
dataIndex: 'orderAmount',
align: 'center',
render: (text, record) =>
<div>
<p>{text}</p>
</div>
},
{
title: '待请款',
dataIndex: 'toBePayAmount',
align: 'center',
render: (text, record) =>
<div>
<p>{text}</p>
</div>
},
]
/***
* @function fetchData 请求表格数据
......@@ -109,15 +219,26 @@ const table = (props: any) => {
return new Promise(resolve => {
PublicApi.getContractApplyAmountContractOrderPageList({ ...params }).then(res => {
console.log(res)
// resolve(res.data)
resolve(res.data)
})
})
}
const Confirm = () => {
let PlanList = [];
PlanList.push(RowCtl.selectRow[0])
setPlanList(PlanList)
console.log(PlanList, RowCtl.selectRow[0])
setvisible(false)
Amount()
}
return (
useEffect(() => {
currentRef.current = {
get: () => new Promise((resolve: any) => {
})
}
})
return (
<div className="table">
{
flag && <div style={{ padding: 15, }} onClick={() => setvisible(!visible)} >
......@@ -159,7 +280,7 @@ const table = (props: any) => {
>
<StandardTable
tableProps={{
rowKey: 'id',
rowKey: 'orderId',
}}
columns={columnsList}
currentRef={refs}
......
This diff is collapsed.
import React, { useState, useRef, ReactNode } from 'react'
import { history, Link } from 'umi';
import { history } from 'umi';
import { PageHeaderWrapper } from '@ant-design/pro-layout';
import { Anchor, Radio, Steps, Row, Col, Input, message, Modal, Card } from 'antd';
import { Radio, Input, message, Modal, Card } from 'antd';
import statuStyle from '../../common/colorTag'
import { ColumnType } from 'antd/lib/table/interface';
import { StandardTable } from 'god';
......@@ -15,6 +15,7 @@ import Submit from '@/components/NiceForm/components/Submit'
import SearchSelect from '@/components/NiceForm/components/SearchSelect'
import DateRangePickerUnix from '@/components/NiceForm/components/DateRangePickerUnix'
import moment from 'moment';
import "../../constants/index.less"
const { TextArea } = Input;
const Bill: React.FC<{}> = () => {
......@@ -36,7 +37,7 @@ const Bill: React.FC<{}> = () => {
return (
<div>
<EyePreview
type="button"
url={`/memberCenter/contract/funds/bill/details?applyId=${record.id}&type=pageDetailList`}
>
{text}
</EyePreview>
......@@ -60,7 +61,8 @@ const Bill: React.FC<{}> = () => {
align: 'center',
dataIndex: 'contractNo',
render: (text: any, record: any) => <EyePreview
type="button"
// type="button"
url={`/memberCenter/contract/manage/QueryList/QueryListdetails?contractId=${record.contractId}`}
>
{text}
</EyePreview>
......@@ -103,9 +105,10 @@ const Bill: React.FC<{}> = () => {
return (
<>
{
record.status != 9 || record.status != 7 || record.status != 8 || record.status != 1 && <span style={{ color: '#00B37A', marginRight: 20, cursor: 'pointer', }} onClick={() => invalid(record.id)}>作废</span>
// 0.全部,1.待提交审核,2.待审核(一级),3.审核不通过(一级),4.待审核(二级),5.审核不通过(二级),6.待提交财务付款,7.待付款,8.已付款,9.已作废
record.status != 7 || record.status != 8 || record.status != 1 || record.status != 9 && <span style={{ color: '#00B37A', marginRight: 20, cursor: 'pointer', }} onClick={() => invalid(record.id)}>作废</span>
}
<span style={{ color: '#00B37A', marginRight: 20, cursor: 'pointer', }} onClick={() => history.push(`/memberCenter/contract/funds/bill/details?applyId=${record.id}&type=1`)}>查看</span>
{/* <span style={{ color: '#00B37A', marginRight: 20, cursor: 'pointer', }} onClick={() => history.push(`}>查看</span> */}
</>
)
}
......
import React, { useState } from 'react';
import { Button, Input, Form, Select, Radio, message, Modal } from 'antd'
const { Search, TextArea } = Input
import { StandardTable } from 'god';
import { PublicApi } from '@/services/api';
const { Option } = Select;
const Examine = (props: any) => {
const { ExamineFlag, getfetchData, applyId, type } = props;
const [Visible, setIsModalVisible] = useState<boolean>(false)
const [isPass, setIsAllMember] = useState()
const [form] = Form.useForm();
/***
* @function fetchData 请求表格数据
**/
/* 提交表单 */
const onFinish = (values: any) => {
values.applyId = applyId;
let fn;
switch (type) {
case 'submitExamine':
fn = PublicApi.postContractApplyAmountSubmitExamine
break;
case 'PageToBeExamineOne':
fn = PublicApi.postContractApplyAmountExamineStepOne
break;
case 'ToBeExamineTwo':
fn = PublicApi.postContractApplyAmountExamineStepTwo
break;
}
const msg = message.loading({
content: '正在操作',
duration: 0,
});
fn(values).then(res => {
console.log(res);
if (res.code === 1000) {
getfetchData({
ExamineFlag: false,
code: 1000
})
}
}).finally(() => {
msg();
});
};
const handleIsAllMemberChange = (v: any) => {
setIsAllMember(v.target.value)
}
const onFinishFailed = (errorInfo: any) => {
console.log('Failed:', errorInfo);
};
/* 回调 */
const fetchData = (val) => {
console.log(22222);
if (val == 'onCancel') {
getfetchData({
ExamineFlag: false,
code: 9999
})
} else {
console.log('确认')
}
}
return (
<div>
<Modal footer={null} title="提交审核" visible={ExamineFlag} onCancel={() => fetchData('onCancel')}>
<Form
name="basic"
form={form}
initialValues={{ remember: true }}
onFinish={onFinish}
onFinishFailed={onFinishFailed}
>
<Form.Item name="isPass" label="" rules={[{ required: true, message: '请选择作废日期' }]} initialValue={isPass} >
<Radio.Group onChange={handleIsAllMemberChange}>
<Radio value={1}>通过</Radio>
<Radio value={0}>不通过</Radio>
</Radio.Group>
</Form.Item>
<Form.Item label={isPass ? '审核通过原因' : '审不核通过原因'} rules={[{ required: true, message: '请选择作废日期' }]}>
</Form.Item>
<Form.Item label='' name="opinion" rules={[{ required: true, message: '审核通过意见' }]}>
<TextArea placeholder="在此输入你的原因,最多60个汉字" maxLength={120} />
</Form.Item>
<div style={{ display: 'flex', justifyContent: 'flex-end' }}>
<Button onClick={() => fetchData('onCancel')} style={{ marginRight: 10 }}>取消</Button>
<Button type="primary" htmlType="submit">保存</Button>
</div>
</Form>
</Modal>
</div>
)
}
export default Examine;
import React, { useRef, useState } from 'react';
import { ColumnType } from 'antd/lib/table/interface';
import { StandardTable } from 'god';
import EyePreview from '@/components/EyePreview'
import { useStateFilterSearchLinkageEffect } from '@/formSchema/effects/useFilterSearch'
import { FORM_FILTER_PATH } from '@/formSchema/const'
import DateRangePickerUnix from '@/components/NiceForm/components/DateRangePickerUnix'
import { PublicApi } from '@/services/api';
import Submit from '@/components/NiceForm/components/Submit'
const Materials = (props: any) => {
const { applyId, type } = props;
const ref = useRef({});
/***
* @function fetchData 请求表格数据
**/
const isTitle = (title, Price) => {
return (
<div className="a">
<div>{title}</div>
<div>合计金额:¥{Price}</div>
</div>
)
}
// 列表数据
const fetchData = (params?: any) => {
console.log(params)//可以直接打印参数
return new Promise((resolve, reject) => {
let fn;
switch (type) {
/* 查询请款明细 */
case 'pageDetailList':
fn = PublicApi.getContractApplyAmountPageDetailList
break;
case 'submitExamine':
fn = PublicApi.getContractApplyAmountPageToBeAdd
break;
case 'PageToBeExamineOne':
fn = PublicApi.getContractApplyAmountPageToBeExamineOne
break;
case 'ToBeExamineTwo':
fn = PublicApi.getContractApplyAmountPageToBeExamineTwo
break;
case 'pageToBeSubmit':
fn = PublicApi.getContractApplyAmountPageToBeSubmit
break;
// case '':
// fn = PublicApi.postContractApplyAmountExamineStepTwo
// break;
}
fn({
applyId,
...params
}).then(res => {
resolve(res.data)
})
})
}
/* 请款明细 */
const columns: ColumnType<any>[] = [{
title: '单据号/摘要',
dataIndex: type == 'pageDetailList' ? 'orderNO' : 'applyNo',
align: 'center',
render: (text, record) =>
<div>
<EyePreview
type="button"
>
{text}
</EyePreview>
<p>{type == 'pageDetailList' ? record.orderAbstract : record.applyAbstract}</p>
</div>
}, {
title: '单据类型',
dataIndex: 'orderTypeName',
align: 'center',
}, {
title: '单据状态',
dataIndex: 'orderTypeName',
align: 'center',
},
{
title: '单据时间',
dataIndex: 'orderTime',
align: 'center',
defaultSortOrder: 'descend',
},
{
title: isTitle('单据金额', '188999'),
dataIndex: 'orderAmount',
align: 'center',
},
{
title: '含税/税率',
dataIndex: 'isHasTaxName',
align: 'center',
},
{
title: isTitle('已付款', '188999'),
dataIndex: 'payAmount',
align: 'center',
},
{
title: isTitle('已请款待付款', '188999'),
dataIndex: 'unPayApplyAmount',
align: 'center',
},
{
title: isTitle('请款金额', '18000'),
dataIndex: 'applyAmount',
align: 'center',
}]
return (
<div className='ant-card-body'>
<StandardTable
tableProps={{
rowKey: 'id',
}}
columns={columns}
currentRef={ref}
fetchTableData={(params: any) => fetchData(params)}
formilyProps={{
ctx: {
inline: false,
effects: ($, actions) => {
useStateFilterSearchLinkageEffect(
$,
actions,
'orderNo',
FORM_FILTER_PATH,
);
},
components: {
DateRangePickerUnix,
Submit
}
}
}}
/>
</div>
)
}
export default Materials;
......@@ -5,14 +5,15 @@ import style from './index.less';
import { ArrowLeftOutlined } from '@ant-design/icons';
import { StandardTable } from 'god';
import { ColumnType } from 'antd/lib/table/interface';
import EyePreview from '@/components/EyePreview'
import statuStyle from '../../common/colorTag'
import { history } from 'umi';
import { useStateFilterSearchLinkageEffect } from '@/formSchema/effects/useFilterSearch'
import Submit from '@/components/NiceForm/components/Submit'
import { FORM_FILTER_PATH } from '@/formSchema/const'
import { PublicApi } from '@/services/api';
import DateRangePickerUnix from '@/components/NiceForm/components/DateRangePickerUnix'
import Examine from '../components/examine'
import Materials from './components/materials'
const { Link } = Anchor;
const { Step } = Steps;
......@@ -36,6 +37,7 @@ const BillDetails = (props: any) => {
const [applyAbstract, setapplyAbstract] = useState('');
const [reason, setDatareason] = useState('');
const [status, setstatus] = useState<any>()
const [ExamineFlag, setExamineFlag] = useState<boolean>(false);
useEffect(() => {
setTargetOffset(window.innerHeight / 6);
}, []);
......@@ -101,6 +103,17 @@ const BillDetails = (props: any) => {
}
})
}
/* 提交审核的回调 */
const getfetchData = (data) => {
console.log(data)
setExamineFlag(data.ExamineFlag)
if (data.code === 1000) {
setTimeout(() => {
history.goBack()
}, 2000)
}
}
/* 作废 */
const oninvalid = () => {
let res_data: any = {
......@@ -141,69 +154,8 @@ const BillDetails = (props: any) => {
// fetchListData(data)
}, []);
const isTitle = (title, Price) => {
return (
<div className="a">
<div>{title}</div>
<div>合计金额:¥{Price}</div>
</div>
)
}
/* 请款明细 */
const columns: ColumnType<any>[] = [{
title: '单据号/摘要',
dataIndex: 'orderNO',
align: 'center',
render: (text, record) =>
<div>
<EyePreview
type="button"
>
{text}
</EyePreview>
<p>{record.orderAbstract}</p>
</div>
}, {
title: '单据类型',
dataIndex: 'orderTypeName',
align: 'center',
}, {
title: '单据状态',
dataIndex: 'orderTypeName',
align: 'center',
},
{
title: '单据时间',
dataIndex: 'orderTime',
align: 'center',
defaultSortOrder: 'descend',
},
{
title: isTitle('单据金额', '188999'),
dataIndex: 'orderAmount',
align: 'center',
},
{
title: '含税/税率',
dataIndex: 'isHasTaxName',
align: 'center',
},
{
title: isTitle('已付款', '188999'),
dataIndex: 'payAmount',
align: 'center',
},
{
title: isTitle('已请款待付款', '188999'),
dataIndex: 'unPayApplyAmount',
align: 'center',
},
{
title: isTitle('请款金额', '18000'),
dataIndex: 'applyAmount',
align: 'center',
}]
/* 操作人 */
const columnsList: ColumnType<any>[] = [{
title: '序号',
......@@ -250,18 +202,7 @@ const BillDetails = (props: any) => {
},
]
// 列表数据
const fetchData = (params?: any) => {
console.log(params)//可以直接打印参数
return new Promise((resolve, reject) => {
PublicApi.getContractApplyAmountPageDetailList({
applyId,
...params
}).then(res => {
resolve(res.data)
})
})
}
// 流转记录
const fetListData = (params: any) => {
return new Promise((resolve, reject) => {
......@@ -320,7 +261,7 @@ const BillDetails = (props: any) => {
</div>
<div>
{
type == 1 || status != 9 || status != 7 || status != 8 || status != 1 && <Button type="primary" style={{ width: 80, marginRight: 16 }} onClick={() => setIsModalVisible(!isModalVisible)}>单据作废 </Button>
status == 1 && <Button type="primary" style={{ width: 80, marginRight: 16 }} onClick={() => setExamineFlag(!ExamineFlag)}>单据审核 </Button>
}
</div>
......@@ -401,34 +342,7 @@ const BillDetails = (props: any) => {
</div>
</div>
</div>
<div className='ant-card-body'>
<StandardTable
tableProps={{
rowKey: 'id',
}}
columns={columns}
currentRef={ref}
fetchTableData={(params: any) => fetchData(params)}
formilyProps={{
ctx: {
inline: false,
effects: ($, actions) => {
useStateFilterSearchLinkageEffect(
$,
actions,
'orderNo',
FORM_FILTER_PATH,
);
},
components: {
DateRangePickerUnix,
Submit
}
}
}}
/>
</div>
<Materials applyId={applyId} type={type} />
</div>
{/* 流转记录 */}
<div id='record' className='ant-card ant-card-bordered'>
......@@ -482,6 +396,13 @@ const BillDetails = (props: any) => {
<p style={{ padding: 10, margin: 0 }}>单据作废原因 <span style={{ color: 'red' }}>*</span></p>
<TextArea placeholder="在此输入你的原因,最多60个汉字" maxLength={120} onChange={(e) => setreason(e)} />
</Modal>
{/* 审核组建 */}
<Examine
ExamineFlag={ExamineFlag}
getfetchData={getfetchData}
applyId={applyId}
type="submitExamine"
/>
</div>
)
}
......
import React, { useState, useRef, ReactNode } from 'react'
import { history, Link } from 'umi';
import { PageHeaderWrapper } from '@ant-design/pro-layout';
import { Anchor, Radio, Steps, Row, Col, Input, message, Modal, Card } from 'antd';
import statuStyle from '../../common/colorTag'
import { Card } from 'antd';
import { SchemaBli } from '../schema';
import { ColumnType } from 'antd/lib/table/interface';
import { StandardTable } from 'god';
import { SchemaBli } from '../schema';
import EyePreview from '@/components/EyePreview';
import { PublicApi } from '@/services/api'
import { useStateFilterSearchLinkageEffect } from '@/formSchema/effects/useFilterSearch'
import EyePreview from '@/components/EyePreview';
import { useAsyncSelect } from '@/formSchema/effects/useAsyncSelect';
import { PublicApi } from '@/services/api'
import { FORM_FILTER_PATH } from '@/formSchema/const'
import Submit from '@/components/NiceForm/components/Submit'
import SearchSelect from '@/components/NiceForm/components/SearchSelect'
import DateRangePickerUnix from '@/components/NiceForm/components/DateRangePickerUnix'
import moment from 'moment';
import Examine from '../components/examine'
import "../../constants/index.less"
const { TextArea } = Input;
const Levelpayment: React.FC<{}> = () => {
const ref = useRef<any>({});
const [ExamineFlag, setExamineFlag] = useState<boolean>(false);
const [applyId, setapplyId] = useState('');
const [selectedRowKeys, setSelectedRowKeys] = useState<Array<string>>([])
const [selectRow, setSelectRow] = useState<any[]>([]) // 模态框选择的行数据
const [id, setId] = useState('');
const [isModalVisible, setIsModalVisible] = useState(false);
const today = moment(); // 当天日期
const [isAllMember, setIsAllMember] = useState(true)
const [reason, setDatareason] = useState('')
;
//表头
const columns: ColumnType<any>[] = [{
title: '请款单号/摘要',
dataIndex: 'applyNo',
align: 'center',
render: (text: any, record: any) => {
return (
<div>
<EyePreview
type="button"
// url={`/memberCenter/contract/funds/levelpayment/Details?applyId=${record.id}&type=PageToBeExamineOne`}
url={`/memberCenter/contract/funds/addbill/Details?applyId=${record.id}&type=PageToBeExamineOne`}
>
{text}
</EyePreview>
......@@ -46,77 +43,60 @@ const Levelpayment: React.FC<{}> = () => {
},
}, {
title: '单据时间',
align: 'center',
dataIndex: 'orderTime',
}, {
title: '收款方',
align: 'center',
dataIndex: 'payeeMemberName',
},
{
title: '合同编号',
align: 'center',
dataIndex: 'contractNo',
render: (text: any, record: any) => <EyePreview
type="button"
// type="button"
url={`/memberCenter/contract/manage/QueryList/QueryListdetails?contractId=${record.contractId}`}
>
{text}
</EyePreview>
},
{
title: '合同总金额',
align: 'center',
dataIndex: 'contractAmount',
render: (text: any, record: any) =>
<span>{text}</span>
<p>{text}</p>
},
{
title: '请款金额',
dataIndex: 'applyAmount',
align: 'center',
render: (text: any, record: any) =>
<span>{text}</span>
<p>{text}</p>
},
{
title: '内部状态',
dataIndex: 'statusName',
align: 'center',
render: (text: any, record: any) => {
let component: ReactNode = null
component = (
<>
<span style={statuStyle.success}>已完成签约</span>
</>
)
return component
}
render: (text: any, record: any) =>
<div style={{ display: 'flex', alignItems: 'center' }}>
<span style={{ marginRight: 10, background: '#FFC400', display: "inline-block", width: '6px', height: '6px', borderRadius: '50%' }}></span>
<span>{text}</span>
</div>
}, {
title: '操作',
dataIndex: 'action',
align: 'center',
render: (text: any, record: any) => {
// 作废:待付款、已付款、待提交审核状态的不能作废
return (
<>
{
record.status != 9 || record.status != 7 || record.status != 8 || record.status != 1 && <span style={{ color: '#00B37A', marginRight: 20, cursor: 'pointer', }} onClick={() => invalid(record.id)}>作废</span>
}
<span style={{ color: '#00B37A', marginRight: 20, cursor: 'pointer', }} onClick={() => history.push(`/memberCenter/contract/funds/bill/details?applyId=${record.id}&type=1`)}>查看</span>
<span style={{ color: '#00B37A', marginRight: 20, cursor: 'pointer', }} onClick={() => isModal(record)}>审核</span>
</>
)
}
}]
const handleIsAllMemberChange = (v: any) => {
setIsAllMember(v.target.value)
}
const invalid = (id) => {
setId(id)
setIsModalVisible(!isModalVisible)
const isModal = (record) => {
setExamineFlag(!ExamineFlag)
setapplyId(record.id)
}
// 模拟请求
const fetchData = (params?: any) => {
......@@ -125,7 +105,7 @@ const Levelpayment: React.FC<{}> = () => {
params.startTime = params.startTime ? moment().format('YYYY-MM-DD') : '';
params.endTime = params.endTime ? moment().format('YYYY-MM-DD') : '';
return new Promise((resolve, reject) => {
PublicApi.getContractApplyAmountPageList({
PublicApi.getContractApplyAmountPageToBeExamineOne({
...params,
}).then(res => {
resolve(res.data)
......@@ -133,13 +113,13 @@ const Levelpayment: React.FC<{}> = () => {
})
}
const fetchOptions = (service) => {
return async function () {
const res = await service();
if (res.code === 1000) {
return res.data.map((item) => { return { label: item.name, value: item.status } })
}
return [];
/* 提交审核的回调 */
const getfetchData = (data) => {
console.log(data)
setExamineFlag(data.ExamineFlag)
if (data.code === 1000) {
ref.current.reload()
}
}
const rowSelection: any = {
......@@ -149,37 +129,15 @@ const Levelpayment: React.FC<{}> = () => {
setSelectRow(selectedRows)
}
};
/* 作废 */
const oninvalid = () => {
let res_data: any = {
applyId: id,
reason,
}
if (isAllMember) {
const msg = message.loading({
content: '正在操作',
duration: 0,
});
PublicApi.postContractApplyAmountInvalid(res_data).then(res => {
if (res.code === 1000) {
handleCancel()
ref.current.reload();
}
}).finally(() => {
msg();
})
} else {
handleCancel()
const fetchOptions = (service) => {
return async function () {
const res = await service();
if (res.code === 1000) {
return res.data.map((item) => { return { label: item.name, value: item.status } })
}
return [];
}
}
const setreason = (e) => {
setDatareason(e.target.value);
}
const handleCancel = () => {
setIsModalVisible(!isModalVisible);
};
return (
<PageHeaderWrapper>
<Card>
......@@ -216,14 +174,12 @@ const Levelpayment: React.FC<{}> = () => {
}}
/>
</Card>
<Modal title="单据作废" visible={isModalVisible} onCancel={handleCancel} onOk={oninvalid}>
<Radio.Group onChange={handleIsAllMemberChange} defaultValue={isAllMember} value={isAllMember}>
<Radio value={true}>作废</Radio>
<Radio value={false}>不作废</Radio>
</Radio.Group>
<p style={{ padding: 10, margin: 0 }}>单据作废原因 <span style={{ color: 'red' }}>*</span></p>
<TextArea placeholder="在此输入你的原因,最多60个汉字" maxLength={120} onChange={(e) => setreason(e)} />
</Modal>
<Examine
ExamineFlag={ExamineFlag}
getfetchData={getfetchData}
applyId={applyId}
type="PageToBeExamineOne"
/>
</PageHeaderWrapper>
)
......
......@@ -69,3 +69,65 @@ export const SchemaBli: any = {
},
}
}
export const addSchemaBli: ISchema = {
type: 'object',
properties: {
applyNo: {
type: 'string',
"x-component": 'SearchFilter',
'x-component-props': {
placeholder: '请输入请款编号',
align: 'flex-end',
},
},
[FORM_FILTER_PATH]: {
type: 'object',
'x-component': 'flex-layout',
'x-component-props': {
inline: true,
colStyle: {
marginLeft: 20
}
},
properties: {
"applyAbstract": {
type: 'string',
"x-component-props": {
placeholder: '请输入请款摘要'
}
},
"payeeMemberName": {
type: 'string',
"x-component-props": {
placeholder: '请输入收款方'
}
},
"[startTime,endTime]": {
type: 'array',
"x-component": 'DateRangePickerUnix',
'x-component-props': {
placeholder: ['开始时间', '结束时间'],
disabledDate: current => {
// return current && current < moment().startOf('day')
}
},
},
status: {
type: 'string',
enum: [],
"x-component-props": {
placeholder: '请选择内部状态'
},
title: '请选择外部状态',
},
submit: {
'x-component': 'Submit',
'x-component-props': {
children: '查询',
},
},
},
},
}
}
import React, { useState, useRef, ReactNode } from 'react'
import { history, Link } from 'umi';
import { PageHeaderWrapper } from '@ant-design/pro-layout';
import { Anchor, Radio, Steps, Row, Col, Input, message, Modal, Card } from 'antd';
import statuStyle from '../../common/colorTag'
import { Card } from 'antd';
import { SchemaBli } from '../schema';
import { ColumnType } from 'antd/lib/table/interface';
import { StandardTable } from 'god';
import { SchemaBli } from '../schema';
import EyePreview from '@/components/EyePreview';
import { PublicApi } from '@/services/api'
import { useStateFilterSearchLinkageEffect } from '@/formSchema/effects/useFilterSearch'
import EyePreview from '@/components/EyePreview';
import { useAsyncSelect } from '@/formSchema/effects/useAsyncSelect';
import { PublicApi } from '@/services/api'
import { FORM_FILTER_PATH } from '@/formSchema/const'
import Submit from '@/components/NiceForm/components/Submit'
import SearchSelect from '@/components/NiceForm/components/SearchSelect'
import DateRangePickerUnix from '@/components/NiceForm/components/DateRangePickerUnix'
import moment from 'moment';
import Examine from '../components/examine'
import "../../constants/index.less"
const { TextArea } = Input;
const Secondpayment: React.FC<{}> = () => {
const ref = useRef<any>({});
const [ExamineFlag, setExamineFlag] = useState<boolean>(false);
const [applyId, setapplyId] = useState('');
const [selectedRowKeys, setSelectedRowKeys] = useState<Array<string>>([])
const [selectRow, setSelectRow] = useState<any[]>([]) // 模态框选择的行数据
const [id, setId] = useState('');
const [isModalVisible, setIsModalVisible] = useState(false);
const today = moment(); // 当天日期
const [isAllMember, setIsAllMember] = useState(true)
const [reason, setDatareason] = useState('')
;
//表头
const columns: ColumnType<any>[] = [{
title: '请款单号/摘要',
dataIndex: 'applyNo',
align: 'center',
render: (text: any, record: any) => {
return (
<div>
<EyePreview
type="button"
url={`/memberCenter/contract/funds/addbill/Details?applyId=${record.id}&type=ToBeExamineTwo`}
>
{text}
</EyePreview>
......@@ -46,77 +42,59 @@ const Secondpayment: React.FC<{}> = () => {
},
}, {
title: '单据时间',
align: 'center',
dataIndex: 'orderTime',
}, {
title: '收款方',
align: 'center',
dataIndex: 'payeeMemberName',
},
{
title: '合同编号',
align: 'center',
dataIndex: 'contractNo',
render: (text: any, record: any) => <EyePreview
type="button"
// type="button"
url={`/memberCenter/contract/manage/QueryList/QueryListdetails?contractId=${record.contractId}`}
>
{text}
</EyePreview>
},
{
title: '合同总金额',
align: 'center',
dataIndex: 'contractAmount',
render: (text: any, record: any) =>
<span>{text}</span>
<p>{text}</p>
},
{
title: '请款金额',
dataIndex: 'applyAmount',
align: 'center',
render: (text: any, record: any) =>
<span>{text}</span>
<p>{text}</p>
},
{
title: '内部状态',
dataIndex: 'statusName',
align: 'center',
render: (text: any, record: any) => {
let component: ReactNode = null
component = (
<>
<span style={statuStyle.success}>已完成签约</span>
</>
)
return component
}
render: (text: any, record: any) =>
<div style={{ display: 'flex', alignItems: 'center' }}>
<span style={{ marginRight: 10, background: '#FFC400', display: "inline-block", width: '6px', height: '6px', borderRadius: '50%' }}></span>
<span>{text}</span>
</div>
}, {
title: '操作',
dataIndex: 'action',
align: 'center',
render: (text: any, record: any) => {
// 作废:待付款、已付款、待提交审核状态的不能作废
return (
<>
{
record.status != 9 || record.status != 7 || record.status != 8 || record.status != 1 && <span style={{ color: '#00B37A', marginRight: 20, cursor: 'pointer', }} onClick={() => invalid(record.id)}>作废</span>
}
<span style={{ color: '#00B37A', marginRight: 20, cursor: 'pointer', }} onClick={() => history.push(`/memberCenter/contract/funds/bill/details?applyId=${record.id}&type=1`)}>查看</span>
<span style={{ color: '#00B37A', marginRight: 20, cursor: 'pointer', }} onClick={() => isModal(record)}>审核</span>
</>
)
}
}]
const handleIsAllMemberChange = (v: any) => {
setIsAllMember(v.target.value)
}
const invalid = (id) => {
setId(id)
setIsModalVisible(!isModalVisible)
const isModal = (record) => {
setExamineFlag(!ExamineFlag)
setapplyId(record.id)
}
// 模拟请求
const fetchData = (params?: any) => {
......@@ -125,7 +103,7 @@ const Secondpayment: React.FC<{}> = () => {
params.startTime = params.startTime ? moment().format('YYYY-MM-DD') : '';
params.endTime = params.endTime ? moment().format('YYYY-MM-DD') : '';
return new Promise((resolve, reject) => {
PublicApi.getContractApplyAmountPageList({
PublicApi.getContractApplyAmountPageToBeExamineTwo({
...params,
}).then(res => {
resolve(res.data)
......@@ -142,6 +120,15 @@ const Secondpayment: React.FC<{}> = () => {
return [];
}
}
/* 提交审核的回调 */
const getfetchData = (data) => {
console.log(data)
setExamineFlag(data.ExamineFlag)
if (data.code === 1000) {
ref.current.reload()
}
}
const rowSelection: any = {
selectedRowKeys: selectedRowKeys,
onChange: (selectedRowKeys: any, selectedRows: any) => {
......@@ -149,37 +136,6 @@ const Secondpayment: React.FC<{}> = () => {
setSelectRow(selectedRows)
}
};
/* 作废 */
const oninvalid = () => {
let res_data: any = {
applyId: id,
reason,
}
if (isAllMember) {
const msg = message.loading({
content: '正在操作',
duration: 0,
});
PublicApi.postContractApplyAmountInvalid(res_data).then(res => {
if (res.code === 1000) {
handleCancel()
ref.current.reload();
}
}).finally(() => {
msg();
})
} else {
handleCancel()
}
}
const setreason = (e) => {
setDatareason(e.target.value);
}
const handleCancel = () => {
setIsModalVisible(!isModalVisible);
};
return (
<PageHeaderWrapper>
<Card>
......@@ -216,14 +172,12 @@ const Secondpayment: React.FC<{}> = () => {
}}
/>
</Card>
<Modal title="单据作废" visible={isModalVisible} onCancel={handleCancel} onOk={oninvalid}>
<Radio.Group onChange={handleIsAllMemberChange} defaultValue={isAllMember} value={isAllMember}>
<Radio value={true}>作废</Radio>
<Radio value={false}>不作废</Radio>
</Radio.Group>
<p style={{ padding: 10, margin: 0 }}>单据作废原因 <span style={{ color: 'red' }}>*</span></p>
<TextArea placeholder="在此输入你的原因,最多60个汉字" maxLength={120} onChange={(e) => setreason(e)} />
</Modal>
<Examine
ExamineFlag={ExamineFlag}
getfetchData={getfetchData}
applyId={applyId}
type="ToBeExamineTwo"
/>
</PageHeaderWrapper>
)
......
import React, { useState, useRef, ReactNode } from 'react'
import { history, Link } from 'umi';
import { PageHeaderWrapper } from '@ant-design/pro-layout';
import { Anchor, Radio, Steps, Row, Col, Input, message, Modal, Card } from 'antd';
import statuStyle from '../../common/colorTag'
import { Card, message } from 'antd';
import { SchemaBli } from '../schema';
import { ColumnType } from 'antd/lib/table/interface';
import { StandardTable } from 'god';
import { SchemaBli } from '../schema';
import EyePreview from '@/components/EyePreview';
import { PublicApi } from '@/services/api'
import { useStateFilterSearchLinkageEffect } from '@/formSchema/effects/useFilterSearch'
import EyePreview from '@/components/EyePreview';
import { useAsyncSelect } from '@/formSchema/effects/useAsyncSelect';
import { PublicApi } from '@/services/api'
import { FORM_FILTER_PATH } from '@/formSchema/const'
import Submit from '@/components/NiceForm/components/Submit'
import SearchSelect from '@/components/NiceForm/components/SearchSelect'
import DateRangePickerUnix from '@/components/NiceForm/components/DateRangePickerUnix'
import moment from 'moment';
import Examine from '../components/examine'
import "../../constants/index.less"
const { TextArea } = Input;
const Submitpayment: React.FC<{}> = () => {
const ref = useRef<any>({});
const [ExamineFlag, setExamineFlag] = useState<boolean>(false);
const [applyId, setapplyId] = useState('');
const [selectedRowKeys, setSelectedRowKeys] = useState<Array<string>>([])
const [selectRow, setSelectRow] = useState<any[]>([]) // 模态框选择的行数据
const [id, setId] = useState('');
const [isModalVisible, setIsModalVisible] = useState(false);
const today = moment(); // 当天日期
const [isAllMember, setIsAllMember] = useState(true)
const [reason, setDatareason] = useState('')
;
//表头
const columns: ColumnType<any>[] = [{
title: '请款单号/摘要',
dataIndex: 'applyNo',
align: 'center',
render: (text: any, record: any) => {
return (
<div>
<EyePreview
type="button"
url={`/memberCenter/contract/funds/addbill/Details?applyId=${record.id}&type=pageToBeSubmit`}
>
{text}
</EyePreview>
......@@ -46,77 +41,72 @@ const Submitpayment: React.FC<{}> = () => {
},
}, {
title: '单据时间',
align: 'center',
dataIndex: 'orderTime',
}, {
title: '收款方',
align: 'center',
dataIndex: 'payeeMemberName',
},
{
title: '合同编号',
align: 'center',
dataIndex: 'contractNo',
render: (text: any, record: any) => <EyePreview
type="button"
// type="button"
url={`/memberCenter/contract/manage/QueryList/QueryListdetails?contractId=${record.contractId}`}
>
{text}
</EyePreview>
},
{
title: '合同总金额',
align: 'center',
dataIndex: 'contractAmount',
render: (text: any, record: any) =>
<span>{text}</span>
<p>{text}</p>
},
{
title: '请款金额',
dataIndex: 'applyAmount',
align: 'center',
render: (text: any, record: any) =>
<span>{text}</span>
<p>{text}</p>
},
{
title: '内部状态',
dataIndex: 'statusName',
align: 'center',
render: (text: any, record: any) => {
let component: ReactNode = null
component = (
<>
<span style={statuStyle.success}>已完成签约</span>
</>
)
return component
}
render: (text: any, record: any) =>
<div style={{ display: 'flex', alignItems: 'center' }}>
<span style={{ marginRight: 10, background: '#C0C4CC', display: "inline-block", width: '6px', height: '6px', borderRadius: '50%' }}></span>
<span>{text}</span>
</div>
}, {
title: '操作',
dataIndex: 'action',
align: 'center',
render: (text: any, record: any) => {
// 作废:待付款、已付款、待提交审核状态的不能作废
return (
<>
{
record.status != 9 || record.status != 7 || record.status != 8 || record.status != 1 && <span style={{ color: '#00B37A', marginRight: 20, cursor: 'pointer', }} onClick={() => invalid(record.id)}>作废</span>
}
<span style={{ color: '#00B37A', marginRight: 20, cursor: 'pointer', }} onClick={() => history.push(`/memberCenter/contract/funds/bill/details?applyId=${record.id}&type=1`)}>查看</span>
<span style={{ color: '#00B37A', marginRight: 20, cursor: 'pointer', }} onClick={() => ApplyAmountSubmit(record.id)}>提交请款单</span>
</>
)
}
}]
const handleIsAllMemberChange = (v: any) => {
setIsAllMember(v.target.value)
}
const invalid = (id) => {
setId(id)
setIsModalVisible(!isModalVisible)
const ApplyAmountSubmit = (applyId) => {
const msg = message.loading({
content: '正在操作',
duration: 0,
});
PublicApi.postContractApplyAmountSubmit({ applyId }).then(res => {
console.log(res);
if (res.code === 1000) {
getfetchData({
ExamineFlag: false,
code: 1000
})
}
}).finally(() => {
msg();
});
}
// 模拟请求
const fetchData = (params?: any) => {
......@@ -125,7 +115,7 @@ const Submitpayment: React.FC<{}> = () => {
params.startTime = params.startTime ? moment().format('YYYY-MM-DD') : '';
params.endTime = params.endTime ? moment().format('YYYY-MM-DD') : '';
return new Promise((resolve, reject) => {
PublicApi.getContractApplyAmountPageList({
PublicApi.getContractApplyAmountPageToBeSubmit({
...params,
}).then(res => {
resolve(res.data)
......@@ -133,13 +123,13 @@ const Submitpayment: React.FC<{}> = () => {
})
}
const fetchOptions = (service) => {
return async function () {
const res = await service();
if (res.code === 1000) {
return res.data.map((item) => { return { label: item.name, value: item.status } })
}
return [];
/* 提交审核的回调 */
const getfetchData = (data) => {
console.log(data)
setExamineFlag(data.ExamineFlag)
if (data.code === 1000) {
ref.current.reload()
}
}
const rowSelection: any = {
......@@ -149,37 +139,15 @@ const Submitpayment: React.FC<{}> = () => {
setSelectRow(selectedRows)
}
};
/* 作废 */
const oninvalid = () => {
let res_data: any = {
applyId: id,
reason,
}
if (isAllMember) {
const msg = message.loading({
content: '正在操作',
duration: 0,
});
PublicApi.postContractApplyAmountInvalid(res_data).then(res => {
if (res.code === 1000) {
handleCancel()
ref.current.reload();
}
}).finally(() => {
msg();
})
} else {
handleCancel()
const fetchOptions = (service) => {
return async function () {
const res = await service();
if (res.code === 1000) {
return res.data.map((item) => { return { label: item.name, value: item.status } })
}
return [];
}
}
const setreason = (e) => {
setDatareason(e.target.value);
}
const handleCancel = () => {
setIsModalVisible(!isModalVisible);
};
return (
<PageHeaderWrapper>
<Card>
......@@ -216,14 +184,12 @@ const Submitpayment: React.FC<{}> = () => {
}}
/>
</Card>
<Modal title="单据作废" visible={isModalVisible} onCancel={handleCancel} onOk={oninvalid}>
<Radio.Group onChange={handleIsAllMemberChange} defaultValue={isAllMember} value={isAllMember}>
<Radio value={true}>作废</Radio>
<Radio value={false}>不作废</Radio>
</Radio.Group>
<p style={{ padding: 10, margin: 0 }}>单据作废原因 <span style={{ color: 'red' }}>*</span></p>
<TextArea placeholder="在此输入你的原因,最多60个汉字" maxLength={120} onChange={(e) => setreason(e)} />
</Modal>
<Examine
ExamineFlag={ExamineFlag}
getfetchData={getfetchData}
applyId={applyId}
type="PageToBeSubmit"
/>
</PageHeaderWrapper>
)
......
......@@ -17,6 +17,7 @@ import DateRangePickerUnix from '@/components/NiceForm/components/DateRangePicke
import { PublicApi } from '@/services/api';
import { PlusCircleOutlined, PlayCircleOutlined, PoweroffOutlined } from '@ant-design/icons'
import moment from 'moment';
import '../../constants/index.less'
const addList = () => {
const ref = useRef<any>({});
......@@ -136,7 +137,7 @@ const addList = () => {
return (
<div>
{
record.innerStatus == '1' || record.outerStatus == '1' || record.outerStatus == '3' || record.outerStatus == '5' ? <span style={{ color: '#00B37A', cursor: 'pointer', marginRight: 10 }}>修改</span> : ''
record.innerStatus == '1' || record.outerStatus == '1' || record.outerStatus == '3' || record.outerStatus == '5' ? <span style={{ color: '#00B37A', cursor: 'pointer', marginRight: 10 }} onClick={() => edit(record)}>修改</span> : ''
}
{/* 只有内部状态为待提交乙方签订合同状态且从未提交过的才可以删除,删除前需要提示,确认后才能删除 */}
{
......@@ -147,6 +148,19 @@ const addList = () => {
)
}
}]
/* 修改 */
const edit = (record) => {
// record.sourceId = record.sourceId;
// record.sourceNo = record.sourceNo;
// record.totalAmount = record.totalAmount;
// record.partyBMemberId = record.partyBMemberId;
// record.partyBRoleId = record.partyARoleId;
// record.partyBName = record.partyBName;
// sessionStorage.setItem('record', JSON.stringify(record));
history.push(`/memberCenter/contract/manage/add/addList/contracAdd?sourceType=${record.sourceType}&id=${record.id}`)
}
/* 提交审核 */
const submit = (id) => {
const msg = message.loading({
......@@ -192,6 +206,9 @@ const addList = () => {
currentRef={ref}
rowSelection={rowSelection}
fetchTableData={(params: any) => fetchData(params)}
formilyLayouts={{
justify: 'space-between'
}}
formilyProps={{
ctx: {
inline: false,
......@@ -211,7 +228,7 @@ const addList = () => {
},
layouts: {
order: 2,
span: 24
span: 16
}
}}
formilyChilds={{
......
......@@ -54,13 +54,20 @@ const FormList = (props: any) => {
dataIndex: 'purchaseCount',
key: 'purchaseCount',
align: 'center',
render: (_, record, index) => <Input
style={{
width: 120,
}}
placeholder=""
onChange={(e) => setInput(e, 'purchaseCount', index)}
/>
render: (text, record, index) =>
<Form.Item
name={`isHasTax${index}`}
initialValue={text + index}
rules={[{ required: true, message: '请选择' }]}
>
<Input
style={{
width: 120,
}}
placeholder=""
onChange={(e) => setInput(e, 'purchaseCount', index)}
/>
</Form.Item>
},
{
title: '含税', dataIndex: 'isHasTax', align: 'center',
......@@ -68,7 +75,7 @@ const FormList = (props: any) => {
<Form.Item
name={`isHasTax${index}`}
initialValue={text}
initialValue={text + index}
rules={[{ required: true, message: '请选择' }]}
>
<Select
......
......@@ -26,7 +26,7 @@ const PurchaseList = () => {
render: (text, record) =>
<div>
<EyePreview
type="button"
url={`/memberCenter/procurementAbility/offter/view?id=${record.demandId}&number=${record.demandNO}`}
>
{text}
</EyePreview>
......@@ -102,7 +102,7 @@ const PurchaseList = () => {
return (
<div>
<span style={{ color: '#00B37A', cursor: 'pointer', marginRight: 10 }} onClick={() => like(record)}>创建采购询价合同</span>
<span style={{ color: '#00B37A', cursor: 'pointer' }} onClick={() => history.push(`/memberCenter/contract/manage/purchase/details?contractId=${record.id}`)}>查看</span>
{/* <span style={{ color: '#00B37A', cursor: 'pointer' }} onClick={() => history.push(`/memberCenter/contract/manage/purchase/details?contractId=${record.id}`)}>查看</span> */}
</div>
)
}
......@@ -126,7 +126,7 @@ const PurchaseList = () => {
record.partyBRoleId = record.awardRoleId;
record.partyBName = record.awardName;
sessionStorage.setItem('record', JSON.stringify(record));
history.push(`/memberCenter/contract/manage/add/addList/contracAdd?contractId=${record.id}&sourceType=1`)
history.push(`/memberCenter/contract/manage/add/addList/contracAdd?contractId=${record.id}&type=list`)
};
// 列表数据
const fetchData = (params?: any) => {
......@@ -169,7 +169,8 @@ const PurchaseList = () => {
DateRangePickerUnix,
Submit
}
}
},
}}
/>
</Card>
......
......@@ -19,11 +19,12 @@ export interface BidCommonLayoutProps {
layoutId: string,
title: string,
layoutType?: string,
extra?: React.ReactNode
extra?: React.ReactNode,
checkDetailFunc?: Function
}
const BidCommonLayout: React.FC<BidCommonLayoutProps> = (props: any) => {
const { layoutId, title, effect, layoutType, extra } = props;
const { layoutId, title, effect, layoutType, extra, checkDetailFunc } = props;
const _returnChild = (child, key) => {
if (child.type === 'text') {
return (
......@@ -61,7 +62,7 @@ const BidCommonLayout: React.FC<BidCommonLayoutProps> = (props: any) => {
<Row gutter={[8, 8]}>
{effect.map((item, index) => (
<Col span={5} key={`effect_result_${index}`}>
<ResultItem itemIndex={index} />
<ResultItem itemIndex={index} checkDetailFunc={checkDetailFunc} />
</Col>
))}
</Row>
......
......@@ -20,15 +20,16 @@
}
.badge {
width: 16px;
height: 16px;
width: 24px;
height: 24px;
background: #EBECF0;
border-radius: 8px;
border-radius: 12px;
text-align: center;
line-height: 16px;
line-height: 24px;
color: #909399;
font-size: 12px;
margin-right: 4px;
margin-left: 4px;
display: inline-block;
}
.title {
......@@ -40,6 +41,9 @@
white-space: nowrap;
word-break: break-all;
}
.label{
width: 40%;
}
}
}
......@@ -5,28 +5,24 @@ import styles from './index.less';
export interface ResultItemPrpos {
itemIndex: number,
detail?: any
detail?: any,
checkDetailFunc? : Function
}
const ResultItem: React.FC<ResultItemPrpos> = (props: any) => {
const { itemIndex, detial } = props;
const { itemIndex, detial, checkDetailFunc } = props;
return (
<div key={`msgItem_key_${itemIndex}`} className={styles.resultItem}>
<div className={styles.resultItemRow}>
<div className={styles.title}>广州白马皮具交易中心</div>
<div className={styles.badge}>1</div>
<div className={styles.title}>广州白马皮具交易中心<div className={styles.badge}>1</div></div>
</div>
<div className={styles.resultItemRow}>
<div className={styles.money}>¥900.00<span>(含税)</span></div>
<Button
type='link'
>
查看报价明细
</Button>
<Button type='link' onClick={checkDetailFunc}>查看报价明细</Button>
</div>
<Divider dashed style={{color: '#EBECF0',margin: '6px 0' }} />
<div className={styles.resultItemRow}>联系人姓名:<div className={styles.title}>小王</div></div>
<div className={styles.resultItemRow}>联系人手机:<div className={styles.title}>185 2929 6758</div></div>
<Divider dashed style={{ color: '#EBECF0', margin: '6px 0' }} />
<div className={styles.resultItemRow}><div className={styles.label}>联系人姓名:</div><div className={styles.title}>小王</div></div>
<div className={styles.resultItemRow}><div className={styles.label}>联系人手机:</div><div className={styles.title}>185 2929 6758</div></div>
</div>
)
}
......
.btnItem {
border: 1px solid #F4F5F7;
padding: 16px 12px;
font-size: 12px;
cursor: pointer;
.btnItemTitle {
display: flex;
flex-direction: row;
color: #909399;
margin-bottom: 16px;
div {
flex: 1;
color: #303133;
}
}
.btnItemPrice {
color: #303133;
display: flex;
flex-direction: row;
div {
flex: 1;
font-size: 16px;
span {
color: #909399;
}
}
}
}
import React, { useContext, useEffect, useState } from 'react';
import style from './index.less';
interface BtnItemProps {
btnType?: number,
active?: boolean
}
const BtnItem: React.FC<BtnItemProps> = (props: any) => {
const { btnType, active } = props;
const _returnBtn = () => {
if (btnType === 1) {
return (
<div className={style.btnItem} style={{borderColor: active ? '#00B37A' : '#F4F5F7'}}>
<div className={style.btnItemTitle}>
<div>广州白马皮具交易中心</div>
第2次</div>
<div className={style.btnItemPrice}>
<div>
¥900.00
<span>(含税)</span>
</div>
10:43:56
</div>
</div>
)
}
}
return (
_returnBtn()
)
}
BtnItem.defaultProps = {
btnType: 1
}
export default BtnItem;
\ No newline at end of file
import React, { useContext, useEffect, useState } from 'react';
import { Row, Col, Table, Button } from 'antd';
import Card from '../../../card';
import BtnItem from './btnItem';
const BidDetailLayout = () => {
const columns = [
{ title: '物料编号/名称', dataIndex: 'materielNo', align: 'center', },
{ title: '规格型号', dataIndex: 'type', align: 'center', },
{ title: '品类', dataIndex: 'category', align: 'center', },
{ title: '品牌', dataIndex: 'brand', align: 'center', },
{ title: '采购数量/单位', dataIndex: 'unit', align: 'center', },
{ title: '含税/税率', dataIndex: 'isHasTaxName', align: 'center', },
{ title: '单价(含税)', dataIndex: 'price', align: 'center', },
{ title: '金额(含税)', dataIndex: 'price', align: 'center', },
]
const dataSource = [
{
key: '1',
materielNo: 'Q89YTE1',
},
]
return (
<div style={{ width: '100%' }}>
<Card
id={'BidDetailLayout'}
title={'竞价详情'}
>
<Row gutter={[8, 8]}>
<Col span={7}>
<BtnItem />
</Col>
</Row>
{/* <Table dataSource={dataSource} columns={columns} />; */}
<Button type="link" block>显示更多</Button>
</Card>
</div>
)
}
export default BidDetailLayout
\ No newline at end of file
.iMBtn{
width: 24px;
height: 24px;
display: flex;
align-items: center;
justify-content: center;
cursor: pointer;
border-radius: 12px;
background-color: #E4F7EF;
img{
width: 16px;
}
}
\ No newline at end of file
import React, { useEffect, useState } from 'react';
import Icon from '@ant-design/icons';
import ImIcon from '@/assets/icons/message_square.svg';
import styles from './index.less';
interface IMBtnProps {
func: Function,
btnStyle?: React.CSSProperties
}
const IMBtn: React.FC<IMBtnProps> = (props: any) => {
const { func, btnStyle } = props;
return (
<div className={styles.iMBtn} style={btnStyle} onClick={func}>
<img src={ImIcon} alt="" />
</div>
)
}
IMBtn.defaultProps = {
btnStyle: {
marginLeft: '6px'
}
}
export default IMBtn
\ No newline at end of file
import React, { useState, useEffect } from 'react';
import { Chart, Tooltip, Axis } from 'bizcharts';
import Point from 'bizcharts/lib/geometry/Point';
import Line from 'bizcharts/lib/geometry/Line';
import Card from '../../../card';
interface QuotationDeskProps {
title?: string,
extra?: React.ReactNode
}
const data = [
{
year: "1991",
value: 3,
},
{
year: "1992",
value: 4,
},
{
year: "1993",
value: 3.5,
},
{
year: "1994",
value: 5,
},
{
year: "1995",
value: 4.9,
},
{
year: "1996",
value: 6,
},
{
year: "1997",
value: 7,
},
{
year: "1998",
value: 9,
},
{
year: "1999",
value: 13,
},
];
const QuotationDesk: React.FC<QuotationDeskProps> = (props: any) => {
const { title, extra } = props;
// const [data] = useState({
// year: "1991",
// value: 3,
// })
return (
<Card
id={'QuotationDesk'}
title={title}
extra={extra}
>
<Chart
appendPadding={[10, 0, 0, 10]}
autoFit
height={375}
data={data}
scale={{ value: { min: 0, alias: '', type: 'linear-strict' }, year: { range: [0, 1] } }}
>
<Axis
title={{text: '金额(元)'}}
// visible={false}
name='value'
// line={{ style: { stroke: "#ff0000" } }}
tickLine={{ style: { lineWidth: 1 }, length: 5 }}
/>
<Line position="year*value" />
<Point position="year*value" />
<Tooltip showCrosshairs />
</Chart>
</Card>
)
}
QuotationDesk.defaultProps = {
title: '报价台'
}
export default QuotationDesk;
\ No newline at end of file
.wrap{
:global{
.ant-modal-body {
padding-top: 0;
padding-left: 0;
padding-bottom: 0;
.ant-tabs-ink-bar{
left: 0;
}
.ant-tabs-content{
min-height: 300px;
}
}
}
}
import React, { useEffect } from 'react';
import { Modal, Tabs, Form, Checkbox, Input } from 'antd';
const { TabPane } = Tabs;
const { TextArea } = Input;
import styles from './index.less';
const ConfirmBidResultModal = (props: any) => {
const [form] = Form.useForm();
const { title, visible, onCancel } = props;
return (
<Modal
width={600}
title={title}
visible={visible}
onCancel={onCancel}
wrapClassName={styles.wrap}
// onOk={() => actions.submit()}
// afterClose={() => actions.reset()}
>
<Form
form={form}
>
<Tabs tabPosition='left'>
<TabPane tab="中标公示" key="1">
<Form.Item name="offer">
<Checkbox>发送中标公示</Checkbox>
</Form.Item>
<Form.Item name="offer">
<TextArea rows={3} maxLength={100} placeholder="最长100个字符,50个汉字" />
</Form.Item>
</TabPane>
<TabPane tab="中标通知" key="2">
<Form.Item name="offer">
<Checkbox>发送中标通知</Checkbox>
</Form.Item>
<Form.Item name="offer">
<TextArea rows={3} maxLength={100} placeholder="最长100个字符,50个汉字" />
</Form.Item>
</TabPane>
<TabPane tab="感谢函" key="3">
<Form.Item name="offer">
<Checkbox>发送感谢函</Checkbox>
</Form.Item>
<Form.Item name="offer">
<TextArea rows={3} maxLength={100} placeholder="最长100个字符,50个汉字" />
</Form.Item>
</TabPane>
</Tabs>
</Form>
</Modal>
)
}
export default ConfirmBidResultModal
\ No newline at end of file
import React, { useRef, useImperativeHandle } from 'react';
import { StandardTable } from 'god';
import { ColumnType } from 'antd/lib/table/interface';
import NiceForm from '@/components/NiceForm';
import { createFormActions, FormEffectHooks } from '@formily/antd';
import { FORM_FILTER_PATH } from '@/formSchema/const';
import { useStateFilterSearchLinkageEffect } from '@/formSchema/effects/useFilterSearch';
import { searchSelectGetSelectCategoryOptionEffect } from '@/pages/transaction/effect/index';
import { PublicApi } from '@/services/api';
import { Row, Col, Space, Button, Typography, Popconfirm, Badge, Tag, Menu, Drawer } from 'antd';
const { Text } = Typography;
const formActions = createFormActions();
const QuotationDetailsDrawer = (props: any) => {
const { visible, onClose, schemaType, effects, reload } = props;
const tableRef = useRef<any>({});
const columns: ColumnType<any>[] = [{
title: '序号',
align: 'center',
dataIndex: 'id',
key: 'id',
render: (t, r, i) => ++i
}, {
title: '物料编号/摘要',
key: 'quotedPriceNo',
dataIndex: 'quotedPriceNo',
render: (text: any, record: any) => (
<Space direction='vertical'>
<Text type='secondary'>{record.quotedPriceNo}</Text>
<Text type='secondary'>{record.details}</Text>
</Space>
)
}, {
title: '规格型号',
key: 'createTime',
dataIndex: 'createTime',
render: (text: any, record: any) => text,
}, {
title: '品类',
key: 'createTime',
dataIndex: 'createTime',
render: (text: any, record: any) => text,
}, {
title: '品牌',
key: 'createTime',
dataIndex: 'createTime',
render: (text: any, record: any) => text,
}, {
title: '采购数量/单位',
key: 'createTime',
dataIndex: 'createTime',
render: (text: any, record: any) => text,
}, {
title: '含税/税率',
key: 'createTime',
dataIndex: 'createTime',
render: (text: any, record: any) => text,
}, {
title: '单价(含税)',
key: 'createTime',
dataIndex: 'createTime',
render: (text: any, record: any) => text,
}, {
title: '金额(含税)',
key: 'createTime',
dataIndex: 'createTime',
render: (text: any, record: any) => text,
}];
/** 列表数据 */
const fetchData = (params?: any) => {
return new Promise((resolve, reject) => {
fetch({ ...params }).then(res => {
resolve(res.data)
})
})
}
useImperativeHandle(reload, () => ({
reload: () => {
tableRef.current.reload();
}
}));
// 搜索
const search = (values: any) => {
tableRef.current.reload(values)
}
return (
<Drawer
title="报价明细"
width={1000}
onClose={onClose}
visible={visible}
bodyStyle={{ paddingBottom: 80 }}
footer={
<div style={{ textAlign: 'right', }}>
<Button onClick={onClose} style={{ marginRight: 8 }}>取消</Button>
<Button onClick={onClose} type="primary">确认</Button>
</div>
}
>
<StandardTable
currentRef={tableRef}
columns={columns}
tableProps={{ rowKew: 'id' }}
fetchTableData={(params: any) => fetchData(params)}
controlRender={
<NiceForm
actions={formActions}
onSubmit={values => search(values)}
effects={($, actions) => {
useStateFilterSearchLinkageEffect($, actions, effects, FORM_FILTER_PATH)
FormEffectHooks.onFieldChange$('category').subscribe(state => {
searchSelectGetSelectCategoryOptionEffect(actions, 'category')
})
}}
schema={
schemaType && SchemaRender()
}
>
</NiceForm>
}
/>
</Drawer>
)
}
export default QuotationDetailsDrawer
import React, { useState } from 'react';
import { Modal, Tabs, Form, Button, Input, Upload, message } from 'antd';
import { UPLOAD_TYPE } from '@/constants'
import { UploadOutlined } from '@ant-design/icons';
const { TabPane } = Tabs;
const { TextArea } = Input;
import styles from './index.less';
const UploadBidResultModal = (props: any) => {
const { title, visible, onCancel } = props;
const [files, setFiles] = useState<any>([]);
const [form] = Form.useForm();
const [loading, setloading] = useState(false);
/**判断文件类型和大小 */
const beforeDocUpload = (file: any) => {
const isLt20M = file.size / 1024 / 1024 < 20;
if (!isLt20M) {
message.error('上传文件大小不超过 20M!');
}
return isLt20M;
}
// 上传回调
const handleChange = ({ file }) => {
const arr: any = files;
setloading(true);
if (file.response) {
if (file.response.code === 1000) {
arr.push({
name: file.name,
url: file.response.data
})
setloading(false);
}
}
setFiles([...arr])
}
return (
<Modal
width={600}
title={title}
visible={visible}
onCancel={onCancel}
wrapClassName={styles.wrap}
// onOk={() => actions.submit()}
// afterClose={() => actions.reset()}
>
<Form
form={form}
layout="vertical"
>
<Form.Item name="offer" label="授标意见" rules={[{ required: true, message: '请输入授标意见' }]}>
<TextArea rows={3} maxLength={200} placeholder="最长200个字符,100个汉字" />
</Form.Item>
<Form.Item
label="报名要求附件"
name="file"
rules={[{ required: true, message: '请选择报名要求附件' }]}
>
<Upload
action="/api/file/file/upload"
data={{ fileType: UPLOAD_TYPE }}
showUploadList={false}
accept='.doc,.docx,.pdf,.ppt,.pptx,.xls,.xlsx'
beforeUpload={beforeDocUpload}
onChange={handleChange}
>
<Button loading={loading} icon={<UploadOutlined />}>上传文件</Button>
<div style={{ marginTop: '8px' }}>一次上传一个文件,每个附件大小不能超过 20M</div>
</Upload>
</Form.Item>
</Form>
</Modal>
)
}
export default UploadBidResultModal
\ No newline at end of file
.rank {
border-radius: 8px;
overflow: hidden;
.rankHeader {
height: 209px;
background: -webkit-linear-gradient(top, rgba(0, 179, 122, 1), #FFFFFF);
padding: 16px;
h5 {
font-size: 14px;
color: #FFFFFF;
margin-bottom: 24px;
}
.rankHeaderBox {
background-color: #FFFFFF;
border-radius: 5px;
padding: 16px;
img {
margin-bottom: 6px;
width: 24px;
}
h4 {
font-size: 16px;
color: #303133;
text-align: center;
position: relative;
}
.rankHeaderBoxInfo {
display: flex;
flex-direction: row;
font-size: 12px;
color: #909399;
span {
color: #303133;
}
.rankHeaderBoxInfoChild {
flex: 1;
align-items: center;
box-sizing: border-box;
text-align: center;
&:first-child{
border-right: 1px solid #EBECF0;
}
}
}
}
}
:global {
.ant-tabs-nav {
padding-left: 16px;
&::before{
border-bottom: 0;
}
}
.ant-tabs {
background-color: #FFFFFF;
}
}
}
\ No newline at end of file
import React, { useEffect, useState } from 'react';
import { Row, Col, Tabs, Button } from 'antd';
import level1 from '@/assets/icons/the_first.png';
import level2 from '@/assets/icons/the_second.png';
import level3 from '@/assets/icons/the_third.png';
import styles from './index.less';
import TriangleTag from '../triangleTag';
import RankRow from '../rankRow';
const { TabPane } = Tabs;
const RankItem = () => {
return (
<div className={styles.rank}>
<div className={styles.rankHeader}>
<h5>竞价排名</h5>
<div className={styles.rankHeaderBox}>
<img src={level1} alt={`排名1`} />
<h4><div style={{display: 'inline-block',position: 'relative',left: '-3%',top: '-5%'}}><TriangleTag text='最低价' wrapStyle={{backgroundColor : '#EA8000'}} bgcolor='#EA8000' direction='right' /></div>广州白马皮具交易中心</h4>
<div className={styles.rankHeaderBoxInfo}>
<div className={styles.rankHeaderBoxInfoChild}>当前最低价:<span>¥ 900.00</span></div>
<div className={styles.rankHeaderBoxInfoChild}>报价次数:<span>5</span></div>
</div>
</div>
</div>
<Tabs defaultActiveKey="1">
<TabPane tab="报价排名" key="1">
<RankRow />
<Button type="link" block>显示更多</Button>
</TabPane>
<TabPane tab="报名会员" key="2">
<RankRow rowType={2} />
<Button type="link" block>显示更多</Button>
</TabPane>
</Tabs>
</div>
)
}
export default RankItem;
.rankRow {
height: 56px;
border-radius: 28px;
padding: 0 16px;
display: flex;
align-items: center;
justify-content: center;
flex-direction: row;
margin-bottom: 4px;
.rankRowLeft {
flex: 1;
color: #303133;
.rankRowLeftTop {
display: flex;
flex-direction: row;
align-items: center;
img {
width: 24px;
margin-right: 8px;
}
.rankRowLeftTopRank {
width: 24px;
height: 24px;
line-height: 24px;
text-align: center;
margin-right: 8px;
background-color: #EBECF0;
font-size: 12px;
color: #909399;
}
}
.rankRowLeftBottom {
padding-left: 32px;
display: flex;
flex-direction: row;
font-size: 14px;
color: #303133;
.rankRowLeftBottomTag {
color: #606266;
font-size: 12px;
padding: 2px;
border-radius: 2px;
margin-left: 8px;
background-color: #F4F5F7;
}
}
.rankRowLeftBottomPhone{
color: #909399;
}
}
.rankRowRight {
display: flex;
flex-direction: row;
align-items: center;
color: #909399;
font-size: 12px;
}
}
.rankRow_level_1 {
background: -webkit-linear-gradient(left, rgba(253, 197, 47, .2), #FFFFFF);
}
.rankRow_level_2 {
background: -webkit-linear-gradient(left, rgba(153, 176, 192, .2), #FFFFFF);
}
.rankRow_level_3 {
background: -webkit-linear-gradient(left, rgba(210, 164, 104, .2), #FFFFFF);
}
import React, { useEffect, useState } from 'react';
import level1 from '@/assets/icons/the_first.png';
import level2 from '@/assets/icons/the_second.png';
import level3 from '@/assets/icons/the_third.png';
import TriangleTag from '../triangleTag';
import IMBtn from '../../../../../components/detail/components/iMBtn';
import styles from './index.less';
interface RankRowProps {
detail?: any,
rowType?: number
}
const RankRow: React.FC<RankRowProps> = (props: any) => {
const { detail, rowType } = props;
const _returnRow = () => {
if (rowType === 1) {
return (
<div className={`${styles.rankRow} ${styles.rankRow_level_1}`}>
<div className={styles.rankRowLeft}>
<div className={styles.rankRowLeftTop}>
<img src={level1} alt="" />
广州白马皮具交易中心
<TriangleTag text='最低价' wrapStyle={{ backgroundColor: '#EA8000', marginLeft: '8px' }} bgcolor='#EA8000' direction='left' />
</div>
<div className={styles.rankRowLeftBottom}>
¥900.00
<div className={styles.rankRowLeftBottomTag}>第2次</div>
</div>
</div>
<div className={styles.rankRowRight}>
蒯美政
<IMBtn func={() => console.log(1)} />
</div>
</div>
)
} else {
return (
<div className={`${styles.rankRow}`}>
<div className={styles.rankRowLeft}>
<div className={styles.rankRowLeftTop}>广州白马皮具交易中心</div>
<div className={styles.rankRowLeftBottomPhone}>185 2929 6758</div>
</div>
<div className={styles.rankRowRight}>
蒯美政
<IMBtn func={() => console.log(1)} />
</div>
</div>
)
}
}
return (
_returnRow()
)
}
RankRow.defaultProps = {
rowType: 1
}
export default RankRow;
.statusBox{
font-size: 12px;
.statusBoxStatus{
background-color: #EA8000;
text-align: center;
line-height: 48px;
height: 48px;
color: #FFFFFF;
font-size: 12px;
span{
font-size: 16px;
}
}
.statusBoxTips{
color: #909399;
margin: 16px 0;
text-align: center;
}
.statusBoxTime{
display: flex;
align-items: baseline;
justify-content: center;
.statusBoxTimeChild{
.statusBoxTimeChild_top{
width: 64px;
height: 64px;
line-height: 64px;
text-align: center;
background-color: #FFF8E6;
font-size: 32px;
color: #EA8000;
margin-bottom: 8px;
}
.statusBoxTimeChild_bottom{
color: #909399;
text-align: center;
}
}
span{
font-size: 32px;
color: #909399;
margin: 0 12px;
}
}
h4{
font-size: 14px;
color: #303133;
margin-bottom: 16px;
}
.statusBoxText{
display: flex;
align-items: center;
margin-bottom: 8px;
color: #303133;
div{
color: #909399;
width: 88px;
}
&:nth-last-child(1){
margin-bottom: 0;
}
}
}
\ No newline at end of file
import React from 'react';
import { Row, Col, Tooltip, Divider } from 'antd';
import styles from './index.less'
const StatuBox = () => {
return (
<div className='ant-card ant-card-bordered'>
<div className='ant-card-body'>
<div className={styles.statusBox}>
<div className={styles.statusBoxStatus}>当前状态:<span>竞价中</span></div>
<p className={styles.statusBoxTips}>距离竞价结束还剩</p>
<div className={styles.statusBoxTime}>
<div className={styles.statusBoxTimeChild}>
<div className={styles.statusBoxTimeChild_top}>02</div>
<p className={styles.statusBoxTimeChild_bottom}>小时</p>
</div>
<span>:</span>
<div className={styles.statusBoxTimeChild}>
<div className={styles.statusBoxTimeChild_top}>32</div>
<p className={styles.statusBoxTimeChild_bottom}>分钟</p>
</div>
<span>:</span>
<div className={styles.statusBoxTimeChild}>
<div className={styles.statusBoxTimeChild_top}>48</div>
<p className={styles.statusBoxTimeChild_bottom}></p>
</div>
</div>
<Divider dashed style={{color: '#EBECF0',margin: '6px 0' }} />
<h4></h4>
<div className={styles.statusBoxText}><div>报价规则:</div>项目总价(含税)</div>
<div className={styles.statusBoxText}><div>起拍价:</div>¥ 1,500.00</div>
<div className={styles.statusBoxText}><div>目标价:</div>¥ 900.00</div>
<div className={styles.statusBoxText}><div>最小价差:</div>¥ 100.00</div>
<div className={styles.statusBoxText}><div>允许报价次数:</div>3</div>
<div className={styles.statusBoxText}><div>报价排名:</div>按项目总价排名</div>
<div className={styles.statusBoxText}><div>公开最低报价:</div></div>
<div className={styles.statusBoxText}><div>公开报价排名:</div></div>
</div>
</div>
</div>
)
}
export default StatuBox
\ No newline at end of file
.triangleTag{
display: inline-block;
position: relative;
color: #FFFFFF;
font-size: 12px;
border-radius: 2px;
.directionTriangle{
width: 0;
height: 0;
border-width: 4px;
border-style: solid;
position: absolute;
}
}
\ No newline at end of file
import React, { useEffect, useState } from 'react';
import styles from './index.less';
interface TriangleTagProps {
text: string,
bgcolor?: string,
direction?: string,
wrapStyle: React.CSSProperties
}
const TriangleTag: React.FC<TriangleTagProps> = (props: any) => {
const { text, bgcolor, direction, wrapStyle } = props;
const _returndirectionStyle = () => {
if(direction === 'left'){
return {
borderColor: `transparent ${bgcolor} transparent transparent`,
left: '-8px',
top : '26%'
}
}else if(direction === 'right'){
return {
borderColor: `transparent ${bgcolor} transparent transparent`,
transform: 'rotate(180deg)',
right: '-8px',
top : '26%'
}
}
}
return (
<div className={styles.triangleTag} style={wrapStyle}>
<div className={styles.directionTriangle} style={_returndirectionStyle()}></div>
{text}
</div>
)
}
TriangleTag.defaultProps = {
bgcolor: '#EA8000',
direction: 'left'
}
export default TriangleTag;
.warp {
.header {
display: flex;
height: 48px;
line-height: 48px;
font-size: 16px;
background-color: #FFFFFF;
color: #303133;
padding: 0 16px;
align-items: center;
&::before {
content: " ";
width: 2px;
height: 16px;
background: @primary-color;
margin-right: 6px;
}
}
.layout {
margin: 24px;
}
:global {
.ant-card-head-wrapper{
padding: 12px 0;
.ant-card-head-wrapper{
padding: 0;
}
}
}
}
import React, { useEffect, useState } from 'react';
import { Row, Col, Tooltip, Button } from 'antd';
import RankItem from './components/rank';
import StatusBox from './components/statusBox';
import QuotationDeskLayout from '../../../components/detail/components/quotationDeskLayout';
import BidDetailLayout from '../../../components/detail/components/bidDetailLayout';
import styles from './index.less';
const Management = () => {
return (
<div className={styles.warp}>
<div className={styles.header}>进口头层黄牛皮荔枝纹竞价</div>
<div className={styles.layout}>
<Row gutter={[8,8]}>
<Col span={6}>
<RankItem />
</Col>
<Col span={18}>
<Row gutter={[8,8]} style={{marginBottom: '8px'}}>
<Col span={16}>
<QuotationDeskLayout />
</Col>
<Col span={8}>
<StatusBox />
</Col>
</Row>
<Row>
<BidDetailLayout />
</Row>
</Col>
</Row>
</div>
</div>
)
}
export default Management;
......@@ -20,6 +20,9 @@ import MaterialLayout from '../../components/detail/components/materialLayout';
import DemandLayout from '../../components/detail/components/demandLayout';
import BidCommonLayout from '../../components/detail/components/bidCommonLayout';
import ModalOperate from '../../components/modalOperate';
import ConfirmBidResultModal from '../components/confirmBidResultModal';
import UploadBidResultModal from '../components/uploadBidResultModal';
import QuotationDetailsDrawer from '../components/quotationDetailsDrawer';
const ICON_STYLE: any = {
color: '#C0C4CC',
......@@ -52,6 +55,12 @@ const SearchDetail = () => {
const [path] = useState(pathname.split('/')[pathname.split('/').length - 1]);
const [pathPci] = useState(pathname.split('/')[pathname.split('/').length - 2]);
const [visible, setVisible] = useState<boolean>(false);
// 确认竞价结果
const [confirmBidResultVisible , setConfirmBidResultVisible] = useState<boolean>(false);
// 提交竞价结果
const [uploadBidResultVisible , setUploadBidResultVisible] = useState<boolean>(false);
// 报价明细
const [quotationDetailsVisible , setQuotationDetailsVisible] = useState<boolean>(false);
const [dataSource, setDataSource] = useState<any>({});
const [basicEffect, setBasicEffect] = useState<any>([]);
const [conditionEffect, setConditionEffect] = useState<any>([]);
......@@ -180,6 +189,20 @@ const SearchDetail = () => {
单据审核
</Button>
)}
<Button
onClick={() => setConfirmBidResultVisible(true)}
type='primary'
>
<CheckCircleOutlined />
确认竞价结果
</Button>
{/* <Button
onClick={() => setUploadBidResultVisible(true)}
type='primary'
>
<CheckCircleOutlined />
提交竞价结果
</Button> */}
</>
}
components={
......@@ -306,7 +329,12 @@ const SearchDetail = () => {
]
} />
<DemandLayout storeList={storeList} />
<BidCommonLayout layoutId="resultLayout" title="授标结果" layoutType='result' effect={
<BidCommonLayout
layoutId="resultLayout"
title="授标结果"
layoutType='result'
checkDetailFunc={() => {setQuotationDetailsVisible(true)}}
effect={
[
{},
{},
......@@ -314,9 +342,7 @@ const SearchDetail = () => {
{},
]
}
extra={<Button type='link'>
查看竞价过程
</Button>} />
extra={<Button type='link'>查看竞价过程</Button>} />
<RecordLyout />
</Fragment>
}
......@@ -330,6 +356,21 @@ const SearchDetail = () => {
onCancel={() => setVisible(false)}
onOk={() => history.goBack()}
/>
<ConfirmBidResultModal
title="确认竞价结果"
visible={confirmBidResultVisible}
onCancel={() => setConfirmBidResultVisible(false)}
/>
<UploadBidResultModal
title="提交竞价结果"
visible={uploadBidResultVisible}
onCancel={() => setUploadBidResultVisible(false)}
/>
<QuotationDetailsDrawer
title="报价明细"
visible={quotationDetailsVisible}
onClose={() => setQuotationDetailsVisible(false)}
/>
</Context.Provider>
)
}
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment