Skip to content

Commit 1288fde

Browse files
authored
feat (OPE-942): Show QR code on transferring and bridging funding flows (#1368)
* feat: add QR code modal and copy functionality to FundingDescription * feat(ui): show QR code & copy address in FundingDescription and use across bridge/transfer flows * fix(ui): always enable copy and QR code modal in FundingDescription
1 parent f22a6fb commit 1288fde

4 files changed

Lines changed: 167 additions & 138 deletions

File tree

frontend/components/Bridge/BridgeOnEvm/BridgeOnEvm.tsx

Lines changed: 36 additions & 26 deletions
Original file line numberDiff line numberDiff line change
@@ -2,6 +2,7 @@ import { Flex, Typography } from 'antd';
22

33
import { BackButton, CardFlex, FundingDescription } from '@/components/ui';
44
import { MiddlewareChain } from '@/constants';
5+
import { useMasterWalletContext } from '@/hooks';
56
import { CrossChainTransferDetails } from '@/types/Bridge';
67

78
import { GetBridgeRequirementsParams } from '../types';
@@ -34,31 +35,40 @@ export const BridgeOnEvm = ({
3435
getBridgeRequirementsParams,
3536
updateQuoteId,
3637
updateCrossChainTransferDetails,
37-
}: BridgeOnEvmProps) => (
38-
<Flex justify="center">
39-
<CardFlex $noBorder $onboarding className="p-8">
40-
<BackButton onPrev={onPrev} />
41-
<Title level={3} className="mt-16">
42-
Bridge Crypto from {FROM_CHAIN_NAME}
43-
</Title>
44-
<Title level={5} className="mt-12 mb-8">
45-
Step 1. Send Funds
46-
</Title>
47-
<Text className="text-base text-lighter">{bridgeFromDescription}</Text>
38+
}: BridgeOnEvmProps) => {
39+
const { masterEoa } = useMasterWalletContext();
40+
const address = masterEoa?.address;
4841

49-
<FundingDescription
50-
chainName={FROM_CHAIN_NAME}
51-
chainImage={FROM_CHAIN_IMAGE}
52-
isMainnet
53-
/>
42+
return (
43+
<Flex justify="center">
44+
<CardFlex $noBorder $onboarding className="p-8">
45+
<BackButton onPrev={onPrev} />
46+
<Title level={3} className="mt-16">
47+
Bridge Crypto from {FROM_CHAIN_NAME}
48+
</Title>
49+
<Title level={5} className="mt-12 mb-8">
50+
Step 1. Send Funds
51+
</Title>
52+
<Text className="text-base text-lighter">{bridgeFromDescription}</Text>
5453

55-
<DepositForBridging
56-
bridgeToChain={bridgeToChain}
57-
getBridgeRequirementsParams={getBridgeRequirementsParams}
58-
updateQuoteId={updateQuoteId}
59-
updateCrossChainTransferDetails={updateCrossChainTransferDetails}
60-
onNext={onNext}
61-
/>
62-
</CardFlex>
63-
</Flex>
64-
);
54+
{address && (
55+
<FundingDescription
56+
address={address}
57+
chainName={FROM_CHAIN_NAME}
58+
chainImage={FROM_CHAIN_IMAGE}
59+
isMainnet
60+
style={{ marginTop: 32 }}
61+
/>
62+
)}
63+
64+
<DepositForBridging
65+
bridgeToChain={bridgeToChain}
66+
getBridgeRequirementsParams={getBridgeRequirementsParams}
67+
updateQuoteId={updateQuoteId}
68+
updateCrossChainTransferDetails={updateCrossChainTransferDetails}
69+
onNext={onNext}
70+
/>
71+
</CardFlex>
72+
</Flex>
73+
);
74+
};

frontend/components/PearlWallet/components/TransferCryptoFromExternalWallet.tsx

Lines changed: 9 additions & 59 deletions
Original file line numberDiff line numberDiff line change
@@ -1,22 +1,19 @@
11
import { Button, Flex, TableColumnsType, Typography } from 'antd';
22
import { kebabCase } from 'lodash';
33
import Image from 'next/image';
4-
import { useCallback } from 'react';
54
import { LuInfo } from 'react-icons/lu';
6-
import { TbCopy, TbWallet } from 'react-icons/tb';
75
import { styled } from 'styled-components';
86

97
import {
108
Alert,
119
BackButton,
1210
CardFlex,
13-
InfoTooltip,
11+
FundingDescription,
1412
Table,
1513
} from '@/components/ui';
1614
import { COLOR, TokenSymbolConfigMap } from '@/constants';
17-
import { useMessageApi } from '@/context/MessageProvider';
1815
import { Address, AvailableAsset, Nullable } from '@/types';
19-
import { copyToClipboard, formatNumber } from '@/utils';
16+
import { formatNumber } from '@/utils';
2017

2118
const { Title, Text, Paragraph } = Typography;
2219

