Skip to content

Commit

Permalink
refactor(wallet-mobile): portfolio token
Browse files Browse the repository at this point in the history
  • Loading branch information
stackchain committed Sep 2, 2024
1 parent 84978b0 commit 433e103
Show file tree
Hide file tree
Showing 40 changed files with 161 additions and 176 deletions.
2 changes: 1 addition & 1 deletion apps/wallet-mobile/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -130,7 +130,7 @@
"@yoroi/explorers": "^1.0.2",
"@yoroi/identicon": "^1.0.1",
"@yoroi/links": "^1.5.7",
"@yoroi/portfolio": "^1.0.2",
"@yoroi/portfolio": "1.0.3",
"@yoroi/resolver": "^2.0.6",
"@yoroi/setup-wallet": "^1.0.1",
"@yoroi/staking": "^1.5.2",
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -9,7 +9,7 @@ import {Amounts} from '../../yoroi-wallets/utils'
import {Spacer} from '..'
import {AmountItem} from './AmountItem'

const primaryAmount = Amounts.getAmount(mocks.balances, mocks.wallet.primaryTokenInfo.id)
const primaryAmount = Amounts.getAmount(mocks.balances, mocks.wallet.portfolioPrimaryTokenInfo.id)
const secondaryAmount = Amounts.getAmount(
mocks.balances,
'698a6ea0ca99f315034072af31eaac6ec11fe8558d3f48e9775aab9d.7444524950',
Expand Down
7 changes: 3 additions & 4 deletions apps/wallet-mobile/src/components/AmountItem/AmountItem.tsx
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
import {isPrimaryToken} from '@yoroi/portfolio'
import {useTheme} from '@yoroi/theme'
import {Balance} from '@yoroi/types'
import {Swap} from '@yoroi/types'
import {Balance, Swap} from '@yoroi/types'
import * as React from 'react'
import {StyleSheet, View, ViewProps} from 'react-native'

Expand All @@ -17,7 +17,6 @@ export type AmountItemProps = {
amount: Balance.Amount
style?: ViewProps['style']
isPrivacyActive?: boolean
status?: string
inWallet?: boolean
variant?: 'swap'
priceImpactRisk?: SwapPriceImpactRisk
Expand All @@ -38,7 +37,7 @@ export const AmountItem = ({
const {quantity, tokenId} = amount
const tokenInfo = useTokenInfo({wallet, tokenId})

const isPrimary = tokenInfo.id === wallet.primaryTokenInfo.id
const isPrimary = isPrimaryToken(tokenInfo.id)
const name = tokenInfo.ticker ?? tokenInfo.name
const nameLabel = isEmptyString(name) ? '-' : name
const detail = isPrimary ? tokenInfo.description : tokenInfo.fingerprint
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -7,7 +7,7 @@ import {TokenIcon} from './TokenIcon'
storiesOf('TokenIcon', module)
.add('PrimaryToken', () => {
const wallet = mocks.wallet
return <TokenIcon wallet={wallet} tokenId={mocks.wallet.primaryTokenInfo.id} />
return <TokenIcon wallet={wallet} tokenId={mocks.wallet.portfolioPrimaryTokenInfo.id} />
})
.add('Nft', () => {
const wallet = {
Expand Down
2 changes: 1 addition & 1 deletion apps/wallet-mobile/src/components/TokenIcon/TokenIcon.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -12,7 +12,7 @@ import {ModeratedNftIcon} from './ModeratedNftIcon'
export const TokenIcon = ({wallet, tokenId, variant}: {wallet: YoroiWallet; tokenId: string; variant?: 'swap'}) => {
const {styles} = useStyles()
const tokenInfo = useTokenInfo({wallet, tokenId})
const isPrimary = tokenInfo.id === wallet.primaryTokenInfo.id
const isPrimary = tokenInfo.id === wallet.portfolioPrimaryTokenInfo.id

if (isPrimary) return <PrimaryIcon variant={variant} />
if (tokenInfo.kind === 'ft') {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -135,7 +135,7 @@ export const AmountList = ({amounts}: {amounts: Balance.Amounts}) => {

return (
<FlatList
data={sortTokenInfos({wallet, tokenInfos})}
data={sortTokenInfos({tokenInfos})}
renderItem={({item: tokenInfo}) => (
<AmountItem wallet={wallet} amount={Amounts.getAmount(amounts, tokenInfo.id)} />
)}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -18,7 +18,7 @@ export const ShowBuyBanner = () => {
selected: {network},
} = useWalletManager()
const balances = useBalances(wallet)
const primaryAmount = Amounts.getAmount(balances, wallet.primaryTokenInfo.id)
const primaryAmount = Amounts.getAmount(balances, wallet.portfolioPrimaryTokenInfo.id)
const hasZeroPt = Quantities.isZero(primaryAmount.quantity)

const showSmallBanner = useShowBuyBannerSmall()
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -10,7 +10,7 @@ export const useShowBuyBannerSmall = (options?: UseQueryOptions<boolean, Error,
const {wallet} = useSelectedWallet()

const balances = useBalances(wallet)
const primaryAmount = Amounts.getAmount(balances, wallet.primaryTokenInfo.id)
const primaryAmount = Amounts.getAmount(balances, wallet.portfolioPrimaryTokenInfo.id)
const isInThresholdToBuy = Quantities.isGreaterThan(minAdaThreshold, primaryAmount.quantity)

const storage = useAsyncStorage()
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -41,7 +41,7 @@ export const RequestSpecificAmountScreen = () => {
const handleOnChangeAmount = (amount: string) => {
const edited = editedFormatter(amount)
const numberOfDecimals = (edited.split('.')[1] ?? []).length
if (Number(edited) <= Number.MAX_SAFE_INTEGER && numberOfDecimals <= (wallet.primaryTokenInfo.decimals ?? 0)) {
if (Number(edited) <= Number.MAX_SAFE_INTEGER && numberOfDecimals <= wallet.portfolioPrimaryTokenInfo.decimals) {
setAmount(edited)
}
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -15,7 +15,7 @@ import {useSelectedWallet} from '../../../../WalletManager/common/hooks/useSelec
export const SecondaryTotals = ({yoroiUnsignedTx}: {yoroiUnsignedTx: YoroiUnsignedTx}) => {
const {wallet} = useSelectedWallet()
const secondaryAmounts = Amounts.remove(Amounts.getAmountsFromEntries(yoroiUnsignedTx.entries), [
wallet.primaryTokenInfo.id,
wallet.portfolioPrimaryTokenInfo.id,
])
const sortedAmounts = Amounts.toArray(secondaryAmounts).sort((a, b) =>
Quantities.isGreaterThan(a.quantity, b.quantity) ? -1 : 1,
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -15,7 +15,7 @@ import {useSelectedWallet} from '../../../../WalletManager/common/hooks/useSelec
export const SecondaryTotals = ({yoroiUnsignedTx}: {yoroiUnsignedTx: YoroiUnsignedTx}) => {
const {wallet} = useSelectedWallet()
const secondaryAmounts = Amounts.remove(Amounts.getAmountsFromEntries(yoroiUnsignedTx.entries), [
wallet.primaryTokenInfo.id,
wallet.portfolioPrimaryTokenInfo.id,
])
const sortedAmounts = Amounts.toArray(secondaryAmounts).sort((a, b) =>
Quantities.isGreaterThan(a.quantity, b.quantity) ? -1 : 1,
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -21,7 +21,7 @@ const goneCollateral: YoroiWallet = {
return {
amount: {
quantity: '0',
tokenId: mocks.wallet.primaryTokenInfo.id,
tokenId: mocks.wallet.portfolioPrimaryTokenInfo.id,
},
collateralId: mocks.wallet.collateralId,
utxo: undefined,
Expand All @@ -37,7 +37,7 @@ const noCollateral: YoroiWallet = {
return {
amount: {
quantity: '0',
tokenId: mocks.wallet.primaryTokenInfo.id,
tokenId: mocks.wallet.portfolioPrimaryTokenInfo.id,
},
collateralId: '',
utxo: undefined,
Expand All @@ -54,7 +54,7 @@ const noFundsWallet: YoroiWallet = {
return {
amount: {
quantity: '0',
tokenId: mocks.wallet.primaryTokenInfo.id,
tokenId: mocks.wallet.portfolioPrimaryTokenInfo.id,
},
collateralId: '',
utxo: undefined,
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -14,7 +14,7 @@ export const createCollateralEntry = (wallet: YoroiWallet): YoroiEntry => {
return {
address: getCollateralAddress(wallet),
amounts: {
[wallet.primaryTokenInfo.id]: getCollateralAmountInLovelace(),
[wallet.portfolioPrimaryTokenInfo.id]: getCollateralAmountInLovelace(),
},
}
}
27 changes: 19 additions & 8 deletions apps/wallet-mobile/src/features/Settings/SettingsItems.tsx
Original file line number Diff line number Diff line change
@@ -1,12 +1,13 @@
import {amountFormatter} from '@yoroi/portfolio'
import {useTheme} from '@yoroi/theme'
import _ from 'lodash'
import React, {ReactElement} from 'react'
import {StyleSheet, TouchableOpacity, TouchableOpacityProps, View} from 'react-native'

import {Hr, Icon, Spacer, Text} from '../../components'
import {isEmptyString} from '../../kernel/utils'
import {useCollateralInfo} from '../../yoroi-wallets/cardano/utxoManager/useCollateralInfo'
import {formatTokenWithSymbol} from '../../yoroi-wallets/utils/format'
import {useSelectedWallet} from '../WalletManager/common/hooks/useSelectedWallet'
import {usePrivacyMode} from './PrivacyMode/PrivacyMode'

const Touchable = (props: TouchableOpacityProps) => <TouchableOpacity {...props} activeOpacity={0.5} />

Expand Down Expand Up @@ -58,7 +59,7 @@ export const SettingsItem = ({label, children, disabled, icon, info}: SettingsIt
<View>{children}</View>
</View>

{!_.isNil(info) && (
{!isEmptyString(info) && (
<>
<Spacer height={12} />

Expand All @@ -85,7 +86,7 @@ export const NavigatedSettingsItem = ({label, onNavigate, icon, disabled, select
<Touchable onPress={onNavigate} disabled={disabled}>
<SettingsItem icon={icon} label={label} disabled={disabled}>
<View style={{flexDirection: 'row', alignItems: 'center'}}>
{!_.isNil(selected) && <Text style={styles.navigationItem}>{selected}</Text>}
{!isEmptyString(selected) && <Text style={styles.navigationItem}>{selected}</Text>}

<Spacer width={16} />

Expand All @@ -111,16 +112,26 @@ export const SettingsCollateralItem = ({label, onNavigate, icon, disabled}: Navi
const {styles, colors} = useStyles()
const {wallet} = useSelectedWallet()
const {amount} = useCollateralInfo(wallet)
const {isPrivacyActive, privacyPlaceholder} = usePrivacyMode()

const formattedAmount = formatTokenWithSymbol(amount.quantity, wallet.primaryTokenInfo)
const formattedCollateral = React.useMemo(() => {
const amountCollateral = {
info: wallet.portfolioPrimaryTokenInfo,
quantity: BigInt(amount.quantity),
}

return !isPrivacyActive
? amountFormatter({template: '{{value}} {{ticker}}'})(amountCollateral)
: amountFormatter({template: `${privacyPlaceholder} {{ticker}}`})(amountCollateral)
}, [amount.quantity, isPrivacyActive, privacyPlaceholder, wallet.portfolioPrimaryTokenInfo])

return (
<Touchable onPress={onNavigate} disabled={disabled}>
<SettingsItem label={label} icon={icon}>
<View style={styles.row}>
<Text secondary>{formattedAmount}</Text>
<Text secondary>{formattedCollateral}</Text>

<Icon.Chevron direction="right" size={28} color={colors.iconColor} />
<Icon.Chevron direction="right" size={28} color={colors.icon} />
</View>
</SettingsItem>
</Touchable>
Expand Down Expand Up @@ -169,7 +180,7 @@ const useStyles = () => {
})

const colors = {
iconColor: color.gray_600,
icon: color.el_gray_medium,
}
return {styles, colors, color}
}
Original file line number Diff line number Diff line change
Expand Up @@ -67,8 +67,7 @@ export const SelectPoolFromList = ({pools = []}: Props) => {
navigate.startSwap()
}

const decimals = wallet.primaryTokenInfo.decimals ?? 0
const ticker = wallet.primaryTokenInfo.ticker
const {decimals, ticker} = wallet.portfolioPrimaryTokenInfo

const protocolCapitalize = (protocol: string): string => protocol[0].toUpperCase() + protocol.substring(1)

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -58,7 +58,7 @@ export const SwapFormProvider = ({
const hasBuyTokenSupply = poolSupply >= buyQuantity
const hasSellBalance = sellBalance >= sellQuantity

const isSellPt = orderData.amounts.sell?.info.id === wallet.primaryTokenInfo.id
const isSellPt = orderData.amounts.sell?.info.id === wallet.portfolioPrimaryTokenInfo.id
const ptTotalRequired = orderData.selectedPoolCalculation?.cost.ptTotalRequired.quantity ?? 0n
const hasPtBalance = primaryTokenBalance >= (!isSellPt ? 0n : sellQuantity + ptTotalRequired)

Expand Down
14 changes: 8 additions & 6 deletions apps/wallet-mobile/src/features/Swap/common/helpers.ts
Original file line number Diff line number Diff line change
@@ -1,12 +1,12 @@
import {createTypeGuardFromSchema, parseSafe} from '@yoroi/common'
import {isPrimaryToken, primaryTokenId as ptId} from '@yoroi/portfolio'
import {useTheme} from '@yoroi/theme'
import {Balance, HW} from '@yoroi/types'
import {SwapApi} from '@yoroi/types/src/swap/api'
import {useMutation, UseMutationOptions} from 'react-query'
import {z} from 'zod'

import {convertBech32ToHex} from '../../../yoroi-wallets/cardano/common/signatureUtils'
import {YoroiWallet} from '../../../yoroi-wallets/cardano/types'
import {generateCIP30UtxoCbor} from '../../../yoroi-wallets/cardano/utils'
import {useSelectedWallet} from '../../WalletManager/common/hooks/useSelectedWallet'
import {PRICE_IMPACT_HIGH_RISK, PRICE_IMPACT_MODERATE_RISK} from './constants'
Expand Down Expand Up @@ -80,15 +80,15 @@ export const parseOrderTxMetadata = (metadataJson: string, primaryTokenId: strin
}

const normalisePrimaryTokenId = (tokenId: string, primaryTokenId: string) => {
return tokenId === '.' || tokenId === '' ? primaryTokenId : tokenId
return tokenId === ptId || tokenId === '' ? primaryTokenId : tokenId
}

function containsOnlyValidChars(str?: string): boolean {
const validCharsRegex = /^[a-zA-Z0 ]*$/
return typeof str === 'string' && validCharsRegex.test(str)
}

export const sortTokensByName = (a: Balance.TokenInfo, b: Balance.TokenInfo, wallet: YoroiWallet) => {
export const sortTokensByName = (a: Balance.TokenInfo, b: Balance.TokenInfo) => {
const isValidNameA = containsOnlyValidChars(a.name)
const isValidNameB = containsOnlyValidChars(b.name)
const isValidTickerA = containsOnlyValidChars(a.ticker)
Expand All @@ -100,10 +100,10 @@ export const sortTokensByName = (a: Balance.TokenInfo, b: Balance.TokenInfo, wal
const nameB =
b.ticker?.toLocaleLowerCase() && isValidTickerB ? b.ticker?.toLocaleLowerCase() : b.name.toLocaleLowerCase()

const isBPrimary = b.ticker === wallet.primaryTokenInfo.ticker
const isBPrimary = isPrimaryToken(b.id)
if (isBPrimary) return 1

const isAPrimary = a.ticker === wallet.primaryTokenInfo.ticker
const isAPrimary = isPrimaryToken(a.id)
if (isAPrimary) return -1

if (!isValidNameA && isValidNameB) {
Expand All @@ -129,7 +129,9 @@ export const usePriceImpactRiskTheme = (risk: SwapPriceImpactRisk) => {
text: color.sys_magenta_500,
background: color.sys_magenta_100,
}
} else if (risk === 'moderate') {
}

if (risk === 'moderate') {
return {
text: color.sys_orange_500,
background: color.sys_orange_100,
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -60,8 +60,8 @@ export const TransactionSummary = () => {
)} ${tokenToSellName}`
const formattedFeeText = `${Quantities.format(
asQuantity((cost.batcherFee.quantity + cost.frontendFeeInfo.fee.quantity).toString()),
wallet.primaryTokenInfo.decimals ?? 0,
)} ${wallet.primaryTokenInfo.ticker}`
wallet.portfolioPrimaryTokenInfo.decimals,
)} ${wallet.portfolioPrimaryTokenInfo.ticker}`
const poolProviderFormatted = capitalize(pool.provider)
const poolUrl = getPoolUrlByProvider(pool.provider)

Expand All @@ -74,7 +74,7 @@ export const TransactionSummary = () => {
const minAdaInfoValue = `${Quantities.format(
asQuantity(cost.deposit.quantity.toString()),
wallet.portfolioPrimaryTokenInfo.decimals,
)} ${wallet.primaryTokenInfo.ticker}`
)} ${wallet.portfolioPrimaryTokenInfo.ticker}`
const minReceivedInfoValue = `${Quantities.format(
asQuantity(calculation.buyAmountWithSlippage.quantity.toString()),
buyTokenInfo.decimals,
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -38,15 +38,16 @@ export const ShowPoolActions = () => {
if (!isBuyTouched || !isSellTouched || calculation === undefined) return null

const {cost, pool} = calculation
const {decimals, ticker} = wallet.portfolioPrimaryTokenInfo

const totalFees = Quantities.format(
asQuantity((cost.batcherFee.quantity + cost.frontendFeeInfo.fee.quantity).toString()),
wallet.primaryTokenInfo.decimals ?? 0,
decimals,
)
const titleTotalFeesFormatted = `${strings.total}: ${Quantities.format(
asQuantity(amounts.sell?.quantity.toString() ?? '0'),
sellTokenInfo?.decimals ?? 0,
)} ${sellTokenName} + ${totalFees} ${wallet.primaryTokenInfo.ticker}`
)} ${sellTokenName} + ${totalFees} ${ticker}`
const handleOnExpand = () => setIsExpanded((state) => !state)
const totalFeesTitle = (
<HeaderWrapper expanded={isExpanded} onPress={handleOnExpand}>
Expand Down Expand Up @@ -121,8 +122,9 @@ const ShowLimitOrderFeeBreakdown = ({totalFees}: {totalFees: string}) => {
wallet.portfolioPrimaryTokenInfo.decimals,
)

const depositFormatted = `${deposit} ${wallet.primaryTokenInfo.ticker}`
const totalFeesFormatted = `${totalFees} ${wallet.primaryTokenInfo.ticker}`
const ticker = wallet.portfolioPrimaryTokenInfo.ticker
const depositFormatted = `${deposit} ${ticker}`
const totalFeesFormatted = `${totalFees} ${ticker}`
const minReceivedFormatted = `${minReceived} ${buyTokenName}`

const feeStructure = [
Expand Down Expand Up @@ -210,8 +212,9 @@ const ShowMarketOrderFeeBreakdown = ({totalFees}: {totalFees: string}) => {
)
const liqFeePerc = pool.fee

const depositFormatted = `${deposit} ${wallet.primaryTokenInfo.ticker}`
const totalFeesFormatted = `${totalFees} ${wallet.primaryTokenInfo.ticker}`
const ticker = wallet.portfolioPrimaryTokenInfo.ticker
const depositFormatted = `${deposit} ${ticker}`
const totalFeesFormatted = `${totalFees} ${ticker}`
const minReceivedFormatted = `${minReceived} ${buyTokenName}`
const liqFeeQuantityFormatted = `${liqFeeQuantity} ${sellTokenName}`
const liqFeePercFormatted = strings.swapLiquidityFeeInfo(liqFeePerc, bold)
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -188,7 +188,7 @@ export const StartSwapOrderScreen = () => {
swap_fees: Number(
Quantities.denominated(
asQuantity(orderData.selectedPoolCalculation.pool.batcherFee.quantity.toString()),
Number(wallet.primaryTokenInfo.decimals),
Number(wallet.portfolioPrimaryTokenInfo.decimals),
),
),
})
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -111,7 +111,7 @@ export const CompletedOrders = () => {
}, [])

const transactionsInfos = useTransactionInfos({wallet})
const completeOrders = findCompletedOrderTx(Object.values(transactionsInfos), wallet.primaryTokenInfo.id)
const completeOrders = findCompletedOrderTx(Object.values(transactionsInfos), wallet.portfolioPrimaryTokenInfo.id)
const tokenIds = React.useMemo(
() => _.uniq(completeOrders?.flatMap((o) => [o.metadata.sellTokenId, o.metadata.buyTokenId])),
[completeOrders],
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -163,7 +163,7 @@ export const OpenOrders = () => {

const hasCollateral = () => {
const info = wallet.getCollateralInfo()
const primaryTokenDecimals = wallet.primaryTokenInfo.decimals ?? 0
const primaryTokenDecimals = wallet.portfolioPrimaryTokenInfo.decimals
return (
!!info.utxo &&
Quantities.integer(info.amount.quantity, primaryTokenDecimals) >=
Expand Down
Loading

0 comments on commit 433e103

Please sign in to comment.