Skip to content

Commit ee62fed

Browse files
committed
feat(suite): display multitoken amount
1 parent d29333b commit ee62fed

File tree

19 files changed

+355
-301
lines changed

19 files changed

+355
-301
lines changed

packages/components/src/components/typography/Link/Link.tsx

Lines changed: 5 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -9,13 +9,14 @@ import { Icon, IconName } from '../../Icon/Icon';
99
type AProps = {
1010
$type?: TypographyStyle;
1111
$variant?: 'default' | 'nostyle' | 'underline';
12+
$color?: string;
1213
};
1314

1415
const A = styled.a<AProps>`
1516
${({ $type }) => ($type ? typography[$type] : typography.body)}
1617
text-decoration: none;
1718
cursor: pointer;
18-
color: ${({ theme }) => theme.textDefault};
19+
color: ${({ $color, theme }) => $color || theme.textDefault};
1920
font-weight: 500;
2021
display: inline-flex;
2122
align-items: center;
@@ -56,6 +57,7 @@ interface LinkProps {
5657
className?: string;
5758
variant?: 'default' | 'nostyle' | 'underline'; // Todo: refactor, variant has different meaning in our design system
5859
icon?: IconName;
60+
color?: string;
5961
'data-testid'?: string;
6062
}
6163

@@ -67,6 +69,7 @@ const Link = ({
6769
onClick,
6870
'data-testid': dataTest,
6971
children,
72+
color,
7073
className,
7174
variant,
7275
}: LinkProps) => {
@@ -85,6 +88,7 @@ const Link = ({
8588
$type={type}
8689
$variant={variant}
8790
className={className}
91+
$color={color}
8892
>
8993
{children}
9094
{icon && <Icon size={iconSize} name={icon} />}

packages/suite/src/components/suite/CoinBalance.tsx

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -4,13 +4,15 @@ import { FormattedCryptoAmount } from 'src/components/suite';
44
interface CoinBalanceProps {
55
value: string;
66
symbol: Account['symbol'] | (string & {});
7+
justifyContent?: 'flex-end' | 'flex-start';
78
}
89

9-
export const CoinBalance = ({ value, symbol }: CoinBalanceProps) => (
10+
export const CoinBalance = ({ value, symbol, justifyContent }: CoinBalanceProps) => (
1011
<FormattedCryptoAmount
1112
value={value}
1213
symbol={symbol}
1314
isBalance
15+
justifyContent={justifyContent}
1416
data-testid={`@wallet/coin-balance/value-${symbol}`}
1517
/>
1618
);

packages/suite/src/components/suite/FormattedCryptoAmount.tsx

Lines changed: 14 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -8,6 +8,7 @@ import {
88
networkAmountToSmallestUnit,
99
} from '@suite-common/wallet-utils';
1010
import { isSignValuePositive } from '@suite-common/formatters';
11+
import { Row } from '@trezor/components';
1112

1213
import { useBitcoinAmountUnit } from 'src/hooks/wallet/useBitcoinAmountUnit';
1314
import { useSelector } from 'src/hooks/suite';
@@ -17,10 +18,6 @@ import { BlurUrls } from 'src/views/wallet/tokens/common/BlurUrls';
1718

1819
import { RedactNumericalValue } from './RedactNumericalValue';
1920

20-
const Container = styled.span`
21-
max-width: 100%;
22-
`;
23-
2421
const Value = styled.span`
2522
font-variant-numeric: tabular-nums;
2623
overflow: hidden;
@@ -35,6 +32,7 @@ export interface FormattedCryptoAmountProps {
3532
disableHiddenPlaceholder?: boolean;
3633
isRawString?: boolean;
3734
'data-testid'?: string;
35+
justifyContent?: 'flex-end' | 'flex-start';
3836
className?: string;
3937
}
4038

