diff --git a/src/lib/components/Swap/Swap.fixture.tsx b/src/lib/components/Swap/Swap.fixture.tsx index 828be4bb50..0f7e6140ee 100644 --- a/src/lib/components/Swap/Swap.fixture.tsx +++ b/src/lib/components/Swap/Swap.fixture.tsx @@ -37,38 +37,33 @@ function Fixture() { defaultValue: FEE_RECIPIENT_OPTIONS[1], }) - const optionsToAddressMap: Record = { - none: '', + const optionsToAddressMap: Record = { + None: undefined, Native: 'NATIVE', DAI: DAI.address, USDC: USDC_MAINNET.address, } const addressOptions = Object.keys(optionsToAddressMap) - const [defaultInput] = useSelect('defaultInputAddress', { - options: addressOptions, - defaultValue: addressOptions[2], - }) - const inputOptions = ['', '0', '100', '-1'] - const [defaultInputAmount] = useSelect('defaultInputAmount', { - options: inputOptions, - defaultValue: inputOptions[2], - }) - const [defaultOutput] = useSelect('defaultOutputAddress', { + + const [defaultInputToken] = useSelect('defaultInputToken', { options: addressOptions, defaultValue: addressOptions[1], }) - const [defaultOutputAmount] = useSelect('defaultOutputAmount', { - options: inputOptions, - defaultValue: inputOptions[0], + const [defaultInputAmount] = useValue('defaultInputAmount', { defaultValue: 1 }) + + const [defaultOutputToken] = useSelect('defaultOutputToken', { + options: addressOptions, + defaultValue: addressOptions[2], }) + const [defaultOutputAmount] = useValue('defaultOutputAmount', { defaultValue: 0 }) return ( console.log('onConnectWallet')} // this handler is included as a test of functionality, but only logs diff --git a/src/lib/components/Swap/SwapPropValidator.tsx b/src/lib/components/Swap/SwapPropValidator.tsx index 20ccc73496..7391b6ceaf 100644 --- a/src/lib/components/Swap/SwapPropValidator.tsx +++ b/src/lib/components/Swap/SwapPropValidator.tsx @@ -1,6 +1,7 @@ import { BigNumber } from '@ethersproject/bignumber' -import { DefaultAddress, SwapProps } from 'lib/components/Swap' import { IntegrationError } from 'lib/errors' +import { FeeOptions } from 'lib/hooks/swap/useSyncConvenienceFee' +import { DefaultAddress, TokenDefaults } from 'lib/hooks/swap/useSyncTokenDefaults' import { PropsWithChildren, useEffect } from 'react' import { isAddress } from '../../../utils' @@ -15,7 +16,7 @@ function isAddressOrAddressMap(addressOrMap: DefaultAddress): boolean { return false } -type ValidatorProps = PropsWithChildren +type ValidatorProps = PropsWithChildren export default function SwapPropValidator(props: ValidatorProps) { const { convenienceFee, convenienceFeeRecipient } = props @@ -47,7 +48,7 @@ export default function SwapPropValidator(props: ValidatorProps) { } }, [convenienceFee, convenienceFeeRecipient]) - const { defaultInputAddress, defaultInputAmount, defaultOutputAddress, defaultOutputAmount } = props + const { defaultInputTokenAddress, defaultInputAmount, defaultOutputTokenAddress, defaultOutputAmount } = props useEffect(() => { if (defaultOutputAmount && defaultInputAmount) { throw new IntegrationError('defaultInputAmount and defaultOutputAmount may not both be defined.') @@ -60,17 +61,25 @@ export default function SwapPropValidator(props: ValidatorProps) { `defaultOutputAmount must be a positive number. (You set it to ${defaultOutputAmount})` ) } - if (defaultInputAddress && !isAddressOrAddressMap(defaultInputAddress) && defaultInputAddress !== 'NATIVE') { + if ( + defaultInputTokenAddress && + !isAddressOrAddressMap(defaultInputTokenAddress) && + defaultInputTokenAddress !== 'NATIVE' + ) { throw new IntegrationError( - `defaultInputAddress(es) must be a valid address or "NATIVE". (You set it to ${defaultInputAddress}` + `defaultInputTokenAddress(es) must be a valid address or "NATIVE". (You set it to ${defaultInputTokenAddress}` ) } - if (defaultOutputAddress && !isAddressOrAddressMap(defaultOutputAddress) && defaultOutputAddress !== 'NATIVE') { + if ( + defaultOutputTokenAddress && + !isAddressOrAddressMap(defaultOutputTokenAddress) && + defaultOutputTokenAddress !== 'NATIVE' + ) { throw new IntegrationError( - `defaultOutputAddress(es) must be a valid address or "NATIVE". (You set it to ${defaultOutputAddress}` + `defaultOutputTokenAddress(es) must be a valid address or "NATIVE". (You set it to ${defaultOutputTokenAddress}` ) } - }, [defaultInputAddress, defaultInputAmount, defaultOutputAddress, defaultOutputAmount]) + }, [defaultInputTokenAddress, defaultInputAmount, defaultOutputTokenAddress, defaultOutputAmount]) return <>{props.children} } diff --git a/src/lib/components/Swap/index.tsx b/src/lib/components/Swap/index.tsx index ec2bf2dfba..0f9a4fc674 100644 --- a/src/lib/components/Swap/index.tsx +++ b/src/lib/components/Swap/index.tsx @@ -2,8 +2,8 @@ import { Trans } from '@lingui/macro' import { TokenInfo } from '@uniswap/token-lists' import { useAtom } from 'jotai' import { SwapInfoUpdater } from 'lib/hooks/swap/useSwapInfo' -import useSyncConvenienceFee from 'lib/hooks/swap/useSyncConvenienceFee' -import useSyncSwapDefaults from 'lib/hooks/swap/useSyncSwapDefaults' +import useSyncConvenienceFee, { FeeOptions } from 'lib/hooks/swap/useSyncConvenienceFee' +import useSyncTokenDefaults, { TokenDefaults } from 'lib/hooks/swap/useSyncTokenDefaults' import { usePendingTransactions } from 'lib/hooks/transactions' import useActiveWeb3React from 'lib/hooks/useActiveWeb3React' import useHasFocus from 'lib/hooks/useHasFocus' @@ -26,8 +26,6 @@ import SwapButton from './SwapButton' import SwapPropValidator from './SwapPropValidator' import Toolbar from './Toolbar' -export type DefaultAddress = string | { [chainId: number]: string | 'NATIVE' } | 'NATIVE' - function getTransactionFromMap( txs: { [hash: string]: Transaction }, hash?: string @@ -44,20 +42,14 @@ function getTransactionFromMap( return } -export interface SwapProps { +export interface SwapProps extends TokenDefaults, FeeOptions { tokenList?: string | TokenInfo[] - defaultInputAddress?: DefaultAddress - defaultInputAmount?: string - defaultOutputAddress?: DefaultAddress - defaultOutputAmount?: string - convenienceFee?: number - convenienceFeeRecipient?: string | { [chainId: number]: string } onConnectWallet?: () => void } export default function Swap(props: SwapProps) { useSyncTokenList(props.tokenList) - useSyncSwapDefaults(props) + useSyncTokenDefaults(props) useSyncConvenienceFee(props) const { active, account } = useActiveWeb3React() diff --git a/src/lib/hooks/swap/useSyncConvenienceFee.ts b/src/lib/hooks/swap/useSyncConvenienceFee.ts index 9364cbbf17..a1b907f200 100644 --- a/src/lib/hooks/swap/useSyncConvenienceFee.ts +++ b/src/lib/hooks/swap/useSyncConvenienceFee.ts @@ -4,12 +4,12 @@ import { useUpdateAtom } from 'jotai/utils' import { feeOptionsAtom } from 'lib/state/swap' import { useEffect } from 'react' -interface FeeOptionsArgs { +export interface FeeOptions { convenienceFee?: number convenienceFeeRecipient?: string | string | { [chainId: number]: string } } -export default function useSyncConvenienceFee({ convenienceFee, convenienceFeeRecipient }: FeeOptionsArgs) { +export default function useSyncConvenienceFee({ convenienceFee, convenienceFeeRecipient }: FeeOptions) { const { chainId } = useActiveWeb3React() const updateFeeOptions = useUpdateAtom(feeOptionsAtom) diff --git a/src/lib/hooks/swap/useSyncSwapDefaults.ts b/src/lib/hooks/swap/useSyncTokenDefaults.ts similarity index 64% rename from src/lib/hooks/swap/useSyncSwapDefaults.ts rename to src/lib/hooks/swap/useSyncTokenDefaults.ts index 3d2eaac64e..a3e9f6bd6f 100644 --- a/src/lib/hooks/swap/useSyncSwapDefaults.ts +++ b/src/lib/hooks/swap/useSyncTokenDefaults.ts @@ -1,12 +1,20 @@ import { Currency } from '@uniswap/sdk-core' import { nativeOnChain } from 'constants/tokens' import { useUpdateAtom } from 'jotai/utils' -import { DefaultAddress } from 'lib/components/Swap' import useActiveWeb3React from 'lib/hooks/useActiveWeb3React' import { useToken } from 'lib/hooks/useCurrency' import { Field, Swap, swapAtom } from 'lib/state/swap' import { useCallback, useLayoutEffect, useState } from 'react' +export type DefaultAddress = string | { [chainId: number]: string | 'NATIVE' } | 'NATIVE' + +export interface TokenDefaults { + defaultInputTokenAddress?: DefaultAddress + defaultInputAmount?: number | string + defaultOutputTokenAddress?: DefaultAddress + defaultOutputAmount?: number | string +} + function useDefaultToken( defaultAddress: DefaultAddress | undefined, chainId: number | undefined @@ -24,23 +32,16 @@ function useDefaultToken( return token } -interface UseSwapDefaultsArgs { - defaultInputAddress?: DefaultAddress - defaultInputAmount?: string - defaultOutputAddress?: DefaultAddress - defaultOutputAmount?: string -} - -export default function useSyncSwapDefaults({ - defaultInputAddress, +export default function useSyncTokenDefaults({ + defaultInputTokenAddress, defaultInputAmount, - defaultOutputAddress, + defaultOutputTokenAddress, defaultOutputAmount, -}: UseSwapDefaultsArgs) { +}: TokenDefaults) { const updateSwap = useUpdateAtom(swapAtom) const { chainId } = useActiveWeb3React() - const defaultInputToken = useDefaultToken(defaultInputAddress, chainId) - const defaultOutputToken = useDefaultToken(defaultOutputAddress, chainId) + const defaultInputToken = useDefaultToken(defaultInputTokenAddress, chainId) + const defaultOutputToken = useDefaultToken(defaultOutputTokenAddress, chainId) const setToDefaults = useCallback(() => { const defaultSwapState: Swap = { @@ -49,14 +50,14 @@ export default function useSyncSwapDefaults({ [Field.OUTPUT]: defaultOutputToken || undefined, independentField: Field.INPUT, } - if (defaultInputAmount && defaultInputToken) { - defaultSwapState.amount = defaultInputAmount - } else if (defaultOutputAmount && defaultOutputToken) { + if (defaultInputToken && defaultInputAmount) { + defaultSwapState.amount = defaultInputAmount.toString() + } else if (defaultOutputToken && defaultOutputAmount) { defaultSwapState.independentField = Field.OUTPUT - defaultSwapState.amount = defaultOutputAmount + defaultSwapState.amount = defaultOutputAmount.toString() } updateSwap((swap) => ({ ...swap, ...defaultSwapState })) - }, [defaultInputToken, defaultOutputToken, defaultInputAmount, defaultOutputAmount, updateSwap]) + }, [defaultInputAmount, defaultInputToken, defaultOutputAmount, defaultOutputToken, updateSwap]) const [previousChainId, setPreviousChainId] = useState(chainId) useLayoutEffect(() => { diff --git a/src/lib/index.tsx b/src/lib/index.tsx index 789e84f7cd..389236fb76 100644 --- a/src/lib/index.tsx +++ b/src/lib/index.tsx @@ -1,10 +1,18 @@ import Swap, { SwapProps } from './components/Swap' import Widget, { WidgetProps } from './components/Widget' + +export type { ErrorHandler } from './components/Error/ErrorBoundary' +export type { FeeOptions } from './hooks/swap/useSyncConvenienceFee' +export type { DefaultAddress, TokenDefaults } from './hooks/swap/useSyncTokenDefaults' +export type { Theme } from './theme' export { darkTheme, lightTheme } from './theme' -export type { Theme } from './theme/theme' +export type { Provider as EthersProvider } from '@ethersproject/abstract-provider' +export type { TokenInfo } from '@uniswap/token-lists' +export type { Provider as Eip1193Provider } from '@web3-react/types' +export type { SupportedLocale } from 'constants/locales' export { SUPPORTED_LOCALES } from 'constants/locales' -type SwapWidgetProps = SwapProps & WidgetProps +export type SwapWidgetProps = SwapProps & WidgetProps export function SwapWidget(props: SwapWidgetProps) { return (