@@ -46,59 +43,6 @@ const DoesNotTrackIncomingTransfers = () => (
4643
</Flex>
4744
);
4845

49-
type TransferDetailsProps = { chainName: string; address?: Address };
50-
const TransferDetails = ({ chainName, address }: TransferDetailsProps) => {
51-
const message = useMessageApi();
52-
53-
const handleCopyAddress = useCallback(() => {
54-
if (!address) return;
55-
copyToClipboard(address).then(() => message.success('Address copied!'));
56-
}, [address, message]);
57-
58-
return (
59-
<YouPayContainer vertical gap={24}>
60-
<Flex vertical gap={8}>
61-
<Text className="text-sm text-neutral-tertiary">On</Text>
62-
<Flex gap={8} align="center">
63-
<Image
64-
src={`/chains/${kebabCase(chainName)}-chain.png`}
65-
alt={chainName}
66-
width={20}
67-
height={20}
68-
/>
69-
<Text>{chainName} Chain</Text>
70-
</Flex>
71-
</Flex>
72-
73-
<Flex vertical gap={8}>
74-
<Text className="text-sm text-neutral-tertiary">From</Text>
75-
<Flex gap={8} align="center">
76-
<TbWallet size={20} color={COLOR.TEXT_NEUTRAL_TERTIARY} />
77-
<Text>Your external wallet</Text>
78-
<InfoTooltip placement="top" iconColor={COLOR.BLACK}>
79-
<Paragraph className="text-sm m-0">
80-
This is the wallet you use outside Pearl
81-
</Paragraph>
82-
</InfoTooltip>
83-
</Flex>
84-
</Flex>
85-
86-
<Flex vertical gap={8}>
87-
<Text className="text-sm text-neutral-tertiary">To Pearl Wallet</Text>
88-
<Flex gap={8} align="center">
89-
<TbWallet size={20} color={COLOR.TEXT_NEUTRAL_TERTIARY} />
90-
<Text>{address}</Text>
91-
</Flex>
92-
<Flex>
93-
<Button onClick={handleCopyAddress} size="small" icon={<TbCopy />}>
94-
Copy
95-
</Button>
96-
</Flex>
97-
</Flex>
98-
</YouPayContainer>
99-
);
100-
};
101-
10246
const getColumns = (
10347
requestedColumnText = 'Requested Deposit Amount',
10448
): TableColumnsType<AvailableAsset> =>
@@ -166,7 +110,13 @@ export const TransferCryptoFromExternalWallet = ({
166110
</Flex>
167111

168112
<ChainWarningAlert chainName={chainName} />
169-
{address && <TransferDetails chainName={chainName} address={address} />}
113+
{address && (
114+
<FundingDescription
115+
address={address}
116+
chainName={chainName}
117+
chainImage={`/chains/${kebabCase(chainName)}-chain.png`}
118+
/>
119+
)}
170120
<Table<AvailableAsset>
171121
dataSource={tokensToDeposit}
172122
columns={getColumns(requestedColumnText)}

frontend/components/SetupPage/FundYourAgent/TransferFunds.tsx

Lines changed: 11 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -16,6 +16,7 @@ import { ChainImageMap, EvmChainName, TokenSymbol } from '@/constants';
1616
import { SetupScreen } from '@/enums';
1717
import {
1818
useMasterSafeCreationAndTransfer,
19+
useMasterWalletContext,
1920
useServices,
2021
useSetup,
2122
} from '@/hooks';
@@ -36,7 +37,7 @@ const FinishingSetupModal = () => (
3637

3738
export const TransferFunds = () => {
3839
const { goto: gotoSetup } = useSetup();
39-
40+
const { masterEoa } = useMasterWalletContext();
4041
const { selectedAgentConfig } = useServices();
4142
const { isFullyFunded, tokensFundingStatus } = useTokensFundingStatus();
4243
const { initialTokenRequirements, isLoading } =
@@ -55,6 +56,7 @@ export const TransferFunds = () => {
5556
const { evmHomeChainId } = selectedAgentConfig;
5657
const chainName = EvmChainName[evmHomeChainId];
5758
const chainImage = ChainImageMap[evmHomeChainId];
59+
const masterEoaAddress = masterEoa?.address;
5860

5961
const tokensDataSource = useMemo(() => {
6062
return (initialTokenRequirements ?? []).map((token) => {
@@ -120,7 +122,14 @@ export const TransferFunds = () => {
120122
message={`Only send on ${chainName} Chain — funds on other networks are unrecoverable.`}
121123
/>
122124

123-
<FundingDescription chainName={chainName} chainImage={chainImage} />
125+
{masterEoaAddress && (
126+
<FundingDescription
127+
address={masterEoaAddress}
128+
chainName={chainName}
129+
chainImage={chainImage}
130+
style={{ marginTop: 32 }}
131+
/>
132+
)}
124133

125134
<TokenRequirementsTable
126135
isLoading={isLoading}

0 commit comments

Comments
 (0)