@@ -45,8 +43,8 @@ export const FormattedCryptoAmount = ({
4543
signValue,
4644
disableHiddenPlaceholder,
4745
isRawString,
46+
justifyContent = 'flex-end',
4847
'data-testid': dataTest,
49-
className,
5048
}: FormattedCryptoAmountProps) => {
5149
const locale = useSelector(selectLanguage);
5250

@@ -97,23 +95,25 @@ export const FormattedCryptoAmount = ({
9795
}
9896

9997
const content = (
100-
<Container className={className}>
101-
{!!signValue && <Sign value={signValue} />}
102-
<Value data-testid={dataTest}>
103-
<RedactNumericalValue value={formattedValue} />
104-
</Value>
98+
<Row width="100%" flexWrap="nowrap" justifyContent={justifyContent} gap={4}>
99+
<Row>
100+
{!!signValue && <Sign value={signValue} />}
101+
<Value data-testid={dataTest}>
102+
<RedactNumericalValue value={formattedValue} />
103+
</Value>
104+
</Row>
105105
{formattedSymbol && (
106106
<>
107107
{' '}
108-
<BlurUrls text={formattedSymbol} />
108+
<BlurUrls text={formattedSymbol} />{' '}
109109
</>
110110
)}
111-
</Container>
111+
</Row>
112112
);
113113

114114
if (disableHiddenPlaceholder) {
115-
return content;
115+
return <>{content}</>;
116116
}
117117

118-
return <HiddenPlaceholder className={className}>{content}</HiddenPlaceholder>;
118+
return <HiddenPlaceholder>{content}</HiddenPlaceholder>;
119119
};
Lines changed: 71 additions & 48 deletions
Original file line numberDiff line numberDiff line change
@@ -1,47 +1,15 @@
1-
import styled from 'styled-components';
1+
import { useTheme } from 'styled-components';
22

33
import { SignValue } from '@suite-common/suite-types';
4-
import { getNftTokenId } from '@suite-common/wallet-utils';
4+
import { getNftTokenId, isNftMultitokenTransfer } from '@suite-common/wallet-utils';
55
import { TokenTransfer } from '@trezor/connect';
6-
import { variables } from '@trezor/components';
6+
import { Column, Flex, Row, Text } from '@trezor/components';
77

8-
import { HiddenPlaceholder, Sign } from 'src/components/suite';
8+
import { HiddenPlaceholder, Sign, Translation } from 'src/components/suite';
99
// importing directly, otherwise unit tests fail, seems to be a styled-components issue
1010
import { TrezorLink } from 'src/components/suite/TrezorLink';
1111
import { useSelector } from 'src/hooks/suite/useSelector';
12-
13-
const Container = styled.div`
14-
max-width: 100%;
15-
display: flex;
16-
`;
17-
18-
const Symbol = styled.div`
19-
white-space: nowrap;
20-
overflow: hidden;
21-
text-overflow: ellipsis;
22-
max-width: 120px;
23-
`;
24-
25-
const StyledTrezorLink = styled(TrezorLink)`
26-
color: ${({ theme }) => theme.legacy.TYPE_GREEN};
27-
text-decoration: underline;
28-
display: flex;
29-
font-size: ${variables.FONT_SIZE.TINY};
30-
line-height: initial;
31-
align-items: center;
32-
`;
33-
34-
const NoLink = styled.div`
35-
display: flex;
36-
`;
37-
38-
const Id = styled.div`
39-
white-space: nowrap;
40-
overflow: hidden;
41-
text-overflow: ellipsis;
42-
max-width: 145px;
43-
`;
44-
12+
import { Id } from 'src/components/wallet/TransactionItem/CommonComponents';
4513
export interface FormattedNftAmountProps {
4614
transfer: TokenTransfer;
4715
signValue?: SignValue;
@@ -56,6 +24,7 @@ export const FormattedNftAmount = ({
5624
isWithLink,
5725
}: FormattedNftAmountProps) => {
5826
const id = getNftTokenId(transfer);
27+
const theme = useTheme();
5928

6029
const { selectedAccount } = useSelector(state => state.wallet);
6130
const { network } = selectedAccount;
@@ -64,26 +33,80 @@ export const FormattedNftAmount = ({
6433
? `${network?.explorer.nft}/${transfer.contract}/${id}`
6534
: undefined;
6635

67-
const idComponent = <Id>{id}</Id>;
68-
const symbolComponent = transfer.symbol ? <Symbol>&nbsp;{transfer.symbol}</Symbol> : null;
36+
const symbolComponent = transfer.symbol ? (
37+
<Text maxWidth="120px" ellipsisLineCount={1} textWrap="nowrap">
38+
{transfer.symbol}
39+
</Text>
40+
) : null;
41+
42+
const isMultitoken = isNftMultitokenTransfer(transfer);
43+
44+
if (isMultitoken) {
45+
const tokens = transfer.multiTokenValues;
46+
47+
return (
48+
<HiddenPlaceholder>
49+
<Column alignItems="flex-start">
50+
{tokens?.map((token, index) => (
51+
<Row key={`${token.id}-${index}`} gap={4}>
52+
<Row>
53+
{signValue ? <Sign value={signValue} /> : null}
54+
{token.value}x
55+
</Row>
56+
<Row gap={4}>
57+
{isWithLink && network?.networkType === 'ethereum' ? (
58+
<>
59+
<Row>
60+
<Translation id="TR_TOKEN_ID" />:
61+
</Row>
62+
<TrezorLink
63+
href={`${network?.explorer.nft}/${transfer.contract}/${token.id}`}
64+
color={theme.textSecondaryHighlight}
65+
variant="underline"
66+
type="label"
67+
>
68+
<Id id={token.id} />
69+
</TrezorLink>
70+
</>
71+
) : (
72+
<Row gap={4}>
73+
<Row>
74+
<Translation id="TR_TOKEN_ID" />:
75+
</Row>
76+
<Id id={token.id} />
77+
</Row>
78+
)}
79+
</Row>
80+
</Row>
81+
))}
82+
</Column>
83+
</HiddenPlaceholder>
84+
);
85+
}
6986

7087
return (
7188
<HiddenPlaceholder>
72-
<Container className={className}>
89+
<Flex className={className}>
7390
{signValue ? <Sign value={signValue} /> : null}
74-
ID:&nbsp;
91+
<Translation id="TR_TOKEN_ID" />
92+
:&nbsp;
7593
{isWithLink ? (
76-
<StyledTrezorLink href={explorerUrl}>
77-
{idComponent}
94+
<TrezorLink
95+
href={explorerUrl}
96+
color={theme.textSecondaryHighlight}
97+
variant="underline"
98+
type="label"
99+
>
100+
<Id id={id} />
78101
{symbolComponent}
79-
</StyledTrezorLink>
102+
</TrezorLink>
80103
) : (
81-
<NoLink>
82-
{idComponent}
104+
<Row gap={4}>
105+
<Id id={id} />
83106
{symbolComponent}
84-
</NoLink>
107+
</Row>
85108
)}
86-
</Container>
109+
</Flex>
87110
</HiddenPlaceholder>
88111
);
89112
};

packages/suite/src/components/suite/graph/TransactionsGraph/GraphTooltipAccount.tsx

Lines changed: 12 additions & 15 deletions
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,3 @@
1-
import styled from 'styled-components';
21
import { TooltipProps } from 'recharts';
32

43
import { NetworkSymbol } from '@suite-common/wallet-config';
@@ -10,10 +9,7 @@ import { CommonAggregatedHistory, GraphRange } from 'src/types/wallet/graph';
109

1110
import type { CryptoGraphProps } from './TransactionsGraph';
1211
import { GraphTooltipBase } from './GraphTooltipBase';
13-
14-
const StyledCryptoAmount = styled(FormattedCryptoAmount)`
15-
margin-right: 2px;
16-
`;
12+
import { Row } from '@trezor/components';
1713

1814
const formatAmount = (
1915
amount: string | undefined,
@@ -26,14 +22,16 @@ const formatAmount = (
2622
const { FiatAmountFormatter } = formatters;
2723

2824
return (
29-
<>
25+
<Row>
3026
{amount && (
31-
<StyledCryptoAmount
32-
value={amount}
33-
symbol={symbol}
34-
signValue={sign}
35-
disableHiddenPlaceholder
36-
/>
27+
<Row margin={{ right: 4 }}>
28+
<FormattedCryptoAmount
29+
value={amount}
30+
symbol={symbol}
31+
signValue={sign}
32+
disableHiddenPlaceholder
33+
/>
34+
</Row>
3735
)}
3836

3937
{fiatAmount && localCurrency && (
@@ -42,7 +40,7 @@ const formatAmount = (
4240
<FiatAmountFormatter currency={localCurrency} value={fiatAmount} />)
4341
</>
4442
)}
45-
</>
43+
</Row>
4644
);
4745
};
4846

@@ -68,7 +66,6 @@ export const GraphTooltipAccount = ({
6866
...props
6967
}: GraphTooltipAccountProps) => {
7068
const formatters = useFormatters();
71-
7269
// Note: payload is [] when discovery is paused.
7370
if (!active || !payload?.length) {
7471
return null;
@@ -85,7 +82,7 @@ export const GraphTooltipAccount = ({
8582
return (
8683
<GraphTooltipBase
8784
{...props}
88-
active={active}
85+
active={true}
8986
payload={payload}
9087
sentAmount={formatAmount(
9188
sentAmountString,

packages/suite/src/components/suite/graph/TransactionsGraph/GraphTooltipBase.tsx

Lines changed: 1 addition & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -115,12 +115,6 @@ const HighlightedAreaRight = styled(HighlightedArea)`
115115
border-bottom-right-radius: 5px;
116116
`;
117117

118-
const Sign = styled.span<{ $color: string }>`
119-
color: ${({ $color }) => $color};
120-
width: 1ch;
121-
margin-right: 4px;
122-
`;
123-
124118
const formatDate = (date: Date, dateFormat: 'day' | 'month') => {
125119
if (dateFormat === 'day') {
126120
return <FormattedDate value={date} date month="long" />;
@@ -200,8 +194,7 @@ export const GraphTooltipBase = (props: GraphTooltipBaseProps) => {
200194
{props.balance && (
201195
<Row>
202196
<Value>
203-
<Sign $color="transparent">+</Sign>
204-
{props.balance}
197+
<Row $noBottomMargin>{props.balance}</Row>
205198
</Value>
206199
</Row>
207200
)}

0 commit comments

Comments
 (0)