@@ -156,7 +156,7 @@ const SearchDemandNoteForm = ({ applySearch, orgComboData, searchCriteria, issue | |||||
}} | }} | ||||
renderInput={(params) => ( | renderInput={(params) => ( | ||||
<TextField {...params} | <TextField {...params} | ||||
label="Organisation" | |||||
label="BR No./Organisation" | |||||
InputLabelProps={{ | InputLabelProps={{ | ||||
shrink: true | shrink: true | ||||
}} | }} | ||||
@@ -14,7 +14,7 @@ const MainCard = Loadable(React.lazy(() => import('components/MainCard'))); | |||||
const LoadingComponent = Loadable(React.lazy(() => import('pages/extra-pages/LoadingComponent'))); | const LoadingComponent = Loadable(React.lazy(() => import('pages/extra-pages/LoadingComponent'))); | ||||
import DownloadIcon from '@mui/icons-material/Download'; | import DownloadIcon from '@mui/icons-material/Download'; | ||||
// ==============================|| DASHBOARD - DEFAULT ||============================== // | // ==============================|| DASHBOARD - DEFAULT ||============================== // | ||||
const PaymentDetails = ({ formData,doPrint }) => { | |||||
const PaymentDetails = ({ formData,doPrint,onDownload }) => { | |||||
const [data, setData] = React.useState({}); | const [data, setData] = React.useState({}); | ||||
const [onReady, setOnReady] = React.useState(false); | const [onReady, setOnReady] = React.useState(false); | ||||
@@ -158,10 +158,14 @@ const PaymentDetails = ({ formData,doPrint }) => { | |||||
</FormLabel> | </FormLabel> | ||||
</Grid> | </Grid> | ||||
<Grid xs={6} md={5} sx={{ml:5,textAlign: "left" }}> | <Grid xs={6} md={5} sx={{ml:5,textAlign: "left" }}> | ||||
{onDownload? | |||||
<LoadingComponent disableText={true} alignItems="flex-start"/> | |||||
: | |||||
<Button className="printHidden" variant="contained" sx={{ mt:2 }} onClick={doPrint}> | <Button className="printHidden" variant="contained" sx={{ mt:2 }} onClick={doPrint}> | ||||
<DownloadIcon/> | <DownloadIcon/> | ||||
<Typography sx={{fontSize: "16px"}}>Download</Typography> | <Typography sx={{fontSize: "16px"}}>Download</Typography> | ||||
</Button> | </Button> | ||||
} | |||||
</Grid> | </Grid> | ||||
</Grid> | </Grid> | ||||
</Grid> | </Grid> | ||||
@@ -4,7 +4,7 @@ import { | |||||
Typography, | Typography, | ||||
Stack, | Stack, | ||||
Box, | Box, | ||||
// Button | |||||
Button | |||||
} from '@mui/material'; | } from '@mui/material'; | ||||
import * as UrlUtils from "utils/ApiPathConst"; | import * as UrlUtils from "utils/ApiPathConst"; | ||||
import * as React from "react"; | import * as React from "react"; | ||||
@@ -12,6 +12,7 @@ import * as HttpUtils from "utils/HttpUtils"; | |||||
import * as DateUtils from "utils/DateUtils"; | import * as DateUtils from "utils/DateUtils"; | ||||
import { useParams } from "react-router-dom"; | import { useParams } from "react-router-dom"; | ||||
import { useNavigate } from "react-router-dom"; | import { useNavigate } from "react-router-dom"; | ||||
import ForwardIcon from '@mui/icons-material/Forward'; | |||||
import Loadable from 'components/Loadable'; | import Loadable from 'components/Loadable'; | ||||
const LoadingComponent = Loadable(React.lazy(() => import('pages/extra-pages/LoadingComponent'))); | const LoadingComponent = Loadable(React.lazy(() => import('pages/extra-pages/LoadingComponent'))); | ||||
@@ -37,6 +38,7 @@ const Index = () => { | |||||
const [record, setRecord] = React.useState(); | const [record, setRecord] = React.useState(); | ||||
const [itemList, setItemList] = React.useState([]); | const [itemList, setItemList] = React.useState([]); | ||||
const [onReady, setOnReady] = React.useState(false); | const [onReady, setOnReady] = React.useState(false); | ||||
const [onDownload, setOnDownload] = React.useState(false); | |||||
// const [detailsOrder, setDetailsOrder] = React.useState(2); | // const [detailsOrder, setDetailsOrder] = React.useState(2); | ||||
React.useEffect(() => { | React.useEffect(() => { | ||||
@@ -54,8 +56,15 @@ const Index = () => { | |||||
const doPrint = () => { | const doPrint = () => { | ||||
// window.print(); | // window.print(); | ||||
setOnDownload(true) | |||||
HttpUtils.fileDownload({ | HttpUtils.fileDownload({ | ||||
url: UrlUtils.GEN_PAYMENT_RECEIPT+"/"+params.id, | url: UrlUtils.GEN_PAYMENT_RECEIPT+"/"+params.id, | ||||
onResponse:()=>{ | |||||
setOnDownload(false) | |||||
}, | |||||
onError:()=>{ | |||||
setOnDownload(false) | |||||
} | |||||
}); | }); | ||||
}; | }; | ||||
@@ -98,6 +107,15 @@ const Index = () => { | |||||
</Stack> | </Stack> | ||||
</div> | </div> | ||||
</Grid> | </Grid> | ||||
<Grid item xs={12} width={{xs:"90%", sm:"90%", md:"90%", lg:"90%"}}> | |||||
<Button | |||||
aria-label={"back"} | |||||
title={"back"} | |||||
sx={{ ml: 0, mt: 2.5 }} style={{ border: '2px solid' }} variant="outlined" onClick={() => { navigate(-1) }} | |||||
> | |||||
<ForwardIcon style={{ height: 30, width: 50, transform: "rotate(180deg)" }} /> | |||||
</Button> | |||||
</Grid> | |||||
{/*row 1*/} | {/*row 1*/} | ||||
<Grid item xs={12} md={12} sx={{textAlign: "center" }}> | <Grid item xs={12} md={12} sx={{textAlign: "center" }}> | ||||
<Grid container justifyContent="center" direction="column" spacing={2} sx={{ p: 2 }} alignitems="stretch" > | <Grid container justifyContent="center" direction="column" spacing={2} sx={{ p: 2 }} alignitems="stretch" > | ||||
@@ -106,6 +124,7 @@ const Index = () => { | |||||
<PaymentDetails | <PaymentDetails | ||||
formData={record} | formData={record} | ||||
doPrint={doPrint} | doPrint={doPrint} | ||||
onDownload={onDownload} | |||||
style={{ | style={{ | ||||
display: "flex", | display: "flex", | ||||
height: "100%", | height: "100%", | ||||
@@ -32,6 +32,8 @@ import UnionPayIcon from "assets/images/icons/unionpay.svg"; | |||||
import PpsIcon from "assets/images/icons/ppshk.svg"; | import PpsIcon from "assets/images/icons/ppshk.svg"; | ||||
import FpsIcon from "assets/images/icons/fps.svg"; | import FpsIcon from "assets/images/icons/fps.svg"; | ||||
import {FormattedMessage, useIntl} from "react-intl"; | import {FormattedMessage, useIntl} from "react-intl"; | ||||
import * as HttpUtils from "utils/HttpUtils" | |||||
import * as UrlUtils from "utils/ApiPathConst" | |||||
const MultiPaymentWindow = (props) => { | const MultiPaymentWindow = (props) => { | ||||
const intl = useIntl(); | const intl = useIntl(); | ||||
@@ -52,7 +54,10 @@ const MultiPaymentWindow = (props) => { | |||||
const [pPSClass, setPPSlass] = useState(""); | const [pPSClass, setPPSlass] = useState(""); | ||||
const [filteredPaymentMethod, setFilteredPaymentMethod] = useState([]); | const [filteredPaymentMethod, setFilteredPaymentMethod] = useState([]); | ||||
const [onReady, setOnReady] = useState(false); | const [onReady, setOnReady] = useState(false); | ||||
const [paymentHoldedErrText, setPaymentHoldedErrText] = React.useState(""); | |||||
const [paymentHoldedErr, setPaymentHoldedErr] = React.useState(false); | |||||
useEffect(() => { | useEffect(() => { | ||||
// console.log(props.transactionData) | // console.log(props.transactionData) | ||||
if(Object.keys(props.transactionData).length > 0){ | if(Object.keys(props.transactionData).length > 0){ | ||||
@@ -185,7 +190,49 @@ const MultiPaymentWindow = (props) => { | |||||
}; | }; | ||||
const confirmPaymentHandle = () => () =>{ | const confirmPaymentHandle = () => () =>{ | ||||
props.setConfirmPayment(true); | |||||
handlePaymentCheck() | |||||
}; | |||||
const handlePaymentCheck = () => { | |||||
let appIdList = props.appIds | |||||
// console.log(props.appIds) | |||||
// console.log(appIdList) | |||||
HttpUtils.post({ | |||||
url: UrlUtils.PAYMENT_CHECK, | |||||
params: { | |||||
appIds: appIdList | |||||
}, | |||||
onSuccess: (responseData) => { | |||||
const latestData = {}; | |||||
responseData.forEach(item => { | |||||
const { appId, timeDiff } = item; | |||||
if (latestData[appId] === undefined || timeDiff < latestData[appId].timeDiff) { | |||||
latestData[appId] = item; | |||||
} | |||||
}); | |||||
const latestDataObjects = Object.values(latestData); | |||||
const filteredData = latestDataObjects.filter(item => item.timeDiff > 20 && item.status !== "APPR"); | |||||
const filteredAppIds = filteredData.map(item => item.appId); | |||||
const appIdsNotInData = appIdList.filter(appId => !latestDataObjects.some(item => item.appId === appId)); | |||||
const combinedAppIdsArray = [...appIdsNotInData, ...filteredAppIds]; | |||||
const readyToPayment = appIdList.every(appId => combinedAppIdsArray.includes(appId)); | |||||
if (readyToPayment){ | |||||
// props.setConfirmPayment(true); | |||||
return; | |||||
}else{ | |||||
const appIdsInData = appIdList.filter(appId => !combinedAppIdsArray.some(item => item === appId)); | |||||
const HoldingApplication = latestDataObjects.filter(item => appIdsInData.includes(item.appId)); | |||||
const resultString = HoldingApplication.map(item => item.appNo).join(' , '); | |||||
setPaymentHoldedErrText(resultString); | |||||
// setPaymentHoldedErrText(intl.formatMessage({ id: 'MSG.paymentHolded' }, { appNo: record.appNo })); | |||||
setPaymentHoldedErr(true); | |||||
} | |||||
} | |||||
}); | |||||
}; | }; | ||||
const closeHandle = () => () =>{ | const closeHandle = () => () =>{ | ||||
@@ -387,10 +434,37 @@ const MultiPaymentWindow = (props) => { | |||||
</DialogActions> | </DialogActions> | ||||
<DialogActions> | <DialogActions> | ||||
<Button variant="contained" color="success" onClick={confirmPaymentHandle()} disabled={paymentMethod === "" || isLimit || isPPSLimit}> | <Button variant="contained" color="success" onClick={confirmPaymentHandle()} disabled={paymentMethod === "" || isLimit || isPPSLimit}> | ||||
<FormattedMessage id="confirm"/> | |||||
<FormattedMessage id="pay"/> | |||||
</Button> | </Button> | ||||
</DialogActions> | </DialogActions> | ||||
</Stack> | </Stack> | ||||
<div> | |||||
<Dialog | |||||
open={paymentHoldedErr} | |||||
onClose={() => setPaymentHoldedErr(false)} | |||||
PaperProps={{ | |||||
sx: { | |||||
minWidth: '40vw', | |||||
maxWidth: { xs: '90vw', s: '90vw', m: '70vw', lg: '70vw' }, | |||||
maxHeight: { xs: '90vh', s: '70vh', m: '70vh', lg: '60vh' } | |||||
} | |||||
}} | |||||
> | |||||
<DialogTitle></DialogTitle> | |||||
<Typography variant="h4" style={{ paddingLeft: '24px' }}><FormattedMessage id="MSG.actionFail" /></Typography> | |||||
<DialogContent style={{ display: 'flex', }}> | |||||
<Stack direction="column" justifyContent="space-between"> | |||||
<div dangerouslySetInnerHTML={{ __html: intl.formatMessage({ id: 'MSG.paymentHolded' }, { appNo: paymentHoldedErrText }) }} /> | |||||
</Stack> | |||||
</DialogContent> | |||||
<DialogActions> | |||||
<Button onClick={() => setPaymentHoldedErr(false)} aria-label={intl.formatMessage({ id: 'close' })}> | |||||
<Typography variant="h5"> | |||||
<FormattedMessage id="close" /> | |||||
</Typography></Button> | |||||
</DialogActions> | |||||
</Dialog> | |||||
</div> | |||||
</Dialog> | </Dialog> | ||||
); | ); | ||||
}; | }; | ||||
@@ -157,12 +157,12 @@ const Index = () => { | |||||
}); | }); | ||||
} | } | ||||
// //For testing | |||||
//For testing | |||||
// if (paymentMethod != "") { | // if (paymentMethod != "") { | ||||
// HttpUtils.post({ | // HttpUtils.post({ | ||||
// url: UrlUtils.PAYMENT_CREATE, | // url: UrlUtils.PAYMENT_CREATE, | ||||
// params: { | // params: { | ||||
// transNo: "test0001", | |||||
// transNo: "test0002", | |||||
// payMethod: paymentMethod, | // payMethod: paymentMethod, | ||||
// payAmount: totalAmount, | // payAmount: totalAmount, | ||||
// appIdList: location.state?.appIdList ?? [] | // appIdList: location.state?.appIdList ?? [] | ||||
@@ -209,18 +209,18 @@ const Index = () => { | |||||
} | } | ||||
}); | }); | ||||
// HttpUtils.get({ | |||||
// url: UrlUtils.PAYMENT_LIMIT_SETTING_LIST, | |||||
// params: {}, | |||||
// onSuccess: (responseData) => { | |||||
// // console.log(responseData) | |||||
// setPaymentLimit(responseData) | |||||
HttpUtils.get({ | |||||
url: UrlUtils.PAYMENT_LIMIT_SETTING_LIST, | |||||
params: {}, | |||||
onSuccess: (responseData) => { | |||||
// console.log(responseData) | |||||
setPaymentLimit(responseData) | |||||
// }, | |||||
// onError: () =>{ | |||||
// // setOnReady(true) | |||||
// } | |||||
// }); | |||||
}, | |||||
onError: () =>{ | |||||
// setOnReady(true) | |||||
} | |||||
}); | |||||
// const responseData = { | // const responseData = { | ||||
// "availablepaymentmethods": [ | // "availablepaymentmethods": [ | ||||
@@ -540,6 +540,8 @@ const Index = () => { | |||||
onReady = {onReady} | onReady = {onReady} | ||||
locale = {locale} | locale = {locale} | ||||
isFullScreen={isFullScreen} | isFullScreen={isFullScreen} | ||||
appIds={appIds} | |||||
// appNo={itemList.appNo} | |||||
/> | /> | ||||
</Grid > | </Grid > | ||||
); | ); | ||||
@@ -37,6 +37,9 @@ const FormPanel = ({ formData }) => { | |||||
const [saving, setSaving] = React.useState(false); | const [saving, setSaving] = React.useState(false); | ||||
const [proofPaymentDeadlineMin, setProofPaymentDeadlineMin] = React.useState({}); | |||||
const [reviseDeadlineMin, setReviseDeadlineMin] = React.useState({}); | |||||
const navigate = useNavigate() | const navigate = useNavigate() | ||||
React.useEffect(() => { | React.useEffect(() => { | ||||
@@ -46,6 +49,8 @@ const FormPanel = ({ formData }) => { | |||||
setColumnPrice(ComboData.proofPrice[1]) | setColumnPrice(ComboData.proofPrice[1]) | ||||
formData['length'] = 18; | formData['length'] = 18; | ||||
} | } | ||||
setProofPaymentDeadlineMin(formData.proofPaymentDeadline); | |||||
setReviseDeadlineMin(formData.reviseDeadline); | |||||
} | } | ||||
}, [formData]); | }, [formData]); | ||||
@@ -206,6 +211,7 @@ const FormPanel = ({ formData }) => { | |||||
onChange={formik.handleChange} | onChange={formik.handleChange} | ||||
name="reviseDeadline" | name="reviseDeadline" | ||||
value={formik.values["reviseDeadline"]} | value={formik.values["reviseDeadline"]} | ||||
InputProps={{ inputProps: { min: DateUtils.datetimeStr(reviseDeadlineMin) } }} | |||||
variant="outlined" | variant="outlined" | ||||
sx={ | sx={ | ||||
{ | { | ||||
@@ -232,6 +238,7 @@ const FormPanel = ({ formData }) => { | |||||
onChange={formik.handleChange} | onChange={formik.handleChange} | ||||
name="proofPaymentDeadline" | name="proofPaymentDeadline" | ||||
value={formik.values["proofPaymentDeadline"]} | value={formik.values["proofPaymentDeadline"]} | ||||
InputProps={{ inputProps: { min: DateUtils.datetimeStr(proofPaymentDeadlineMin) } }} | |||||
variant="outlined" | variant="outlined" | ||||
sx={ | sx={ | ||||
{ | { | ||||
@@ -45,6 +45,8 @@ const Index = () => { | |||||
const [record, setRecord] = React.useState({}); | const [record, setRecord] = React.useState({}); | ||||
const [onReady, setOnReady] = React.useState(false); | const [onReady, setOnReady] = React.useState(false); | ||||
const [isPopUp, setIsPopUp] = useState(false); | const [isPopUp, setIsPopUp] = useState(false); | ||||
const [paymentHoldedErrText, setPaymentHoldedErrText] = React.useState(""); | |||||
const [paymentHoldedErr, setPaymentHoldedErr] = React.useState(false); | |||||
const intl = useIntl(); | const intl = useIntl(); | ||||
@@ -77,9 +79,48 @@ const Index = () => { | |||||
function doPayment() { | function doPayment() { | ||||
setIsPopUp(false); | setIsPopUp(false); | ||||
navigate('/paymentPage', { state: { amount: fee, appIdList: [record?.appId] } }); | |||||
let appIdList = [record?.appId] | |||||
handlePaymentCheck(appIdList) | |||||
} | } | ||||
const handlePaymentCheck = (appIdList) => { | |||||
HttpUtils.post({ | |||||
url: UrlUtils.PAYMENT_CHECK, | |||||
params: { | |||||
appIds: appIdList | |||||
}, | |||||
onSuccess: (responseData) => { | |||||
const latestData = {}; | |||||
responseData.forEach(item => { | |||||
const { appId, timeDiff } = item; | |||||
if (latestData[appId] === undefined || timeDiff < latestData[appId].timeDiff) { | |||||
latestData[appId] = item; | |||||
} | |||||
}); | |||||
const latestDataObjects = Object.values(latestData); | |||||
const filteredData = latestDataObjects.filter(item => item.timeDiff > 20 && item.status !== "APPR"); | |||||
const filteredAppIds = filteredData.map(item => item.appId); | |||||
const appIdsNotInData = appIdList.filter(appId => !latestDataObjects.some(item => item.appId === appId)); | |||||
const combinedAppIdsArray = [...appIdsNotInData, ...filteredAppIds]; | |||||
const readyToPayment = appIdList.every(appId => combinedAppIdsArray.includes(appId)); | |||||
if (readyToPayment){ | |||||
navigate('/paymentPage', { state: { amount: fee, appIdList: appIdList } }); | |||||
}else{ | |||||
const appIdsInData = appIdList.filter(appId => !combinedAppIdsArray.some(item => item === appId)); | |||||
const HoldingApplication = latestDataObjects.filter(item => appIdsInData.includes(item.appId)); | |||||
const resultString = HoldingApplication.map(item => item.appNo).join(' , '); | |||||
setPaymentHoldedErrText(resultString); | |||||
// setPaymentHoldedErrText(intl.formatMessage({ id: 'MSG.paymentHolded' }, { appNo: record.appNo })); | |||||
setPaymentHoldedErr(true); | |||||
} | |||||
} | |||||
}); | |||||
}; | |||||
return ( | return ( | ||||
!onReady ? | !onReady ? | ||||
<Grid container sx={{ minHeight: '87vh', mb: 3 }} direction="column" justifyContent="center" alignItems="center"> | <Grid container sx={{ minHeight: '87vh', mb: 3 }} direction="column" justifyContent="center" alignItems="center"> | ||||
@@ -200,6 +241,33 @@ const Index = () => { | |||||
</Dialog> | </Dialog> | ||||
</div> | </div> | ||||
{/*row 2*/} | {/*row 2*/} | ||||
<div> | |||||
<Dialog | |||||
open={paymentHoldedErr} | |||||
onClose={() => setPaymentHoldedErr(false)} | |||||
PaperProps={{ | |||||
sx: { | |||||
minWidth: '40vw', | |||||
maxWidth: { xs: '90vw', s: '90vw', m: '70vw', lg: '70vw' }, | |||||
maxHeight: { xs: '90vh', s: '70vh', m: '70vh', lg: '60vh' } | |||||
} | |||||
}} | |||||
> | |||||
<DialogTitle></DialogTitle> | |||||
<Typography variant="h4" style={{ paddingLeft: '24px' }}><FormattedMessage id="MSG.actionFail" /></Typography> | |||||
<DialogContent style={{ display: 'flex', }}> | |||||
<Stack direction="column" justifyContent="space-between"> | |||||
<div dangerouslySetInnerHTML={{ __html: intl.formatMessage({ id: 'MSG.paymentHolded' }, { appNo: paymentHoldedErrText }) }} /> | |||||
</Stack> | |||||
</DialogContent> | |||||
<DialogActions> | |||||
<Button onClick={() => setPaymentHoldedErr(false)} aria-label={intl.formatMessage({ id: 'close' })}> | |||||
<Typography variant="h5"> | |||||
<FormattedMessage id="close" /> | |||||
</Typography></Button> | |||||
</DialogActions> | |||||
</Dialog> | |||||
</div> | |||||
</Grid > | </Grid > | ||||
@@ -139,7 +139,7 @@ const ApplicationDetailCard = ({ | |||||
<Grid container alignItems={"center"}> | <Grid container alignItems={"center"}> | ||||
<Grid item xs={12} md={3} lg={3} | <Grid item xs={12} md={3} lg={3} | ||||
sx={{ display: 'flex', alignItems: 'center' }}> | sx={{ display: 'flex', alignItems: 'center' }}> | ||||
<FormLabel><Typography variant="h5">App No.:</Typography></FormLabel> | |||||
<FormLabel><Typography variant="h5">App. No.:</Typography></FormLabel> | |||||
</Grid> | </Grid> | ||||
<Grid item xs={12} md={9} lg={9}> | <Grid item xs={12} md={9} lg={9}> | ||||
@@ -151,7 +151,7 @@ const ApplicationDetailCard = ({ | |||||
<Grid container alignItems={"left"}> | <Grid container alignItems={"left"}> | ||||
<Grid item xs={12} md={3} lg={3} | <Grid item xs={12} md={3} lg={3} | ||||
sx={{ display: 'flex', alignItems: 'center' }}> | sx={{ display: 'flex', alignItems: 'center' }}> | ||||
<FormLabel><Typography variant="h5">Status:</Typography></FormLabel> | |||||
<FormLabel><Typography variant="h5">App. Status:</Typography></FormLabel> | |||||
</Grid> | </Grid> | ||||
<Grid item xs={12} md={9} lg={9} sx={{ display: 'flex', alignItems: 'center' }}> | <Grid item xs={12} md={9} lg={9} sx={{ display: 'flex', alignItems: 'center' }}> | ||||
@@ -278,7 +278,9 @@ const ApplicationDetailCard = ({ formData, }) => { | |||||
? | ? | ||||
<Typography variant="pnspsFormParagraph">( {data.noOfPages} {intl.formatMessage({id: 'page'})} x $6,552 )</Typography> | <Typography variant="pnspsFormParagraph">( {data.noOfPages} {intl.formatMessage({id: 'page'})} x $6,552 )</Typography> | ||||
: | : | ||||
<Typography variant="pnspsFormParagraph">( {data.length} cm x {data.colCount === 2 ? "$364 二格位" : "$182 一格位"} )</Typography> | |||||
<Typography variant="pnspsFormParagraph">( {data.length} cm x {data.colCount === 2 ? | |||||
"$364 "+intl.formatMessage({id: 'doubleCol'}) : | |||||
"$182 "+intl.formatMessage({id: 'singleCol'})} )</Typography> | |||||
} | } | ||||
</Grid> | </Grid> | ||||
</Grid> | </Grid> | ||||
@@ -119,6 +119,7 @@ const GazetteDetailCard = ( | |||||
// size="large" | // size="large" | ||||
variant="contained" | variant="contained" | ||||
onClick={groupDetailClick()} | onClick={groupDetailClick()} | ||||
disabled={applicationDetailData.data.status!="submitted"&&applicationDetailData.data.status!="reviewed"} | |||||
sx={{ | sx={{ | ||||
textTransform: 'capitalize', | textTransform: 'capitalize', | ||||
alignItems: 'end' | alignItems: 'end' | ||||
@@ -52,6 +52,8 @@ const ApplicationDetailCard = ( | |||||
const [isPopUp, setIsPopUp] = useState(false); | const [isPopUp, setIsPopUp] = useState(false); | ||||
const [errorText, setErrorText] = useState(""); | const [errorText, setErrorText] = useState(""); | ||||
const [errorPopUp, setErrorPopUp] = useState(false); | const [errorPopUp, setErrorPopUp] = useState(false); | ||||
const [paymentHoldedErrText, setPaymentHoldedErrText] = React.useState(""); | |||||
const [paymentHoldedErr, setPaymentHoldedErr] = React.useState(false); | |||||
// const params = useParams(); | // const params = useParams(); | ||||
const [currentApplicationDetailData, setCurrentApplicationDetailData] = useState({}); | const [currentApplicationDetailData, setCurrentApplicationDetailData] = useState({}); | ||||
const [fee, setFee] = useState(0); | const [fee, setFee] = useState(0); | ||||
@@ -113,7 +115,8 @@ const ApplicationDetailCard = ( | |||||
}, | }, | ||||
onSuccess: (responData) => { | onSuccess: (responData) => { | ||||
if (responData.success == true) { | if (responData.success == true) { | ||||
setIsPopUp(true); | |||||
let appIdList = [currentApplicationDetailData.id] | |||||
handlePaymentCheck(appIdList) | |||||
return; | return; | ||||
} | } | ||||
setErrorText("公共啟事申請已過期"); | setErrorText("公共啟事申請已過期"); | ||||
@@ -125,9 +128,49 @@ const ApplicationDetailCard = ( | |||||
function doPayment() { | function doPayment() { | ||||
setIsPopUp(false); | setIsPopUp(false); | ||||
navigate('/paymentPage', { state: { amount: fee, appIdList: [currentApplicationDetailData.id] } }); | |||||
let appIdList = [currentApplicationDetailData.id] | |||||
navigate('/paymentPage', { state: { amount: fee, appIdList: appIdList } }); | |||||
} | } | ||||
const handlePaymentCheck = (appIdList) => { | |||||
HttpUtils.post({ | |||||
url: UrlUtils.PAYMENT_CHECK, | |||||
params: { | |||||
appIds: appIdList | |||||
}, | |||||
onSuccess: (responseData) => { | |||||
const latestData = {}; | |||||
responseData.forEach(item => { | |||||
const { appId, timeDiff } = item; | |||||
if (latestData[appId] === undefined || timeDiff < latestData[appId].timeDiff) { | |||||
latestData[appId] = item; | |||||
} | |||||
}); | |||||
const latestDataObjects = Object.values(latestData); | |||||
const filteredData = latestDataObjects.filter(item => item.timeDiff > 20 && item.status !== "APPR"); | |||||
const filteredAppIds = filteredData.map(item => item.appId); | |||||
const appIdsNotInData = appIdList.filter(appId => !latestDataObjects.some(item => item.appId === appId)); | |||||
const combinedAppIdsArray = [...appIdsNotInData, ...filteredAppIds]; | |||||
const readyToPayment = appIdList.every(appId => combinedAppIdsArray.includes(appId)); | |||||
if (readyToPayment){ | |||||
setIsPopUp(true); | |||||
return; | |||||
}else{ | |||||
const appIdsInData = appIdList.filter(appId => !combinedAppIdsArray.some(item => item === appId)); | |||||
const HoldingApplication = latestDataObjects.filter(item => appIdsInData.includes(item.appId)); | |||||
const resultString = HoldingApplication.map(item => item.appNo).join(' , '); | |||||
setPaymentHoldedErrText(resultString); | |||||
// setPaymentHoldedErrText(intl.formatMessage({ id: 'MSG.paymentHolded' }, { appNo: record.appNo })); | |||||
setPaymentHoldedErr(true); | |||||
} | |||||
} | |||||
}); | |||||
}; | |||||
return ( | return ( | ||||
!onReady ? | !onReady ? | ||||
<LoadingComponent /> | <LoadingComponent /> | ||||
@@ -669,6 +712,33 @@ const ApplicationDetailCard = ( | |||||
</DialogActions> | </DialogActions> | ||||
</Dialog> | </Dialog> | ||||
</div> | </div> | ||||
<div> | |||||
<Dialog | |||||
open={paymentHoldedErr} | |||||
onClose={() => setPaymentHoldedErr(false)} | |||||
PaperProps={{ | |||||
sx: { | |||||
minWidth: '40vw', | |||||
maxWidth: { xs: '90vw', s: '90vw', m: '70vw', lg: '70vw' }, | |||||
maxHeight: { xs: '90vh', s: '70vh', m: '70vh', lg: '60vh' } | |||||
} | |||||
}} | |||||
> | |||||
<DialogTitle></DialogTitle> | |||||
<Typography variant="h4" style={{ paddingLeft: '24px' }}><FormattedMessage id="MSG.actionFail" /></Typography> | |||||
<DialogContent style={{ display: 'flex', }}> | |||||
<Stack direction="column" justifyContent="space-between"> | |||||
<div dangerouslySetInnerHTML={{ __html: intl.formatMessage({ id: 'MSG.paymentHolded' }, { appNo: paymentHoldedErrText }) }} /> | |||||
</Stack> | |||||
</DialogContent> | |||||
<DialogActions> | |||||
<Button onClick={() => setPaymentHoldedErr(false)} aria-label={intl.formatMessage({ id: 'close' })}> | |||||
<Typography variant="h5"> | |||||
<FormattedMessage id="close" /> | |||||
</Typography></Button> | |||||
</DialogActions> | |||||
</Dialog> | |||||
</div> | |||||
</form> | </form> | ||||
</MainCard > | </MainCard > | ||||
); | ); | ||||
@@ -19,6 +19,8 @@ export default function SubmittedTab({ rows }) { | |||||
const theme = useTheme(); | const theme = useTheme(); | ||||
const isMdOrLg = useMediaQuery(theme.breakpoints.up('md')); | const isMdOrLg = useMediaQuery(theme.breakpoints.up('md')); | ||||
const intl = useIntl(); | const intl = useIntl(); | ||||
const { locale } = intl; | |||||
const handleEditClick = (params) => () => { | const handleEditClick = (params) => () => { | ||||
navigate('/paymentPage/details/' + params.row.id); | navigate('/paymentPage/details/' + params.row.id); | ||||
@@ -52,7 +54,7 @@ export default function SubmittedTab({ rows }) { | |||||
width: isMdOrLg ? 'auto' : 160, | width: isMdOrLg ? 'auto' : 160, | ||||
flex: isMdOrLg ? 1 : undefined, | flex: isMdOrLg ? 1 : undefined, | ||||
renderCell: (params) => { | renderCell: (params) => { | ||||
return PaymentStatus.getStatus_Cht(params); | |||||
return locale === 'en' ? PaymentStatus.getStatus_Eng(params):PaymentStatus.getStatus_Cht(params); | |||||
} | } | ||||
}, | }, | ||||
{ | { | ||||
@@ -34,6 +34,10 @@ export default function SubmittedTab({ rows }) { | |||||
const [selectedCareOf, setSelectedCareOf] = React.useState(null); | const [selectedCareOf, setSelectedCareOf] = React.useState(null); | ||||
const [expiryDateErrText, setExpiryDateErrText] = React.useState(""); | const [expiryDateErrText, setExpiryDateErrText] = React.useState(""); | ||||
const [expiryDateErr, setExpiryDateErr] = React.useState(false); | const [expiryDateErr, setExpiryDateErr] = React.useState(false); | ||||
const [paymentHoldedErrText, setPaymentHoldedErrText] = React.useState(""); | |||||
const [paymentHoldedErr, setPaymentHoldedErr] = React.useState(false); | |||||
const theme = useTheme(); | const theme = useTheme(); | ||||
const isMdOrLg = useMediaQuery(theme.breakpoints.up('md')); | const isMdOrLg = useMediaQuery(theme.breakpoints.up('md')); | ||||
const intl = useIntl(); | const intl = useIntl(); | ||||
@@ -103,7 +107,8 @@ export default function SubmittedTab({ rows }) { | |||||
}, | }, | ||||
onSuccess: (responData) => { | onSuccess: (responData) => { | ||||
if (responData.success == true) { | if (responData.success == true) { | ||||
setIsPopUp(true); | |||||
// setIsPopUp(true); | |||||
handlePaymentCheck(appIdList) | |||||
return; | return; | ||||
} | } | ||||
let str = ""; | let str = ""; | ||||
@@ -114,8 +119,45 @@ export default function SubmittedTab({ rows }) { | |||||
setExpiryDateErr(true); | setExpiryDateErr(true); | ||||
} | } | ||||
}); | }); | ||||
}; | |||||
const handlePaymentCheck = (appIdList) => { | |||||
HttpUtils.post({ | |||||
url: UrlUtils.PAYMENT_CHECK, | |||||
params: { | |||||
appIds: appIdList | |||||
}, | |||||
onSuccess: (responseData) => { | |||||
const latestData = {}; | |||||
responseData.forEach(item => { | |||||
const { appId, timeDiff } = item; | |||||
if (latestData[appId] === undefined || timeDiff < latestData[appId].timeDiff) { | |||||
latestData[appId] = item; | |||||
} | |||||
}); | |||||
const latestDataObjects = Object.values(latestData); | |||||
const filteredData = latestDataObjects.filter(item => item.timeDiff > 20 && item.status !== "APPR"); | |||||
const filteredAppIds = filteredData.map(item => item.appId); | |||||
const appIdsNotInData = appIdList.filter(appId => !latestDataObjects.some(item => item.appId === appId)); | |||||
const combinedAppIdsArray = [...appIdsNotInData, ...filteredAppIds]; | |||||
const readyToPayment = appIdList.every(appId => combinedAppIdsArray.includes(appId)); | |||||
if (readyToPayment){ | |||||
setIsPopUp(true); | |||||
return; | |||||
}else{ | |||||
const appIdsInData = appIdList.filter(appId => !combinedAppIdsArray.some(item => item === appId)); | |||||
const HoldingApplication = latestDataObjects.filter(item => appIdsInData.includes(item.appId)); | |||||
const resultString = HoldingApplication.map(item => item.appNo).join(' , '); | |||||
setPaymentHoldedErrText(resultString); | |||||
// setPaymentHoldedErrText(intl.formatMessage({ id: 'MSG.paymentHolded' }, { appNo: record.appNo })); | |||||
setPaymentHoldedErr(true); | |||||
} | |||||
} | |||||
}); | |||||
}; | }; | ||||
const columns = [ | const columns = [ | ||||
@@ -405,6 +447,33 @@ export default function SubmittedTab({ rows }) { | |||||
</DialogActions> | </DialogActions> | ||||
</Dialog> | </Dialog> | ||||
</div> | </div> | ||||
<div> | |||||
<Dialog | |||||
open={paymentHoldedErr} | |||||
onClose={() => setPaymentHoldedErr(false)} | |||||
PaperProps={{ | |||||
sx: { | |||||
minWidth: '40vw', | |||||
maxWidth: { xs: '90vw', s: '90vw', m: '70vw', lg: '70vw' }, | |||||
maxHeight: { xs: '90vh', s: '70vh', m: '70vh', lg: '60vh' } | |||||
} | |||||
}} | |||||
> | |||||
<DialogTitle></DialogTitle> | |||||
<Typography variant="h4" style={{ paddingLeft: '24px' }}><FormattedMessage id="MSG.actionFail" /></Typography> | |||||
<DialogContent style={{ display: 'flex', }}> | |||||
<Stack direction="column" justifyContent="space-between"> | |||||
<div dangerouslySetInnerHTML={{ __html: intl.formatMessage({ id: 'MSG.paymentHolded' }, { appNo: paymentHoldedErrText }) }} /> | |||||
</Stack> | |||||
</DialogContent> | |||||
<DialogActions> | |||||
<Button onClick={() => setPaymentHoldedErr(false)} aria-label={intl.formatMessage({ id: 'close' })}> | |||||
<Typography variant="h5"> | |||||
<FormattedMessage id="close" /> | |||||
</Typography></Button> | |||||
</DialogActions> | |||||
</Dialog> | |||||
</div> | |||||
</> | </> | ||||
); | ); | ||||
@@ -303,13 +303,13 @@ const CustomFormWizard = (props) => { | |||||
selectedAddress4, selectedAddress5, | selectedAddress4, selectedAddress5, | ||||
termsAndConAccept, termsAndConNotAccept, fileList]) | termsAndConAccept, termsAndConNotAccept, fileList]) | ||||
useEffect(()=>{ | |||||
useEffect(() => { | |||||
setDistrictErrStr(""); | setDistrictErrStr(""); | ||||
if(selectedAddress5?.type === "hongKong"){ | |||||
if(selectedAddress4 ==null || selectedAddress4 == ""|| selectedAddress4 == {}) | |||||
if (selectedAddress5?.type === "hongKong") { | |||||
if (selectedAddress4 == null || selectedAddress4 == "" || selectedAddress4 == {}) | |||||
setDistrictErrStr(getRequiredErrStr("district")) | setDistrictErrStr(getRequiredErrStr("district")) | ||||
} | } | ||||
},[selectedAddress4, selectedAddress5]) | |||||
}, [selectedAddress4, selectedAddress5]) | |||||
useEffect(() => { | useEffect(() => { | ||||
props.step == 2 ? _onSubmit() : null; | props.step == 2 ? _onSubmit() : null; | ||||
@@ -541,11 +541,11 @@ const CustomFormWizard = (props) => { | |||||
return <Typography variant="errorMessage1">{errorMsg}</Typography> | return <Typography variant="errorMessage1">{errorMsg}</Typography> | ||||
} | } | ||||
function getMaxErrStr(num, fieldname){ | |||||
return displayErrorMsg(intl.formatMessage({ id: 'noMoreThenNWords' },{num:num, fieldname:fieldname?intl.formatMessage({ id: fieldname})+": ":""})); | |||||
function getMaxErrStr(num, fieldname) { | |||||
return displayErrorMsg(intl.formatMessage({ id: 'noMoreThenNWords' }, { num: num, fieldname: fieldname ? intl.formatMessage({ id: fieldname }) + ": " : "" })); | |||||
} | } | ||||
function getRequiredErrStr(fieldname){ | |||||
return displayErrorMsg(intl.formatMessage({ id: 'require'},{fieldname:fieldname?intl.formatMessage({ id: fieldname}):""})); | |||||
function getRequiredErrStr(fieldname) { | |||||
return displayErrorMsg(intl.formatMessage({ id: 'require' }, { fieldname: fieldname ? intl.formatMessage({ id: fieldname }) : "" })); | |||||
} | } | ||||
const formik = useFormik({ | const formik = useFormik({ | ||||
@@ -581,14 +581,17 @@ const CustomFormWizard = (props) => { | |||||
.matches(/^(?=.*[0-9])/, { message: displayErrorMsg(intl.formatMessage({ id: 'atLeast1Number' })) }) | .matches(/^(?=.*[0-9])/, { message: displayErrorMsg(intl.formatMessage({ id: 'atLeast1Number' })) }) | ||||
.matches(/^(?=.*[!@#%&])/, { message: displayErrorMsg(intl.formatMessage({ id: 'atLeast1SpecialChar' })) }), | .matches(/^(?=.*[!@#%&])/, { message: displayErrorMsg(intl.formatMessage({ id: 'atLeast1SpecialChar' })) }), | ||||
confirmPassword: yup.string().min(8, displayErrorMsg(intl.formatMessage({ id: 'atLeast8CharPassword' }))).required(displayErrorMsg(intl.formatMessage({ id: 'pleaseConfirmPassword' }))).oneOf([yup.ref('password'), null], displayErrorMsg(intl.formatMessage({ id: 'samePassword' }))), | confirmPassword: yup.string().min(8, displayErrorMsg(intl.formatMessage({ id: 'atLeast8CharPassword' }))).required(displayErrorMsg(intl.formatMessage({ id: 'pleaseConfirmPassword' }))).oneOf([yup.ref('password'), null], displayErrorMsg(intl.formatMessage({ id: 'samePassword' }))), | ||||
enName: yup.string().max(40, getMaxErrStr(40)).required(displayErrorMsg(intl.formatMessage({ id: 'userRequireEnglishName' }))), | |||||
chName: yup.string().max(6, getMaxErrStr(6)).required(displayErrorMsg(intl.formatMessage({ id: 'userRequireChineseName' }))), | |||||
enName: yup.string().max(40, getMaxErrStr(40)), | |||||
chName: yup.string().max(6, getMaxErrStr(6)).when('enName', { | |||||
is: (enName) => enName?false:true, | |||||
then: yup.string().required(displayErrorMsg(intl.formatMessage({ id: 'userRequireChineseName' }))) | |||||
}), | |||||
address1: yup.string().max(40, getMaxErrStr(40, "addressLine1")).required(displayErrorMsg(intl.formatMessage({ id: 'validateAddressLine1' }))), | address1: yup.string().max(40, getMaxErrStr(40, "addressLine1")).required(displayErrorMsg(intl.formatMessage({ id: 'validateAddressLine1' }))), | ||||
address2: yup.string().max(40, getMaxErrStr(40, "addressLine2")), | address2: yup.string().max(40, getMaxErrStr(40, "addressLine2")), | ||||
address3: yup.string().max(40, getMaxErrStr(40, "addressLine3")), | address3: yup.string().max(40, getMaxErrStr(40, "addressLine3")), | ||||
email: yup.string().email(displayErrorMsg(intl.formatMessage({ id: 'validEmailFormat' }))).max(128, getMaxErrStr(128)).required(displayErrorMsg(intl.formatMessage({ id: 'requireEmail' }))), | email: yup.string().email(displayErrorMsg(intl.formatMessage({ id: 'validEmailFormat' }))).max(128, getMaxErrStr(128)).required(displayErrorMsg(intl.formatMessage({ id: 'requireEmail' }))), | ||||
emailConfirm: yup.string().email(displayErrorMsg(intl.formatMessage({ id: 'validEmailFormat' }))).max(128, getMaxErrStr(128)).required(displayErrorMsg(intl.formatMessage({ id: 'requireEmail' }))).oneOf([yup.ref('email'), null], displayErrorMsg(intl.formatMessage({ id: 'validSameEmail' }))), | emailConfirm: yup.string().email(displayErrorMsg(intl.formatMessage({ id: 'validEmailFormat' }))).max(128, getMaxErrStr(128)).required(displayErrorMsg(intl.formatMessage({ id: 'requireEmail' }))).oneOf([yup.ref('email'), null], displayErrorMsg(intl.formatMessage({ id: 'validSameEmail' }))), | ||||
idNo: yup.string().required(displayErrorMsg(`${intl.formatMessage({ id: 'require' })}${selectedIdDocInputType}${intl.formatMessage({ id: 'number' })}`)) | |||||
idNo: yup.string().required(getRequiredErrStr('number')) | |||||
.matches(/^[aA-zZ0-9\s]+$/, { message: displayErrorMsg(`${selectedIdDocInputType}${intl.formatMessage({ id: 'noSpecialCharacter' })}`) }) | .matches(/^[aA-zZ0-9\s]+$/, { message: displayErrorMsg(`${selectedIdDocInputType}${intl.formatMessage({ id: 'noSpecialCharacter' })}`) }) | ||||
.matches(/^\S*$/, { message: displayErrorMsg(`${selectedIdDocInputType}${intl.formatMessage({ id: 'noSpace' })}`) }) | .matches(/^\S*$/, { message: displayErrorMsg(`${selectedIdDocInputType}${intl.formatMessage({ id: 'noSpace' })}`) }) | ||||
.test('checkIDCardFormat', displayErrorMsg(`${intl.formatMessage({ id: 'requiredValid' })}${selectedIdDocInputType}${intl.formatMessage({ id: 'number' })}`), function (value) { | .test('checkIDCardFormat', displayErrorMsg(`${intl.formatMessage({ id: 'requiredValid' })}${selectedIdDocInputType}${intl.formatMessage({ id: 'number' })}`), function (value) { | ||||
@@ -648,7 +651,7 @@ const CustomFormWizard = (props) => { | |||||
// faxCountryCode: yup.string().min(3,'請輸入3位數字'), | // faxCountryCode: yup.string().min(3,'請輸入3位數字'), | ||||
phone: yup.string().min(8, displayErrorMsg(intl.formatMessage({ id: 'requireAtLeast8Number' }))).required(displayErrorMsg(intl.formatMessage({ id: 'requireContactNumber' }))), | phone: yup.string().min(8, displayErrorMsg(intl.formatMessage({ id: 'requireAtLeast8Number' }))).required(displayErrorMsg(intl.formatMessage({ id: 'requireContactNumber' }))), | ||||
// fax: yup.string().min(8,'請輸入8位數字'), | // fax: yup.string().min(8,'請輸入8位數字'), | ||||
captchaField: yup.string().max(5, getMaxErrStr(5)).required(displayErrorMsg(intl.formatMessage({ id: 'requireVerify' }))),//.oneOf([captcha], displayErrorMsg('請輸入有效驗證')), | |||||
captchaField: yup.string().max(5, getMaxErrStr(5)).required(displayErrorMsg(intl.formatMessage({ id: 'requireVerify' }))),//.oneOf([captcha], displayErrorMsg('請輸入有效驗證')), | |||||
}), | }), | ||||
}); | }); | ||||
@@ -934,7 +937,7 @@ const CustomFormWizard = (props) => { | |||||
/> | /> | ||||
{formik.touched.idDocType && ( | {formik.touched.idDocType && ( | ||||
selectedIdDocType === null || selectedIdDocType?.type == null ? | selectedIdDocType === null || selectedIdDocType?.type == null ? | ||||
<FormHelperText error id="helper-text-idDocType-signup" sx={{fontSize:16,fontWeight: 'bold',}}> | |||||
<FormHelperText error id="helper-text-idDocType-signup" sx={{ fontSize: 16, fontWeight: 'bold', }}> | |||||
<FormattedMessage id="requireIdDocType" /> | <FormattedMessage id="requireIdDocType" /> | ||||
</FormHelperText> : '' | </FormHelperText> : '' | ||||
)} | )} | ||||
@@ -1067,12 +1070,17 @@ const CustomFormWizard = (props) => { | |||||
} | } | ||||
</Grid> | </Grid> | ||||
</Grid> | </Grid> | ||||
<Grid item xs={12} md={12}> | |||||
<Typography variant="subtitle1"> | |||||
<FormattedMessage id="registerNameLabel" /> | |||||
</Typography> | |||||
</Grid> | |||||
<Grid item xs={12} md={6}> | <Grid item xs={12} md={6}> | ||||
<Stack spacing={1}> | <Stack spacing={1}> | ||||
<InputLabel htmlFor="enName-signup"> | <InputLabel htmlFor="enName-signup"> | ||||
<Typography variant="pnspsFormHeader"> | <Typography variant="pnspsFormHeader"> | ||||
<FormattedMessage id="userEnglishName" /> | <FormattedMessage id="userEnglishName" /> | ||||
{selectedIdDocType.type === "CNID" ? "" : <span style={{ color: '#f10000' }}>*</span>} | |||||
{selectedIdDocType.type === "CNID" ? "" : <span style={{ color: '#f10000' }}></span>} | |||||
</Typography> | </Typography> | ||||
</InputLabel> | </InputLabel> | ||||
<OutlinedInput | <OutlinedInput | ||||
@@ -1105,7 +1113,7 @@ const CustomFormWizard = (props) => { | |||||
<InputLabel htmlFor="chName-signup"> | <InputLabel htmlFor="chName-signup"> | ||||
<Typography variant="pnspsFormHeader"> | <Typography variant="pnspsFormHeader"> | ||||
<FormattedMessage id="userChineseName" /> | <FormattedMessage id="userChineseName" /> | ||||
<span style={{ color: '#f10000' }}>*</span> | |||||
<span style={{ color: '#f10000' }}></span> | |||||
</Typography> | </Typography> | ||||
</InputLabel> | </InputLabel> | ||||
<OutlinedInput | <OutlinedInput | ||||
@@ -1199,7 +1207,7 @@ const CustomFormWizard = (props) => { | |||||
value={selectedAddress4} | value={selectedAddress4} | ||||
options={ComboData.district} | options={ComboData.district} | ||||
disabled={checkCountry} | disabled={checkCountry} | ||||
error={Boolean(districtErrStr!="")} | |||||
error={Boolean(districtErrStr != "")} | |||||
onBlur={formik.handleBlur} | onBlur={formik.handleBlur} | ||||
getOptionLabel={(option) => option.type ? intl.formatMessage({ id: option.type }) : ""} | getOptionLabel={(option) => option.type ? intl.formatMessage({ id: option.type }) : ""} | ||||
onChange={(event, newValue) => { | onChange={(event, newValue) => { | ||||
@@ -1252,7 +1260,7 @@ const CustomFormWizard = (props) => { | |||||
{formik.errors.address3} | {formik.errors.address3} | ||||
</FormHelperText> | </FormHelperText> | ||||
)} | )} | ||||
{districtErrStr!= "" && ( | |||||
{districtErrStr != "" && ( | |||||
<FormHelperText error > | <FormHelperText error > | ||||
{districtErrStr} | {districtErrStr} | ||||
</FormHelperText> | </FormHelperText> | ||||
@@ -1685,8 +1693,8 @@ const CustomFormWizard = (props) => { | |||||
<FormattedMessage id="idDocType" />: | <FormattedMessage id="idDocType" />: | ||||
</Typography> | </Typography> | ||||
<Typography variant="pnspsFormHeader" name="preview-idDocType"> | <Typography variant="pnspsFormHeader" name="preview-idDocType"> | ||||
{intl.formatMessage({ id: selectedIdDocType?.label??" " })} | |||||
{intl.formatMessage({ id: selectedIdDocType?.label ?? " " })} | |||||
</Typography> | </Typography> | ||||
</Stack> | </Stack> | ||||
</Grid> | </Grid> | ||||
@@ -20,13 +20,26 @@ const DashboardDefault = () => { | |||||
backgroundColor: '#0C489E', | backgroundColor: '#0C489E', | ||||
backgroundPosition: 'right' | backgroundPosition: 'right' | ||||
} | } | ||||
const getWelcomeMsg=()=>{ | |||||
var current = new Date() | |||||
var curHr = current.getHours() | |||||
if (curHr < 12) { | |||||
return "Good Morning" | |||||
} else if (curHr < 18) { | |||||
return "Good Afternoon" | |||||
} else { | |||||
//evening | |||||
return "Good Evening" | |||||
} | |||||
} | |||||
return ( | return ( | ||||
<Grid container sx={{minHeight: '87vh', backgroundColor: "backgroundColor.default"}} direction="column"> | <Grid container sx={{minHeight: '87vh', backgroundColor: "backgroundColor.default"}} direction="column"> | ||||
<Grid item xs={12}> | <Grid item xs={12}> | ||||
<div style={BackgroundHead}> | <div style={BackgroundHead}> | ||||
<Stack direction="row" height='70px' justifyContent="flex-start" alignItems="center"> | <Stack direction="row" height='70px' justifyContent="flex-start" alignItems="center"> | ||||
<Typography ml={15} color='#FFF' variant="h4" sx={{display: { xs: 'none', sm: 'none', md: 'block' }}}> | <Typography ml={15} color='#FFF' variant="h4" sx={{display: { xs: 'none', sm: 'none', md: 'block' }}}> | ||||
Morning, {userData.fullenName} | |||||
{getWelcomeMsg()}, {userData.fullenName} | |||||
</Typography> | </Typography> | ||||
</Stack> | </Stack> | ||||
</div> | </div> | ||||
@@ -35,6 +35,22 @@ const DashboardDefault = () => { | |||||
backgroundColor: '#0C489E', | backgroundColor: '#0C489E', | ||||
backgroundPosition: 'right' | backgroundPosition: 'right' | ||||
} | } | ||||
const { locale } = intl; | |||||
const getWelcomeMsg=()=>{ | |||||
var current = new Date() | |||||
var curHr = current.getHours() | |||||
if (curHr < 12) { | |||||
return <FormattedMessage id="welcomeMsg_am" /> | |||||
} else if (curHr < 18) { | |||||
return <FormattedMessage id="welcomeMsg_pm" /> | |||||
} else { | |||||
return <FormattedMessage id="welcomeMsg_night" /> | |||||
} | |||||
} | |||||
return ( | return ( | ||||
<Grid container sx={{ minHeight: '87vh' }} direction="column"> | <Grid container sx={{ minHeight: '87vh' }} direction="column"> | ||||
<Grid item xs={12} > | <Grid item xs={12} > | ||||
@@ -42,7 +58,7 @@ const DashboardDefault = () => { | |||||
<Stack direction="row" height='70px' justifyContent="flex-start" alignItems="center"> | <Stack direction="row" height='70px' justifyContent="flex-start" alignItems="center"> | ||||
{/* <Typography variant="h5">我的公共啟事</Typography> */} | {/* <Typography variant="h5">我的公共啟事</Typography> */} | ||||
<Typography color='#FFF' variant="h5" sx={{ ml: 10, display: { xs: 'none', sm: 'none', md: 'block' } }}> | <Typography color='#FFF' variant="h5" sx={{ ml: 10, display: { xs: 'none', sm: 'none', md: 'block' } }}> | ||||
{isORGLoggedIn() ? userData.fullenName : userData.fullchName}, <FormattedMessage id="welcomeMsg" /> | |||||
{isORGLoggedIn() ? userData.fullenName: (locale === 'en' ?userData.fullenName: userData.fullchName)}, {getWelcomeMsg()} | |||||
</Typography> | </Typography> | ||||
</Stack> | </Stack> | ||||
</div> | </div> | ||||
@@ -67,6 +67,7 @@ | |||||
"MSG.proofOutOfTime": "Response out of time, please apply again.", | "MSG.proofOutOfTime": "Response out of time, please apply again.", | ||||
"MSG.plzSelectApp": "Please select application", | "MSG.plzSelectApp": "Please select application", | ||||
"MSG.actionFail": "Action failed", | "MSG.actionFail": "Action failed", | ||||
"MSG.paymentHolded": "Application number {appNo} is currently in the process of payment. If the payment is unsuccessful, please try again after 20 minutes. We apologise for any inconvenience caused.", | |||||
"registerTitle1": "Become", | "registerTitle1": "Become", | ||||
"registerTitle2": "Gazette Notice", | "registerTitle2": "Gazette Notice", | ||||
@@ -96,7 +97,10 @@ | |||||
"onlinePaymentHistory": "Online Payment History", | "onlinePaymentHistory": "Online Payment History", | ||||
"setting": "Settings", | "setting": "Settings", | ||||
"companyOrUserRecord": "Company/Institutional User Records", | "companyOrUserRecord": "Company/Institutional User Records", | ||||
"welcomeMsg": "Good afternoon! Please select the required service.", | |||||
"welcomeMsg_am": "Good morning! Please select the required service.", | |||||
"welcomeMsg_pm": "Good afternoon! Please select the required service.", | |||||
"welcomeMsg_night": "Good evening! Please select the required service.", | |||||
"login": "Login", | "login": "Login", | ||||
"logout": "Logout", | "logout": "Logout", | ||||
@@ -147,6 +151,7 @@ | |||||
"registerNewBusinessUser": "Apply as organisation/company user", | "registerNewBusinessUser": "Apply as organisation/company user", | ||||
"becomeNewBusinessUser": "Become New Organisation/Company user", | "becomeNewBusinessUser": "Become New Organisation/Company user", | ||||
"userName": "Username", | "userName": "Username", | ||||
"registerNameLabel": "Please provide either an English name or a Chinese name, at a minimum.", | |||||
"userChineseName": "Chinese Name", | "userChineseName": "Chinese Name", | ||||
"userEnglishName": "English Name", | "userEnglishName": "English Name", | ||||
"userContactName": "Name", | "userContactName": "Name", | ||||
@@ -256,7 +261,7 @@ | |||||
"mainlandIDCard": "Mainland ID card", | "mainlandIDCard": "Mainland ID card", | ||||
"proCert": "Professional Practice Certificate", | "proCert": "Professional Practice Certificate", | ||||
"idDocType": "Document Category", | "idDocType": "Document Category", | ||||
"requireIdDocType": "Please enter the document type", | |||||
"requireIdDocType": "Please select the document type", | |||||
"idDocNumber": "ID number", | "idDocNumber": "ID number", | ||||
"requireIdDocNumber": "Please enter the document ID", | "requireIdDocNumber": "Please enter the document ID", | ||||
"requiredNumberInQuote": "Please enter the numbers or letters in brackets", | "requiredNumberInQuote": "Please enter the numbers or letters in brackets", | ||||
@@ -354,7 +359,7 @@ | |||||
"publicNoticeDetailTitle": "Public Notice Application Information", | "publicNoticeDetailTitle": "Public Notice Application Information", | ||||
"applyPerson": "Applicant", | "applyPerson": "Applicant", | ||||
"applyStatus": "Application Status", | |||||
"applyStatus": "App. Status", | |||||
"gazetteCount": "Gazette issues number", | "gazetteCount": "Gazette issues number", | ||||
"gazetteCount2" :"Gazette issues number / Remarks", | "gazetteCount2" :"Gazette issues number / Remarks", | ||||
"gazetteCount2_1" :"Care Of / Remarks", | "gazetteCount2_1" :"Care Of / Remarks", | ||||
@@ -391,6 +396,8 @@ | |||||
"upload": "Upload", | "upload": "Upload", | ||||
"actionFail": "Action failed: Please check the content and submit the reply again", | "actionFail": "Action failed: Please check the content and submit the reply again", | ||||
"issueInvalidMsg": "Action failed: The Gazette Issue invalid, please apply again", | "issueInvalidMsg": "Action failed: The Gazette Issue invalid, please apply again", | ||||
"singleCol":"Single Column", | |||||
"doubleCol":"Double Column", | |||||
"transactionNo": "Transaction number", | "transactionNo": "Transaction number", | ||||
"transactionDate": "Transaction date", | "transactionDate": "Transaction date", | ||||
@@ -436,7 +443,7 @@ | |||||
"noRecordFound": "No record found", | "noRecordFound": "No record found", | ||||
"rowsPerPage": "Rows Per Page", | "rowsPerPage": "Rows Per Page", | ||||
"date" : "Date", | "date" : "Date", | ||||
"keyword": "Key word", | |||||
"keyword": "Keyword", | |||||
"dateFrom": "Date(From)", | "dateFrom": "Date(From)", | ||||
"dateTo": "Date(To)", | "dateTo": "Date(To)", | ||||
"of": "of", | "of": "of", | ||||
@@ -66,7 +66,8 @@ | |||||
"MSG.proofOutOfTime": "回覆逾时,请重新申请。", | "MSG.proofOutOfTime": "回覆逾时,请重新申请。", | ||||
"MSG.plzSelectApp": "请选择公共启事。", | "MSG.plzSelectApp": "请选择公共启事。", | ||||
"MSG.actionFail": "行动失败", | "MSG.actionFail": "行动失败", | ||||
"MSG.paymentHolded": "申请编号 {appNo} 已正在付款的流程中,如相关付款没有成功,请于20分钟后再尝试付款,不便之处,请见谅!", | |||||
"registerTitle1": "立即成为", | "registerTitle1": "立即成为", | ||||
"registerTitle2": "宪报刊登公共启事", | "registerTitle2": "宪报刊登公共启事", | ||||
"registerTitle3": "用户", | "registerTitle3": "用户", | ||||
@@ -95,7 +96,9 @@ | |||||
"onlinePaymentHistory": "网上付款记录", | "onlinePaymentHistory": "网上付款记录", | ||||
"setting": "设置", | "setting": "设置", | ||||
"companyOrUserRecord": "公司/机构用户记录", | "companyOrUserRecord": "公司/机构用户记录", | ||||
"welcomeMsg": "午安! 请选择所需服务。", | |||||
"welcomeMsg_am": "早安! 请选择所需服务。", | |||||
"welcomeMsg_pm": "午安! 请选择所需服务。", | |||||
"welcomeMsg_night": "晚安! 请选择所需服务。", | |||||
"login": "登录", | "login": "登录", | ||||
"logout": "登出", | "logout": "登出", | ||||
@@ -142,6 +145,7 @@ | |||||
"registerNewBusinessUser": "申请机构/公司用户", | "registerNewBusinessUser": "申请机构/公司用户", | ||||
"becomeNewBusinessUser": "成为新的机构/公司用户", | "becomeNewBusinessUser": "成为新的机构/公司用户", | ||||
"userName": "用户名称", | "userName": "用户名称", | ||||
"registerNameLabel": "请至少输入英文姓名或中文姓名。", | |||||
"userChineseName": "中文姓名", | "userChineseName": "中文姓名", | ||||
"userEnglishName": "英文姓名", | "userEnglishName": "英文姓名", | ||||
"userContactName": "姓名", | "userContactName": "姓名", | ||||
@@ -251,7 +255,7 @@ | |||||
"mainlandIDCard": "内地身份证", | "mainlandIDCard": "内地身份证", | ||||
"proCert": "专业执业证书", | "proCert": "专业执业证书", | ||||
"idDocType": "证件类别", | "idDocType": "证件类别", | ||||
"requireIdDocType": "请输入证件类别", | |||||
"requireIdDocType": "请选择证件类别", | |||||
"idDocNumber": "证件号码", | "idDocNumber": "证件号码", | ||||
"requireIdDocNumber": "请输入证件号码", | "requireIdDocNumber": "请输入证件号码", | ||||
"requiredNumberInQuote": "请输入括号内的数字或字母", | "requiredNumberInQuote": "请输入括号内的数字或字母", | ||||
@@ -386,6 +390,8 @@ | |||||
"upload": "上载", | "upload": "上载", | ||||
"actionFail": "行动失败: 请检查内容并再次提交回覆", | "actionFail": "行动失败: 请检查内容并再次提交回覆", | ||||
"issueInvalidMsg": "行动失败: 无效宪报期数,请重新申请", | "issueInvalidMsg": "行动失败: 无效宪报期数,请重新申请", | ||||
"singleCol":"一格位", | |||||
"doubleCol":"二格位", | |||||
"transactionNo": "交易号码", | "transactionNo": "交易号码", | ||||
"transactionDate": "交易日期", | "transactionDate": "交易日期", | ||||
@@ -66,6 +66,7 @@ | |||||
"MSG.proofOutOfTime": "回覆逾時,請重新申請。", | "MSG.proofOutOfTime": "回覆逾時,請重新申請。", | ||||
"MSG.plzSelectApp": "請選擇公共啟事。", | "MSG.plzSelectApp": "請選擇公共啟事。", | ||||
"MSG.actionFail": "行動失敗", | "MSG.actionFail": "行動失敗", | ||||
"MSG.paymentHolded": "申請編號 {appNo} 已正在付款的流程中,如相關付款沒有成功,請於20分鐘後再嘗試付款,不便之處,請見諒!", | |||||
"registerTitle1": "立即成為", | "registerTitle1": "立即成為", | ||||
"registerTitle2": "憲報刊登公共啟事", | "registerTitle2": "憲報刊登公共啟事", | ||||
@@ -95,7 +96,9 @@ | |||||
"onlinePaymentHistory": "網上付款記錄", | "onlinePaymentHistory": "網上付款記錄", | ||||
"setting": "設定", | "setting": "設定", | ||||
"companyOrUserRecord": "公司/機構用戶記錄", | "companyOrUserRecord": "公司/機構用戶記錄", | ||||
"welcomeMsg": "午安! 請選擇所需服務。", | |||||
"welcomeMsg_am": "早安! 請選擇所需服務。", | |||||
"welcomeMsg_pm": "午安! 請選擇所需服務。", | |||||
"welcomeMsg_night": "晚安! 請選擇所需服務。", | |||||
"login": "登入", | "login": "登入", | ||||
"logout": "登出", | "logout": "登出", | ||||
@@ -145,6 +148,7 @@ | |||||
"registerNewBusinessUser": "申請機構/公司用戶", | "registerNewBusinessUser": "申請機構/公司用戶", | ||||
"becomeNewBusinessUser": "成為新的機構/公司用戶", | "becomeNewBusinessUser": "成為新的機構/公司用戶", | ||||
"userName": "用戶名稱", | "userName": "用戶名稱", | ||||
"registerNameLabel": "請至少輸入英文姓名或中文姓名。", | |||||
"userChineseName": "中文姓名", | "userChineseName": "中文姓名", | ||||
"userEnglishName": "英文姓名", | "userEnglishName": "英文姓名", | ||||
"userContactName": "姓名", | "userContactName": "姓名", | ||||
@@ -254,7 +258,7 @@ | |||||
"mainlandIDCard": "內地身份證", | "mainlandIDCard": "內地身份證", | ||||
"proCert": "專業執業證書", | "proCert": "專業執業證書", | ||||
"idDocType": "證件類別", | "idDocType": "證件類別", | ||||
"requireIdDocType": "請輸入證件類別", | |||||
"requireIdDocType": "請選擇證件類別", | |||||
"idDocNumber": "證件號碼", | "idDocNumber": "證件號碼", | ||||
"requireIdDocNumber": "請輸入證件號碼", | "requireIdDocNumber": "請輸入證件號碼", | ||||
"requiredNumberInQuote": "請輸入括號內的數字或字母", | "requiredNumberInQuote": "請輸入括號內的數字或字母", | ||||
@@ -389,6 +393,8 @@ | |||||
"upload": "上載", | "upload": "上載", | ||||
"actionFail": "行動失敗: 請檢查內容並再次提交回覆", | "actionFail": "行動失敗: 請檢查內容並再次提交回覆", | ||||
"issueInvalidMsg": "行動失敗: 無效憲報期數,請重新申請", | "issueInvalidMsg": "行動失敗: 無效憲報期數,請重新申請", | ||||
"singleCol":"一格位", | |||||
"doubleCol":"二格位", | |||||
"transactionNo": "交易號碼", | "transactionNo": "交易號碼", | ||||
"transactionDate": "交易日期", | "transactionDate": "交易日期", | ||||
@@ -133,12 +133,13 @@ export const PROOF_CHECK_PRICE = apiPath+'/proof/check-price';//GET | |||||
export const GET_PROOF_PAY = apiPath+'/proof/pay-details';//GET | export const GET_PROOF_PAY = apiPath+'/proof/pay-details';//GET | ||||
export const CANCEL_PROOF = apiPath+'/proof/cancel';//GET | export const CANCEL_PROOF = apiPath+'/proof/cancel';//GET | ||||
//payment | |||||
export const PAYMENT_CREATE = apiPath+'/payment/create';//POST | export const PAYMENT_CREATE = apiPath+'/payment/create';//POST | ||||
export const PAYMENT_SAVE = apiPath+'/payment/save';//POST | export const PAYMENT_SAVE = apiPath+'/payment/save';//POST | ||||
export const PAYMENT_LIST = apiPath+'/payment/list';//GET | export const PAYMENT_LIST = apiPath+'/payment/list';//GET | ||||
export const PAYMENT_LOAD = apiPath+'/payment/load';//GET | export const PAYMENT_LOAD = apiPath+'/payment/load';//GET | ||||
export const PAYMENT_APP_LIST = apiPath+'/payment/applist';//POST | export const PAYMENT_APP_LIST = apiPath+'/payment/applist';//POST | ||||
export const PAYMENT_CHECK = apiPath+'/payment/check-payment';//GET | |||||
export const PAYMENT_LIMIT_SETTING_LIST = apiPath+'/settings/payment';//GET | export const PAYMENT_LIMIT_SETTING_LIST = apiPath+'/settings/payment';//GET | ||||
export const PAYMENT_AVAILABLE_PAYMENT = paymentPath+'/api/payment/availability';//POST | export const PAYMENT_AVAILABLE_PAYMENT = paymentPath+'/api/payment/availability';//POST | ||||