utils#getBscScanLink TypeScript Examples
The following examples show how to use
utils#getBscScanLink.
You can vote up the ones you like or vote down the ones you don't like,
and go to the original project or source file by following the links above each example. You may check out the related API usage on the sidebar.
Example #1
Source File: Transaction.tsx From glide-frontend with GNU General Public License v3.0 | 6 votes |
export default function Transaction({ tx }: { tx: TransactionDetails }) {
const { chainId } = useActiveWeb3React()
const summary = tx?.summary
const pending = !tx?.receipt
const success = !pending && tx && (tx.receipt?.status === 1 || typeof tx.receipt?.status === 'undefined')
if (!chainId) return null
return (
<TransactionState pending={pending} success={success}>
<LinkExternal href={getBscScanLink(tx.hash, 'transaction', chainId)}>{summary ?? tx.hash}</LinkExternal>
<IconWrapper pending={pending} success={success}>
{pending ? <CircleLoader /> : success ? <CheckmarkIcon color="success" /> : <CloseIcon color="failure" />}
</IconWrapper>
</TransactionState>
)
}
Example #2
Source File: TransactionRow.tsx From glide-frontend with GNU General Public License v3.0 | 6 votes |
TransactionRow: React.FC<TransactionRowProps> = ({ txn }) => {
const { chainId } = useActiveWeb3React()
if (!txn) {
return null
}
return (
<TxnLink href={getBscScanLink(txn.hash, 'transaction', chainId)} external>
<TxnIcon>{renderIcon(txn)}</TxnIcon>
<Summary>{txn.summary ?? txn.hash}</Summary>
<TxnIcon>
<OpenNewIcon width="24px" color="primary" />
</TxnIcon>
</TxnLink>
)
}
Example #3
Source File: VoteRow.tsx From glide-frontend with GNU General Public License v3.0 | 6 votes |
VoteRow: React.FC<VoteRowProps> = ({ vote, isVoter }) => {
const { t } = useTranslation()
const hasVotingPower = !!vote.metadata?.votingPower
const votingPower = hasVotingPower ? new BigNumber(vote.metadata.votingPower).toFormat(3) : '--'
return (
<Row>
<AddressColumn>
<Flex alignItems="center">
<LinkExternal href={getBscScanLink(vote.voter, 'address')}>{truncateWalletAddress(vote.voter)}</LinkExternal>
{isVoter && (
<Tag variant="success" outline ml="8px">
<CheckmarkCircleIcon mr="4px" /> {t('Voted')}
</Tag>
)}
</Flex>
</AddressColumn>
<ChoiceColumn>
<TextEllipsis title={vote.proposal.choices[vote.choice - 1]}>
{vote.proposal.choices[vote.choice - 1]}
</TextEllipsis>
</ChoiceColumn>
<VotingPowerColumn>
<Flex alignItems="center" justifyContent="end">
<Text title={vote.metadata.votingPower}>{votingPower}</Text>
{hasVotingPower && <LinkExternal href={`${IPFS_GATEWAY}/${vote.id}`} />}
</Flex>
</VotingPowerColumn>
</Row>
)
}
Example #4
Source File: Timer.tsx From glide-frontend with GNU General Public License v3.0 | 6 votes |
TooltipContent = ({ blockNumber, t }: { blockNumber: number; t: ContextApi['t'] }): JSX.Element => (
<>
<Text color="body" mb="10px" fontWeight="600">
{t('Block %num%', { num: blockNumber })}
</Text>
<Link external href={getBscScanLink(blockNumber, 'block')}>
{t('View on explorer')}
</Link>
</>
)
Example #5
Source File: BetDetails.tsx From glide-frontend with GNU General Public License v3.0 | 6 votes |
BetDetails: React.FC<BetDetailsProps> = ({ bet, result }) => {
const { t } = useTranslation()
const { totalAmount, bullAmount, bearAmount } = bet.round
const bullMultiplier = getMultiplier(totalAmount, bullAmount)
const bearMultiplier = getMultiplier(totalAmount, bearAmount)
return (
<StyledBetDetails>
{result === Result.CANCELED && (
<Text as="p" color="failure" mb="24px">
{t(
'This round was automatically canceled due to an error. If you entered a position, please reclaim your funds below.',
)}
</Text>
)}
{result !== Result.LIVE && <BetResult bet={bet} result={result} />}
<Heading mb="8px">{t('Round History')}</Heading>
<RoundResultHistory round={bet.round} mb="24px">
<PayoutRow positionLabel={t('Up')} multiplier={bullMultiplier} amount={bullAmount} />
<PayoutRow positionLabel={t('Down')} multiplier={bearMultiplier} amount={bearAmount} />
</RoundResultHistory>
<Flex alignItems="center" justifyContent="space-between" mb="8px">
<Text>{t('Opening Block')}</Text>
<Link href={getBscScanLink(bet.round.lockBlock, 'block')} external>
{bet.round.lockBlock}
</Link>
</Flex>
<Flex alignItems="center" justifyContent="space-between">
<Text>{t('Closing Block')}</Text>
<Link href={getBscScanLink(bet.round.endBlock, 'block')} external>
{bet.round.endBlock}
</Link>
</Flex>
</StyledBetDetails>
)
}
Example #6
Source File: TransactionsTable.tsx From glide-frontend with GNU General Public License v3.0 | 6 votes |
DataRow: React.FC<{ transaction: Transaction }> = ({ transaction }) => {
const { t } = useTranslation()
const abs0 = Math.abs(transaction.amountToken0)
const abs1 = Math.abs(transaction.amountToken1)
const outputTokenSymbol = transaction.amountToken0 < 0 ? transaction.token0Symbol : transaction.token1Symbol
const inputTokenSymbol = transaction.amountToken1 < 0 ? transaction.token0Symbol : transaction.token1Symbol
return (
<ResponsiveGrid>
<LinkExternal href={getBscScanLink(transaction.hash, 'transaction')}>
<Text>
{transaction.type === TransactionType.MINT
? t('Add %token0% and %token1%', { token0: transaction.token0Symbol, token1: transaction.token1Symbol })
: transaction.type === TransactionType.SWAP
? t('Swap %token0% for %token1%', { token0: inputTokenSymbol, token1: outputTokenSymbol })
: t('Remove %token0% and %token1%', { token0: transaction.token0Symbol, token1: transaction.token1Symbol })}
</Text>
</LinkExternal>
<Text>${formatAmount(transaction.amountUSD)}</Text>
<Text>
<Text>{`${formatAmount(abs0)} ${transaction.token0Symbol}`}</Text>
</Text>
<Text>
<Text>{`${formatAmount(abs1)} ${transaction.token1Symbol}`}</Text>
</Text>
<LinkExternal href={getBscScanLink(transaction.sender, 'address')}>
{truncateHash(transaction.sender)}
</LinkExternal>
<Text>{formatDistanceToNowStrict(parseInt(transaction.timestamp, 10) * 1000)}</Text>
</ResponsiveGrid>
)
}
Example #7
Source File: Timer.tsx From glide-frontend with GNU General Public License v3.0 | 6 votes |
Timer: React.FC<Props> = ({ publicIfoData }) => {
const { t } = useTranslation()
const { status, secondsUntilStart, secondsUntilEnd, startBlockNum } = publicIfoData
const countdownToUse = status === 'coming_soon' ? secondsUntilStart : secondsUntilEnd
const timeUntil = getTimePeriods(countdownToUse)
const suffix = status === 'coming_soon' ? t('Start').toLowerCase() : t('Finish').toLowerCase()
return (
<Flex justifyContent="center" mb="32px">
{status === 'idle' ? (
<Skeleton animation="pulse" variant="rect" width="100%" height="48px" />
) : (
<>
<PocketWatchIcon width="48px" mr="16px" />
<Flex alignItems="center">
<Text bold mr="16px">
{suffix}:
</Text>
<Text>
{t('%day%d %hour%h %minute%m', {
day: timeUntil.days,
hour: timeUntil.hours,
minute: timeUntil.minutes,
})}
</Text>
<Link
href={getBscScanLink(startBlockNum, 'countdown')}
target="blank"
rel="noopener noreferrer"
ml="8px"
textTransform="lowercase"
>
{`(${t('Blocks')})`}
</Link>
</Flex>
</>
)}
</Flex>
)
}
Example #8
Source File: RecentTransactionsModal.tsx From pancakeswap-testnet with GNU General Public License v3.0 | 5 votes |
RecentTransactionsModal = ({ onDismiss = defaultOnDismiss, translateString }: RecentTransactionsModalProps) => {
const TranslateString = translateString
const { account, chainId } = useActiveWeb3React()
const allTransactions = useAllTransactions()
// Logic taken from Web3Status/index.tsx line 175
const sortedRecentTransactions = useMemo(() => {
const txs = Object.values(allTransactions)
return txs.filter(isTransactionRecent).sort(newTransactionsFirst)
}, [allTransactions])
return (
<Modal title={TranslateString(1202, 'Recent transactions')} onDismiss={onDismiss}>
{!account && (
<Flex justifyContent="center" flexDirection="column" alignItems="center">
<Text mb="8px" bold>
Please connect your wallet to view your recent transactions
</Text>
<Button variant="tertiary" scale="sm" onClick={onDismiss}>
Close
</Button>
</Flex>
)}
{account && chainId && sortedRecentTransactions.length === 0 && (
<Flex justifyContent="center" flexDirection="column" alignItems="center">
<Text mb="8px" bold>
No recent transactions
</Text>
<Button variant="tertiary" scale="sm" onClick={onDismiss}>
Close
</Button>
</Flex>
)}
{account &&
chainId &&
sortedRecentTransactions.map((sortedRecentTransaction) => {
const { hash, summary } = sortedRecentTransaction
const { icon, color } = getRowStatus(sortedRecentTransaction)
return (
<>
<Flex key={hash} alignItems="center" justifyContent="space-between" mb="4px">
<LinkExternal href={getBscScanLink(chainId, hash, 'transaction')} color={color}>
{summary ?? hash}
</LinkExternal>
{icon}
</Flex>
</>
)
})}
</Modal>
)
}
Example #9
Source File: RecentTransactionsModal.tsx From panther-frontend-dex with GNU General Public License v3.0 | 5 votes |
RecentTransactionsModal = ({ onDismiss = defaultOnDismiss }: RecentTransactionsModalProps) => {
const { account, chainId } = useActiveWeb3React()
const allTransactions = useAllTransactions()
// Logic taken from Web3Status/index.tsx line 175
const sortedRecentTransactions = useMemo(() => {
const txs = Object.values(allTransactions)
return txs.filter(isTransactionRecent).sort(newTransactionsFirst)
}, [allTransactions])
return (
<Modal title="Recent Transactions" onDismiss={onDismiss}>
{!account && (
<Flex justifyContent="center" flexDirection="column" alignItems="center">
<Text mb="8px" bold>
Please connect your wallet to view your recent transactions
</Text>
<Button variant="tertiary" size="sm" onClick={onDismiss}>
Close
</Button>
</Flex>
)}
{account && chainId && sortedRecentTransactions.length === 0 && (
<Flex justifyContent="center" flexDirection="column" alignItems="center">
<Text mb="8px" bold>
No recent transactions
</Text>
<Button variant="tertiary" size="sm" onClick={onDismiss}>
Close
</Button>
</Flex>
)}
{account &&
chainId &&
sortedRecentTransactions.map((sortedRecentTransaction) => {
const { hash, summary } = sortedRecentTransaction
const { icon, color } = getRowStatus(sortedRecentTransaction)
return (
<>
<Flex key={hash} alignItems="center" justifyContent="space-between" mb="4px">
<LinkExternal href={getBscScanLink(chainId, hash, 'transaction')} color={color}>
{summary ?? hash}
</LinkExternal>
{icon}
</Flex>
</>
)
})}
</Modal>
)
}
Example #10
Source File: RecentTransactionsModal.tsx From pancake-swap-testnet with MIT License | 5 votes |
RecentTransactionsModal = ({ onDismiss = defaultOnDismiss, translateString }: RecentTransactionsModalProps) => {
const { account, chainId } = useActiveWeb3React()
const allTransactions = useAllTransactions()
// Logic taken from Web3Status/index.tsx line 175
const sortedRecentTransactions = useMemo(() => {
const txs = Object.values(allTransactions)
return txs.filter(isTransactionRecent).sort(newTransactionsFirst)
}, [allTransactions])
return (
<Modal title={translateString(1202, 'Recent transactions')} onDismiss={onDismiss}>
{!account && (
<Flex justifyContent="center" flexDirection="column" alignItems="center">
<Text mb="8px" bold>
Please connect your wallet to view your recent transactions
</Text>
<Button variant="tertiary" scale="sm" onClick={onDismiss}>
Close
</Button>
</Flex>
)}
{account && chainId && sortedRecentTransactions.length === 0 && (
<Flex justifyContent="center" flexDirection="column" alignItems="center">
<Text mb="8px" bold>
No recent transactions
</Text>
<Button variant="tertiary" scale="sm" onClick={onDismiss}>
Close
</Button>
</Flex>
)}
{account &&
chainId &&
sortedRecentTransactions.map((sortedRecentTransaction) => {
const { hash, summary } = sortedRecentTransaction
const { icon, color } = getRowStatus(sortedRecentTransaction)
return (
<>
<Flex key={hash} alignItems="center" justifyContent="space-between" mb="4px">
<LinkExternal href={getBscScanLink(chainId, hash, 'transaction')} color={color}>
{summary ?? hash}
</LinkExternal>
{icon}
</Flex>
</>
)
})}
</Modal>
)
}
Example #11
Source File: RecentTransactionsModal.tsx From pancake-swap-exchange-testnet with GNU General Public License v3.0 | 5 votes |
RecentTransactionsModal = ({ onDismiss = defaultOnDismiss, translateString }: RecentTransactionsModalProps) => {
const { account, chainId } = useActiveWeb3React()
const allTransactions = useAllTransactions()
// Logic taken from Web3Status/index.tsx line 175
const sortedRecentTransactions = useMemo(() => {
const txs = Object.values(allTransactions)
return txs.filter(isTransactionRecent).sort(newTransactionsFirst)
}, [allTransactions])
return (
<Modal title={translateString(1202, 'Recent transactions')} onDismiss={onDismiss}>
{!account && (
<Flex justifyContent="center" flexDirection="column" alignItems="center">
<Text mb="8px" bold>
Please connect your wallet to view your recent transactions
</Text>
<Button variant="tertiary" scale="sm" onClick={onDismiss}>
Close
</Button>
</Flex>
)}
{account && chainId && sortedRecentTransactions.length === 0 && (
<Flex justifyContent="center" flexDirection="column" alignItems="center">
<Text mb="8px" bold>
No recent transactions
</Text>
<Button variant="tertiary" scale="sm" onClick={onDismiss}>
Close
</Button>
</Flex>
)}
{account &&
chainId &&
sortedRecentTransactions.map((sortedRecentTransaction) => {
const { hash, summary } = sortedRecentTransaction
const { icon, color } = getRowStatus(sortedRecentTransaction)
return (
<>
<Flex key={hash} alignItems="center" justifyContent="space-between" mb="4px">
<LinkExternal href={getBscScanLink(chainId, hash, 'transaction')} color={color}>
{summary ?? hash}
</LinkExternal>
{icon}
</Flex>
</>
)
})}
</Modal>
)
}
Example #12
Source File: RecentTransactionsModal.tsx From mozartfinance-swap-interface with GNU General Public License v3.0 | 5 votes |
RecentTransactionsModal = ({ onDismiss = defaultOnDismiss, translateString }: RecentTransactionsModalProps) => {
const TranslateString = translateString
const { account, chainId } = useActiveWeb3React()
const allTransactions = useAllTransactions()
// Logic taken from Web3Status/index.tsx line 175
const sortedRecentTransactions = useMemo(() => {
const txs = Object.values(allTransactions)
return txs.filter(isTransactionRecent).sort(newTransactionsFirst)
}, [allTransactions])
return (
<Modal title={TranslateString(1202, 'Recent transactions')} onDismiss={onDismiss}>
{!account && (
<Flex justifyContent="center" flexDirection="column" alignItems="center">
<Text mb="8px" bold>
Please connect your wallet to view your recent transactions
</Text>
<Button variant="tertiary" scale="sm" onClick={onDismiss}>
Close
</Button>
</Flex>
)}
{account && chainId && sortedRecentTransactions.length === 0 && (
<Flex justifyContent="center" flexDirection="column" alignItems="center">
<Text mb="8px" bold>
No recent transactions
</Text>
<Button variant="tertiary" scale="sm" onClick={onDismiss}>
Close
</Button>
</Flex>
)}
{account &&
chainId &&
sortedRecentTransactions.map((sortedRecentTransaction) => {
const { hash, summary } = sortedRecentTransaction
const { icon, color } = getRowStatus(sortedRecentTransaction)
return (
<>
<Flex key={hash} alignItems="center" justifyContent="space-between" mb="4px">
<LinkExternal href={getBscScanLink(chainId, hash, 'transaction')} color={color}>
{summary ?? hash}
</LinkExternal>
{icon}
</Flex>
</>
)
})}
</Modal>
)
}
Example #13
Source File: Details.tsx From glide-frontend with GNU General Public License v3.0 | 5 votes |
Details: React.FC<DetailsProps> = ({ proposal }) => {
const { t } = useTranslation()
const startDate = new Date(proposal.start * 1000)
const endDate = new Date(proposal.end * 1000)
return (
<Card mb="16px">
<CardHeader>
<Heading as="h3" scale="md">
{t('Details')}
</Heading>
</CardHeader>
<CardBody>
<Flex alignItems="center" mb="8px">
<Text color="textSubtle">{t('Identifier')}</Text>
<LinkExternal href={`${IPFS_GATEWAY}/${proposal.id}`} ml="8px">
{proposal.id.slice(0, 8)}
</LinkExternal>
</Flex>
<Flex alignItems="center" mb="8px">
<Text color="textSubtle">{t('Creator')}</Text>
<LinkExternal href={getBscScanLink(proposal.author, 'address')} ml="8px">
{truncateWalletAddress(proposal.author)}
</LinkExternal>
</Flex>
<Flex alignItems="center" mb="16px">
<Text color="textSubtle">{t('Snapshot')}</Text>
<LinkExternal href={getBscScanLink(proposal.snapshot, 'block')} ml="8px">
{proposal.snapshot}
</LinkExternal>
</Flex>
<DetailBox p="16px">
<ProposalStateTag proposalState={proposal.state} mb="8px" />
<Flex alignItems="center">
<Text color="textSubtle" fontSize="14px">
{t('Start Date')}
</Text>
<Text ml="8px">{format(startDate, 'yyyy-MM-dd HH:mm')}</Text>
</Flex>
<Flex alignItems="center">
<Text color="textSubtle" fontSize="14px">
{t('End Date')}
</Text>
<Text ml="8px">{format(endDate, 'yyyy-MM-dd HH:mm')}</Text>
</Flex>
</DetailBox>
</CardBody>
</Card>
)
}
Example #14
Source File: PublicProfile.tsx From glide-frontend with GNU General Public License v3.0 | 5 votes |
PublicProfile = () => {
const { account } = useWeb3React()
const { profile } = useProfile()
const [usernameVisibilityToggled, setUsernameVisibility] = usePersistState(false, {
localStorageKey: 'username_visibility_toggled',
})
const { t } = useTranslation()
if (!account) {
return <WalletNotConnected />
}
const toggleUsernameVisibility = () => {
setUsernameVisibility(!usernameVisibilityToggled)
}
const { username, team, isActive, points } = profile
const Icon = usernameVisibilityToggled ? VisibilityOff : VisibilityOn
return (
<>
<Menu activeIndex={1} />
<div>
<Card>
<CardHeader>
<Flex alignItems={['start', null, 'center']} flexDirection={['column', null, 'row']}>
<EditProfileAvatar profile={profile} />
<Content>
<Flex alignItems="center">
<Username>@{usernameVisibilityToggled ? username : username.replace(/./g, '*')}</Username>
<Icon ml="4px" onClick={toggleUsernameVisibility} cursor="pointer" />
</Flex>
<Flex alignItems="center">
<AddressLink href={getBscScanLink(account, 'address')} color="text" external>
{account}
<OpenNewIcon ml="4px" />
</AddressLink>
</Flex>
<ResponsiveText bold>{team.name}</ResponsiveText>
</Content>
</Flex>
<Status>
{isActive ? (
<Tag startIcon={<CheckmarkCircleIcon width="18px" />} outline>
{t('Active')}
</Tag>
) : (
<Tag variant="failure" startIcon={<BlockIcon width="18px" />} outline>
{t('Paused')}
</Tag>
)}
</Status>
</CardHeader>
<CardBody>
<StatBox icon={PrizeIcon} title={points} subtitle={t('Points')} mb="24px" />
<Section>
<Heading as="h4" scale="md" mb="16px">
{t('Achievements')}
</Heading>
<AchievementsList />
</Section>
<Collectibles />
</CardBody>
</Card>
</div>
</>
)
}
Example #15
Source File: ActionPanel.tsx From glide-frontend with GNU General Public License v3.0 | 5 votes |
ActionPanel: React.FunctionComponent<ActionPanelProps> = ({
details,
apr,
multiplier,
liquidity,
userDataReady,
expanded,
}) => {
const farm = details
const { t } = useTranslation()
const isActive = farm.multiplier !== '0X'
const { quoteToken, token, dual } = farm
const lpLabel = farm.lpSymbol && farm.lpSymbol.toUpperCase().replace('', '')
const liquidityUrlPathParts = getLiquidityUrlPathParts({
quoteTokenAddress: quoteToken.address,
tokenAddress: token.address,
})
const lpAddress = getAddress(farm.lpAddresses)
const bsc = getBscScanLink(lpAddress, 'address')
// const info = `https://glidefinance.info/pool/${lpAddress}`
return (
<Container expanded={expanded}>
<InfoContainer>
{isActive && (
<StakeContainer>
<StyledLinkExternal href={`/add/${liquidityUrlPathParts}`}>
{t('Get %symbol%', { symbol: lpLabel })}
</StyledLinkExternal>
</StakeContainer>
)}
<StyledLinkExternal href={bsc}>{t('View Contract')}</StyledLinkExternal>
{/* <StyledLinkExternal href={info}>{t('See Pair Info')}</StyledLinkExternal> popsicle */}
<TagsContainer>
{farm.isCommunity ? <CommunityTag /> : <CoreTag />}
{dual ? <DualTag /> : null}
</TagsContainer>
</InfoContainer>
<ValueContainer>
<ValueWrapper>
<Text>{t('APR')}</Text>
<Apr {...apr} />
</ValueWrapper>
<ValueWrapper>
<Text>{t('Multiplier')}</Text>
<Multiplier {...multiplier} />
</ValueWrapper>
<ValueWrapper>
<Text>{t('Liquidity')}</Text>
<Liquidity {...liquidity} />
</ValueWrapper>
</ValueContainer>
<ActionContainer>
<HarvestAction {...farm} userDataReady={userDataReady} />
<StakedAction {...farm} userDataReady={userDataReady} />
</ActionContainer>
</Container>
)
}
Example #16
Source File: WalletInfo.tsx From glide-frontend with GNU General Public License v3.0 | 5 votes |
WalletInfo: React.FC<WalletInfoProps> = ({ hasLowBnbBalance, onDismiss }) => {
const { t } = useTranslation()
const { account } = useWeb3React()
const { balance } = useGetBnbBalance()
const { balance: cakeBalance } = useTokenBalance(getCakeAddress())
const { logout } = useAuth()
const handleLogout = () => {
onDismiss()
logout()
}
return (
<>
<Text color="secondary" fontSize="12px" textTransform="uppercase" fontWeight="bold" mb="8px">
{t('Your Address')}
</Text>
<CopyAddress account={account} mb="24px" />
{hasLowBnbBalance && (
<Message variant="warning" mb="24px">
<Box>
<Text fontWeight="bold">{t('ELA Balance Low')}</Text>
<Text as="p">{t('You need ELA for transaction fees.')}</Text>
</Box>
</Message>
)}
<Flex alignItems="center" justifyContent="space-between">
<Text color="textSubtle">{t('ELA Balance')}</Text>
<Text>{getFullDisplayBalance(balance, 18, 6)}</Text>
</Flex>
<Flex alignItems="center" justifyContent="space-between" mb="24px">
<Text color="textSubtle">{t('GLIDE Balance')}</Text>
<Text>{getFullDisplayBalance(cakeBalance, 18, 3)}</Text>
</Flex>
<Flex alignItems="center" justifyContent="end" mb="24px">
<LinkExternal href={getBscScanLink(account, 'address')}>{t('View on explorer')}</LinkExternal>
</Flex>
<Button variant="secondary" width="100%" onClick={handleLogout}>
{t('Disconnect Wallet')}
</Button>
</>
)
}
Example #17
Source File: UnsupportedCurrencyFooter.tsx From glide-frontend with GNU General Public License v3.0 | 5 votes |
UnsupportedModal: React.FC<Props> = ({ currencies, onDismiss }) => {
const { chainId } = useActiveWeb3React()
const tokens =
chainId && currencies
? currencies.map((currency) => {
return wrappedCurrency(currency, chainId)
})
: []
const unsupportedTokens: { [address: string]: Token } = useUnsupportedTokens()
return (
<Modal title="Unsupported Assets" maxWidth="420px" onDismiss={onDismiss}>
<AutoColumn gap="lg">
{tokens.map((token) => {
return (
token &&
unsupportedTokens &&
Object.keys(unsupportedTokens).includes(token.address) && (
<AutoColumn key={token.address?.concat('not-supported')} gap="10px">
<AutoRow gap="5px" align="center">
<CurrencyLogo currency={token} size="24px" />
<Text>{token.symbol}</Text>
</AutoRow>
{chainId && (
<Link external small color="primaryDark" href={getBscScanLink(token.address, 'address', chainId)}>
{token.address}
</Link>
)}
</AutoColumn>
)
)
})}
<AutoColumn gap="lg">
<Text>
Some assets are not available through this interface because they may not work well with our smart contract
or we are unable to allow trading for legal reasons.
</Text>
</AutoColumn>
</AutoColumn>
</Modal>
)
}
Example #18
Source File: updater.tsx From glide-frontend with GNU General Public License v3.0 | 5 votes |
export default function Updater(): null {
const { library, chainId } = useActiveWeb3React()
const lastBlockNumber = useBlockNumber()
const dispatch = useDispatch<AppDispatch>()
const state = useSelector<AppState, AppState['transactions']>((s) => s.transactions)
const transactions = useMemo(() => (chainId ? state[chainId] ?? {} : {}), [chainId, state])
const { toastError, toastSuccess } = useToast()
useEffect(() => {
if (!chainId || !library || !lastBlockNumber) return
Object.keys(transactions)
.filter((hash) => shouldCheck(lastBlockNumber, transactions[hash]))
.forEach((hash) => {
library
.getTransactionReceipt(hash)
.then((receipt) => {
if (receipt) {
dispatch(
finalizeTransaction({
chainId,
hash,
receipt: {
blockHash: receipt.blockHash,
blockNumber: receipt.blockNumber,
contractAddress: receipt.contractAddress,
from: receipt.from,
status: receipt.status,
to: receipt.to,
transactionHash: receipt.transactionHash,
transactionIndex: receipt.transactionIndex,
},
}),
)
const toast = receipt.status === 1 ? toastSuccess : toastError
toast(
'Transaction receipt',
<Flex flexDirection="column">
<Text>{transactions[hash]?.summary ?? `Hash: ${hash.slice(0, 8)}...${hash.slice(58, 65)}`}</Text>
{chainId && (
<Link external href={getBscScanLink(hash, 'transaction', chainId)}>
View on explorer
</Link>
)}
</Flex>,
)
} else {
dispatch(checkedTransaction({ chainId, hash, blockNumber: lastBlockNumber }))
}
})
.catch((error) => {
console.error(`failed to check transaction hash: ${hash}`, error)
})
})
}, [chainId, library, transactions, lastBlockNumber, dispatch, toastSuccess, toastError])
return null
}
Example #19
Source File: EndsInCell.tsx From glide-frontend with GNU General Public License v3.0 | 5 votes |
EndsInCell: React.FC<FinishCellProps> = ({ pool }) => {
const { sousId, totalStaked, startBlock, endBlock, isFinished } = pool
const { currentBlock } = useBlock()
const { t } = useTranslation()
const { shouldShowBlockCountdown, blocksUntilStart, blocksRemaining, hasPoolStarted, blocksToDisplay } =
getPoolBlockInfo(pool, currentBlock)
const isCakePool = sousId === 0
const renderBlocks = shouldShowBlockCountdown ? (
<Flex alignItems="center">
<Flex flex="1.3">
<Balance fontSize="16px" value={blocksToDisplay} decimals={0} />
<Text ml="4px" textTransform="lowercase">
{t('Blocks')}
</Text>
</Flex>
<Flex flex="1">
<Link
external
href={getBscScanLink(hasPoolStarted ? endBlock : startBlock, 'countdown')}
onClick={(e) => e.stopPropagation()}
>
<TimerIcon ml="4px" />
</Link>
</Flex>
</Flex>
) : (
<Text>-</Text>
)
// A bit hacky way to determine if public data is loading relying on totalStaked
// Opted to go for this since we don't really need a separate publicDataLoaded flag
// anywhere else
const isLoadingPublicData = !totalStaked.gt(0) || !currentBlock || (!blocksRemaining && !blocksUntilStart)
const showLoading = isLoadingPublicData && !isCakePool && !isFinished
return (
<StyledCell role="cell">
<CellContent>
<Text fontSize="12px" color="textSubtle" textAlign="left">
{hasPoolStarted || !shouldShowBlockCountdown ? t('Ends in') : t('Starts in')}
</Text>
{showLoading ? <Skeleton width="80px" height="16px" /> : renderBlocks}
</CellContent>
</StyledCell>
)
}
Example #20
Source File: AuctionLeaderboardTable.tsx From glide-frontend with GNU General Public License v3.0 | 5 votes |
LeaderboardRow: React.FC<LeaderboardRowProps> = ({ bidder, cakePriceUsdc, isMobile }) => {
const { t } = useTranslation()
const { isTopPosition, position, samePositionAsAbove, farmName, tokenName, amount, projectSite, lpAddress, account } =
bidder
return (
<>
<GridCell isTopPosition={isTopPosition} pl={['12px', '24px']}>
<Flex>
<Text bold={isTopPosition} color={samePositionAsAbove ? 'textDisabled' : 'text'} textTransform="uppercase">
#{position}
</Text>
</Flex>
</GridCell>
<GridCell isTopPosition={isTopPosition}>
<Flex flexDirection="column" pl={['8px']}>
<Flex>
<Text bold={isTopPosition} mr="4px">
{farmName}
</Text>
{!isMobile && <Text>(1x)</Text>}
</Flex>
<Text fontSize="12px" color="textSubtle">
{tokenName}
</Text>
</Flex>
</GridCell>
<GridCell isTopPosition={isTopPosition}>
<Flex flexDirection="column" width="100%" justifyContent="flex-end" pr={[null, null, '24px']}>
<Text bold textTransform="uppercase" width="100%" textAlign="right">
{getBalanceNumber(amount).toLocaleString()}
</Text>
{cakePriceUsdc.gt(0) ? (
<Text fontSize="12px" color="textSubtle" textAlign="right">
~${getBalanceNumber(amount.times(cakePriceUsdc)).toLocaleString('en', { maximumFractionDigits: 0 })}
</Text>
) : (
<Flex justifyContent="flex-end">
<Skeleton width="48px" />
</Flex>
)}
</Flex>
</GridCell>
<GridCell isTopPosition={isTopPosition}>
<SubMenu component={<EllipsisIcon height="16px" width="16px" />}>
{projectSite && (
<SubMenuItem as={LinkExternal} href={projectSite} bold={false} color="text">
{t('Project Site')}
</SubMenuItem>
)}
{lpAddress && (
<SubMenuItem as={LinkExternal} href={`http://pancakeswap.info/pool/${lpAddress}`} bold={false} color="text">
{t('LP Info')}
</SubMenuItem>
)}
{account && (
<SubMenuItem as={LinkExternal} href={getBscScanLink(account, 'address')} bold={false} color="text">
{t('Bidder Address')}
</SubMenuItem>
)}
</SubMenu>
</GridCell>
</>
)
}
Example #21
Source File: FarmCard.tsx From glide-frontend with GNU General Public License v3.0 | 5 votes |
FarmCard: React.FC<FarmCardProps> = ({ farm, displayApr, removed, cakePrice, account }) => {
const { t } = useTranslation()
const [showExpandableSection, setShowExpandableSection] = useState(false)
const totalValueFormatted =
farm.liquidity && farm.liquidity.gt(0)
? `$${farm.liquidity.toNumber().toLocaleString(undefined, { maximumFractionDigits: 0 })}`
: ''
const lpLabel = farm.lpSymbol && farm.lpSymbol.toUpperCase().replace('', '')
const earnLabel = farm.dual ? farm.dual.earnLabel : t('GLIDE + Fees')
const liquidityUrlPathParts = getLiquidityUrlPathParts({
quoteTokenAddress: farm.quoteToken.address,
tokenAddress: farm.token.address,
})
const addLiquidityUrl = `${BASE_ADD_LIQUIDITY_URL}/${liquidityUrlPathParts}`
const lpAddress = getAddress(farm.lpAddresses)
const isPromotedFarm = farm.token.symbol === 'GLIDE'
return (
<StyledCard isActive={isPromotedFarm}>
<FarmCardInnerContainer>
<CardHeading
lpLabel={lpLabel}
multiplier={farm.multiplier}
isCommunityFarm={farm.isCommunity}
token={farm.token}
quoteToken={farm.quoteToken}
/>
{!removed && (
<Flex justifyContent="space-between" alignItems="center">
<Text>{t('APR')}:</Text>
<Text bold style={{ display: 'flex', alignItems: 'center' }}>
{farm.apr ? (
<>
<ApyButton
lpLabel={lpLabel}
addLiquidityUrl={addLiquidityUrl}
cakePrice={cakePrice}
apr={farm.apr}
displayApr={displayApr}
/>
{displayApr}%
</>
) : (
<Skeleton height={24} width={80} />
)}
</Text>
</Flex>
)}
<Flex justifyContent="space-between">
<Text>{t('Earn')}:</Text>
<Text bold>{earnLabel}</Text>
</Flex>
<CardActionsContainer farm={farm} account={account} addLiquidityUrl={addLiquidityUrl} />
</FarmCardInnerContainer>
<ExpandingWrapper>
<ExpandableSectionButton
onClick={() => setShowExpandableSection(!showExpandableSection)}
expanded={showExpandableSection}
/>
{showExpandableSection && (
<DetailsSection
removed={removed}
bscScanAddress={getBscScanLink(lpAddress, 'address')}
// infoAddress={`https://glidefinance.info/pool/${lpAddress}`}
totalValueFormatted={totalValueFormatted}
lpLabel={lpLabel}
addLiquidityUrl={addLiquidityUrl}
/>
)}
</ExpandingWrapper>
</StyledCard>
)
}
Example #22
Source File: Achievement.tsx From glide-frontend with GNU General Public License v3.0 | 5 votes |
Achievement: React.FC<Props> = ({ ifo, publicIfoData }) => {
const { t } = useTranslation()
const tokenName = ifo.token.symbol.toLowerCase()
const campaignTitle = ifo.name
const minLpForAchievement = MIN_DOLLAR_FOR_ACHIEVEMENT.div(publicIfoData.currencyPriceInUSD).toNumber()
return (
<Container>
<AchievementFlex isFinished={publicIfoData.status === 'finished'} alignItems="center" flexGrow={1}>
<Image src={`/images/achievements/ifo-${tokenName}.svg`} width={56} height={56} mr="8px" />
<Flex flexDirection="column">
<Text color="secondary" fontSize="12px">
{`${t('Achievement')}:`}
</Text>
<Flex>
<Text bold mr="8px">
{t('IFO Shopper: %title%', { title: campaignTitle })}
</Text>
<Flex alignItems="center" mr="8px">
<PrizeIcon color="textSubtle" width="16px" mr="4px" />
<Text color="textSubtle">{publicIfoData.numberPoints}</Text>
</Flex>
</Flex>
{publicIfoData.currencyPriceInUSD.gt(0) ? (
<Text color="textSubtle" fontSize="12px">
{t('Commit ~%amount% LP in total to earn!', { amount: minLpForAchievement.toFixed(3) })}
</Text>
) : (
<Skeleton minHeight={18} width={80} />
)}
</Flex>
</AchievementFlex>
<Flex alignItems="flex-end" flexDirection="column">
<StyledLinkExternal href={ifo.articleUrl} mb="8px">
{t('Learn more about %title%', { title: campaignTitle })}
</StyledLinkExternal>
<StyledLinkExternal href={getBscScanLink(ifo.address, 'address')}>{t('View Contract')}</StyledLinkExternal>
</Flex>
</Container>
)
}
Example #23
Source File: CollectRoundWinningsModal.tsx From glide-frontend with GNU General Public License v3.0 | 4 votes |
CollectRoundWinningsModal: React.FC<CollectRoundWinningsModalProps> = ({ payout, betAmount, epoch, onDismiss, onSuccess, }) => { const [isPendingTx, setIsPendingTx] = useState(false) const { account } = useWeb3React() const { t } = useTranslation() const { toastSuccess, toastError } = useToast() const predictionsContract = usePredictionsContract() const bnbUsdcPrice = usePriceBnbUsdc() const dispatch = useAppDispatch() // Convert payout to number for compatibility const payoutAsFloat = parseFloat(payout) const betAmountAsFloat = parseFloat(betAmount) const handleClick = async () => { try { const tx = await predictionsContract.claim(epoch) setIsPendingTx(true) const receipt = await tx.wait() if (onSuccess) { await onSuccess() } await dispatch(fetchClaimableStatuses({ account, epochs: [epoch] })) onDismiss() setIsPendingTx(false) toastSuccess( t('Winnings collected!'), <Box> <Text as="p" mb="8px"> {t('Your prizes have been sent to your wallet')} </Text> {receipt.transactionHash && ( <LinkExternal href={getBscScanLink(receipt.transactionHash, 'transaction')}> {t('View on explorer')} </LinkExternal> )} </Box>, ) } catch { toastError(t('Error'), t('Please try again. Confirm the transaction and make sure you are paying enough gas!')) } finally { setIsPendingTx(false) } } return ( <Modal minWidth="288px" position="relative" mt="124px"> <BunnyDecoration> <img src="/images/decorations/prize-bunny.png" alt="bunny decoration" height="124px" width="168px" /> </BunnyDecoration> <ModalHeader> <ModalTitle> <Heading>{t('Collect Winnings')}</Heading> </ModalTitle> <ModalCloseButton onDismiss={onDismiss} /> </ModalHeader> <ModalBody p="24px"> <TrophyGoldIcon width="96px" mx="auto" mb="24px" /> <Flex alignItems="start" justifyContent="space-between" mb="8px"> <Text>{t('Your position')}</Text> <Box style={{ textAlign: 'right' }}> <Text>{`${betAmount} BNB`}</Text> <Text fontSize="12px" color="textSubtle"> {`~$${bnbUsdcPrice.times(betAmountAsFloat).toFormat(2)}`} </Text> </Box> </Flex> <Flex alignItems="start" justifyContent="space-between" mb="24px"> <Text>{t('Your winnings')}</Text> <Box style={{ textAlign: 'right' }}> <Text>{`${payout} BNB`}</Text> <Text fontSize="12px" color="textSubtle"> {`~$${bnbUsdcPrice.times(payoutAsFloat).toFormat(2)}`} </Text> </Box> </Flex> <Button width="100%" mb="8px" onClick={handleClick} isLoading={isPendingTx} endIcon={isPendingTx ? <AutoRenewIcon spin color="currentColor" /> : null} > {t('Confirm')} </Button> </ModalBody> </Modal> ) }
Example #24
Source File: ExpandedFooter.tsx From glide-frontend with GNU General Public License v3.0 | 4 votes |
ExpandedFooter: React.FC<ExpandedFooterProps> = ({ pool, account }) => {
const { t } = useTranslation()
const { currentBlock } = useBlock()
const {
totalCakeInVault,
fees: { performanceFee },
} = useCakeVault()
const {
stakingToken,
earningToken,
totalStaked,
startBlock,
endBlock,
stakingLimit,
contractAddress,
sousId,
isAutoVault,
} = pool
const tokenAddress = earningToken.address ? getAddress(earningToken.address) : ''
const poolContractAddress = getAddress(contractAddress)
const cakeVaultContractAddress = getCakeVaultAddress()
const isMetaMaskInScope = !!window.ethereum?.isMetaMask
const isManualCakePool = sousId === 0
const { shouldShowBlockCountdown, blocksUntilStart, blocksRemaining, hasPoolStarted, blocksToDisplay } =
getPoolBlockInfo(pool, currentBlock)
const { targetRef, tooltip, tooltipVisible } = useTooltip(
t('Subtracted automatically from each yield harvest and burned.'),
{ placement: 'bottom-start' },
)
const getTotalStakedBalance = () => {
if (isAutoVault) {
return getBalanceNumber(totalCakeInVault, stakingToken.decimals)
}
if (isManualCakePool) {
const manualCakeTotalMinusAutoVault = new BigNumber(totalStaked).minus(totalCakeInVault)
return getBalanceNumber(manualCakeTotalMinusAutoVault, stakingToken.decimals)
}
return getBalanceNumber(totalStaked, stakingToken.decimals)
}
const {
targetRef: totalStakedTargetRef,
tooltip: totalStakedTooltip,
tooltipVisible: totalStakedTooltipVisible,
} = useTooltip(t('Total amount of %symbol% staked in this pool', { symbol: stakingToken.symbol }), {
placement: 'bottom',
})
return (
<ExpandedWrapper flexDirection="column">
<Flex mb="2px" justifyContent="space-between" alignItems="center">
<Text small>{t('Total staked')}:</Text>
<Flex alignItems="flex-start">
{totalStaked && totalStaked.gte(0) ? (
<>
<Balance small value={getTotalStakedBalance()} decimals={0} unit={` ${stakingToken.symbol}`} />
<span ref={totalStakedTargetRef}>
<HelpIcon color="textSubtle" width="20px" ml="6px" mt="4px" />
</span>
</>
) : (
<Skeleton width="90px" height="21px" />
)}
{totalStakedTooltipVisible && totalStakedTooltip}
</Flex>
</Flex>
{stakingLimit && stakingLimit.gt(0) && (
<Flex mb="2px" justifyContent="space-between">
<Text small>{t('Max. stake per user')}:</Text>
<Text small>{`${getFullDisplayBalance(stakingLimit, stakingToken.decimals, 0)} ${stakingToken.symbol}`}</Text>
</Flex>
)}
{shouldShowBlockCountdown && (
<Flex mb="2px" justifyContent="space-between" alignItems="center">
<Text small>{hasPoolStarted ? t('Ends in') : t('Starts in')}:</Text>
{blocksRemaining || blocksUntilStart ? (
<Flex alignItems="center">
<Link external href={getBscScanLink(hasPoolStarted ? endBlock : startBlock, 'countdown')}>
<Balance small value={blocksToDisplay} decimals={0} color="primary" />
<Text small ml="4px" color="primary" textTransform="lowercase">
{t('Blocks')}
</Text>
<TimerIcon ml="4px" color="primary" />
</Link>
</Flex>
) : (
<Skeleton width="54px" height="21px" />
)}
</Flex>
)}
{isAutoVault && (
<Flex mb="2px" justifyContent="space-between" alignItems="center">
{tooltipVisible && tooltip}
<TooltipText ref={targetRef} small>
{t('Performance Fee')}
</TooltipText>
<Flex alignItems="center">
<Text ml="4px" small>
{performanceFee / 100}%
</Text>
</Flex>
</Flex>
)}
{/* <Flex mb="2px" justifyContent="flex-end">
<LinkExternal href={`https://pancakeswap.info/token/${getAddress(earningToken.address)}`} bold={false} small>
{t('See Token Info')}
</LinkExternal>
</Flex> */}
<Flex mb="2px" justifyContent="flex-end">
<LinkExternal href={earningToken.projectLink} bold={false} small>
{t('View Project Site')}
</LinkExternal>
</Flex>
{poolContractAddress && (
<Flex mb="2px" justifyContent="flex-end">
<LinkExternal
href={`${BASE_BSC_SCAN_URL}/address/${isAutoVault ? cakeVaultContractAddress : poolContractAddress}`}
bold={false}
small
>
{t('View Contract')}
</LinkExternal>
</Flex>
)}
{account && isMetaMaskInScope && tokenAddress && (
<Flex justifyContent="flex-end">
<Button
variant="text"
p="0"
height="auto"
onClick={() => registerToken(tokenAddress, earningToken.symbol, earningToken.decimals)}
>
<Text color="primary" fontSize="14px">
{t('Add to Metamask')}
</Text>
<MetamaskIcon ml="4px" />
</Button>
</Flex>
)}
</ExpandedWrapper>
)
}
Example #25
Source File: BetResult.tsx From glide-frontend with GNU General Public License v3.0 | 4 votes |
BetResult: React.FC<BetResultProps> = ({ bet, result }) => {
const { t } = useTranslation()
const dispatch = useAppDispatch()
const { account } = useWeb3React()
const { isRefundable } = useIsRefundable(bet.round.epoch)
const bnbUsdcPrice = usePriceBnbUsdc()
const canClaim = !bet.claimed && bet.position === bet.round.position
const rewardRate = useGetRewardRate()
const { targetRef, tooltip, tooltipVisible } = useTooltip(
<Text as="p">{t('Includes your original position and your winnings, minus the %fee% fee.', { fee: '3%' })}</Text>,
{ placement: 'auto' },
)
const isWinner = result === Result.WIN
// Winners get the payout, otherwise the claim what they put it if it was canceled
const payout = isWinner ? getNetPayout(bet, rewardRate) : bet.amount
const returned = payout + bet.amount
const getHeaderColor = () => {
switch (result) {
case Result.WIN:
return 'warning'
case Result.LOSE:
return 'textSubtle'
case Result.CANCELED:
return 'textDisabled'
default:
return 'text'
}
}
const getHeaderText = () => {
switch (result) {
case Result.WIN:
return t('Win')
case Result.LOSE:
return t('Lose')
case Result.CANCELED:
return t('Canceled')
default:
return ''
}
}
const getHeaderIcon = () => {
switch (result) {
case Result.WIN:
return <PrizeIcon color={getHeaderColor()} />
case Result.LOSE:
case Result.CANCELED:
return <BlockIcon color={getHeaderColor()} />
default:
return null
}
}
const getResultColor = () => {
switch (result) {
case Result.WIN:
return 'success'
case Result.LOSE:
return 'failure'
case Result.CANCELED:
default:
return 'text'
}
}
const handleSuccess = async () => {
// We have to mark the bet as claimed immediately because it does not update fast enough
dispatch(markBetHistoryAsCollected({ account, betId: bet.id }))
dispatch(fetchLedgerData({ account, epochs: [bet.round.epoch] }))
}
return (
<>
<Flex alignItems="center" justifyContent="space-between" mb="8px">
<Heading>{t('Your History')}</Heading>
<Flex alignItems="center">
<Heading as="h3" color={getHeaderColor()} textTransform="uppercase" bold mr="4px">
{getHeaderText()}
</Heading>
{getHeaderIcon()}
</Flex>
</Flex>
<StyledBetResult>
{result === Result.WIN && !canClaim && (
<CollectWinningsButton
payout={formatBnb(payout)}
betAmount={bet.amount.toString()}
epoch={bet.round.epoch}
hasClaimed={!canClaim}
width="100%"
mb="16px"
onSuccess={handleSuccess}
>
{bet.claimed ? t('Already Collected') : t('Collect Winnings')}
</CollectWinningsButton>
)}
{bet.claimed && (
<Flex justifyContent="center">
<LinkExternal href={getBscScanLink(bet.claimedHash, 'transaction')} mb="16px">
{t('View on explorer')}
</LinkExternal>
</Flex>
)}
{result === Result.CANCELED && isRefundable && (
<ReclaimPositionButton epoch={bet.round.epoch} width="100%" mb="16px" />
)}
<Flex alignItems="center" justifyContent="space-between" mb="16px">
<Text>{t('Your direction')}:</Text>
<PositionTag betPosition={bet.position}>
{bet.position === BetPosition.BULL ? t('Up') : t('Down')}
</PositionTag>
</Flex>
<Flex alignItems="center" justifyContent="space-between" mb="16px">
<Text>{t('Your position')}</Text>
<Text>{`${formatBnb(bet.amount)} BNB`}</Text>
</Flex>
<Flex alignItems="start" justifyContent="space-between">
<Text bold>{isWinner ? t('Your winnings') : t('Your Result')}:</Text>
<Box style={{ textAlign: 'right' }}>
<Text bold color={getResultColor()}>{`${isWinner ? '+' : '-'}${formatBnb(payout)} BNB`}</Text>
<Text fontSize="12px" color="textSubtle">
{`~$${formatBnb(bnbUsdcPrice.times(payout).toNumber())}`}
</Text>
</Box>
</Flex>
{isWinner && (
<>
<Divider />
<Flex alignItems="start" justifyContent="space-between">
<Text fontSize="14px" color="textSubtle">
{t('Amount to collect')}:
</Text>
<Flex justifyContent="end">
<Text fontSize="14px" color="textSubtle">{`${formatBnb(returned)} BNB`}</Text>
<span ref={targetRef}>
<InfoIcon color="textSubtle" ml="4px" />
</span>
</Flex>
{tooltipVisible && tooltip}
</Flex>
</>
)}
</StyledBetResult>
</>
)
}
Example #26
Source File: PnlTab.tsx From glide-frontend with GNU General Public License v3.0 | 4 votes |
PnlTab: React.FC<PnlTabProps> = ({ hasBetHistory, bets }) => {
const { t } = useTranslation()
const { account } = useWeb3React()
const currentEpoch = useGetCurrentEpoch()
const bnbUsdcPrice = usePriceBnbUsdc()
const summary = getPnlSummary(bets, currentEpoch)
const netResultAmount = summary.won.payout - summary.lost.amount
const netResultIsPositive = netResultAmount > 0
const avgPositionEntered = summary.entered.amount / summary.entered.rounds
const avgBnbWonPerRound = netResultAmount / summary.entered.rounds
const avgBnbWonIsPositive = avgBnbWonPerRound > 0
// Guard in case user has only lost rounds
const hasBestRound = summary.won.bestRound.payout !== 0
return hasBetHistory ? (
<Box p="16px">
<Text bold fontSize="24px" color="secondary" pb="24px">
{t('Your history')}
</Text>
<Flex>
<PnlChart lost={summary.lost.rounds} won={summary.won.rounds} />
<Flex flexDirection="column" justifyContent="center" pl="24px">
<Text bold color="textSubtle">
{t('Net results')}
</Text>
<Text bold fontSize="24px" lineHeight="1" color={netResultIsPositive ? 'success' : 'failure'}>
{`${netResultIsPositive ? '+' : ''}${formatBnb(netResultAmount)} BNB`}
</Text>
<Text small color="textSubtle">
{`~$${formatBnb(bnbUsdcPrice.times(netResultAmount).toNumber())}`}
</Text>
</Flex>
</Flex>
<Box pl="8px">
<Text mt="24px" bold color="textSubtle">
{t('Average return / round')}
</Text>
<Text bold color={avgBnbWonIsPositive ? 'success' : 'failure'}>
{`${avgBnbWonIsPositive ? '+' : ''}${formatBnb(avgBnbWonPerRound)} BNB`}
</Text>
<Text small color="textSubtle">
{`~$${formatBnb(bnbUsdcPrice.times(avgBnbWonPerRound).toNumber())}`}
</Text>
{hasBestRound && (
<>
<Text mt="16px" bold color="textSubtle">
{t('Best round: #%roundId%', { roundId: summary.won.bestRound.id })}
</Text>
<Flex alignItems="flex-end">
<Text bold color="success">{`+${formatBnb(summary.won.bestRound.payout)} BNB`}</Text>
<Text ml="4px" small color="textSubtle">
({summary.won.bestRound.multiplier.toFixed(2)}x)
</Text>
</Flex>
<Text small color="textSubtle">
{`~$${formatBnb(bnbUsdcPrice.times(summary.won.bestRound.payout).toNumber())}`}
</Text>
</>
)}
<Text mt="16px" bold color="textSubtle">
{t('Average position entered / round')}
</Text>
<Text bold>{`${formatBnb(avgPositionEntered)} BNB`}</Text>
<Text small color="textSubtle">
{`~$${formatBnb(bnbUsdcPrice.times(avgPositionEntered).toNumber())}`}
</Text>
<Divider />
<SummaryRow type="won" summary={summary} bnbUsdcPrice={bnbUsdcPrice} />
<SummaryRow type="lost" summary={summary} bnbUsdcPrice={bnbUsdcPrice} />
<SummaryRow type="entered" summary={summary} bnbUsdcPrice={bnbUsdcPrice} />
<Flex justifyContent="center" mt="24px">
<Link href={`${getBscScanLink(account, 'address')}#internaltx`} mb="16px" external>
<Button mt="8px" width="100%">
{t('View Reclaimed & Won')}
<OpenNewIcon color="white" ml="4px" />
</Button>
</Link>
</Flex>
</Box>
</Box>
) : (
<Box p="24px">
<Heading size="lg" textAlign="center" mb="8px">
{t('No prediction history available')}
</Heading>
<Text as="p" textAlign="center">
{t(
'If you are sure you should see history here, make sure you’re connected to the correct wallet and try again.',
)}
</Text>
</Box>
)
}
Example #27
Source File: ActionPanel.tsx From glide-frontend with GNU General Public License v3.0 | 4 votes |
ActionPanel: React.FC<ActionPanelProps> = ({ account, pool, userDataLoaded, expanded, breakpoints }) => {
const {
sousId,
stakingToken,
earningToken,
totalStaked,
startBlock,
endBlock,
stakingLimit,
contractAddress,
isAutoVault,
isDividendPool,
} = pool
const { t } = useTranslation()
const poolContractAddress = getAddress(contractAddress)
const cakeVaultContractAddress = getCakeVaultAddress()
const { currentBlock } = useBlock()
const { isXs, isSm, isMd } = breakpoints
const showSubtitle = (isXs || isSm) && sousId === 0
const { shouldShowBlockCountdown, blocksUntilStart, blocksRemaining, hasPoolStarted, blocksToDisplay } =
getPoolBlockInfo(pool, currentBlock)
const isMetaMaskInScope = !!window.ethereum?.isMetaMask
const tokenAddress = earningToken.address ? getAddress(earningToken.address) : ''
const {
totalCakeInVault,
fees: { performanceFee },
} = useCakeVault()
const performanceFeeAsDecimal = performanceFee && performanceFee / 100
const isManualCakePool = sousId === 0
const getTotalStakedBalance = () => {
if (isAutoVault) {
return getBalanceNumber(totalCakeInVault, stakingToken.decimals)
}
if (isDividendPool) {
return getBalanceNumber(totalCakeInVault, stakingToken.decimals)
}
if (isManualCakePool) {
const manualCakeTotalMinusAutoVault = new BigNumber(totalStaked).minus(totalCakeInVault)
return getBalanceNumber(manualCakeTotalMinusAutoVault, stakingToken.decimals)
}
return getBalanceNumber(totalStaked, stakingToken.decimals)
}
const {
targetRef: totalStakedTargetRef,
tooltip: totalStakedTooltip,
tooltipVisible: totalStakedTooltipVisible,
} = useTooltip(t('Total amount of %symbol% staked in this pool', { symbol: stakingToken.symbol }), {
placement: 'bottom',
})
const manualTooltipText = t('You must harvest and compound your earnings from this pool manually.')
const autoTooltipText = t(
'Any funds you stake in this pool will be automatically harvested and restaked (compounded) for you.',
)
const {
targetRef: tagTargetRef,
tooltip: tagTooltip,
tooltipVisible: tagTooltipVisible,
} = useTooltip(isDividendPool ? autoTooltipText : isAutoVault ? autoTooltipText : manualTooltipText, {
placement: 'bottom-start',
})
const maxStakeRow = stakingLimit.gt(0) ? (
<Flex mb="8px" justifyContent="space-between">
<Text>{t('Max. stake per user')}:</Text>
<Text>{`${getFullDisplayBalance(stakingLimit, stakingToken.decimals, 0)} ${stakingToken.symbol}`}</Text>
</Flex>
) : null
const blocksRow =
blocksRemaining || blocksUntilStart ? (
<Flex mb="8px" justifyContent="space-between">
<Text>{hasPoolStarted ? t('Ends in') : t('Starts in')}:</Text>
<Flex>
<Link external href={getBscScanLink(hasPoolStarted ? endBlock : startBlock, 'countdown')}>
<Balance fontSize="16px" value={blocksToDisplay} decimals={0} color="primary" />
<Text ml="4px" color="primary" textTransform="lowercase">
{t('Blocks')}
</Text>
<TimerIcon ml="4px" color="primary" />
</Link>
</Flex>
</Flex>
) : (
<Skeleton width="56px" height="16px" />
)
const aprRow = (
<Flex justifyContent="space-between" alignItems="center" mb="8px">
<Text>{isAutoVault ? t('APY') : t('APR')}:</Text>
<Apr pool={pool} showIcon performanceFee={isAutoVault ? performanceFeeAsDecimal : 0} />
</Flex>
)
const totalStakedRow = (
<Flex justifyContent="space-between" alignItems="center" mb="8px">
<Text maxWidth={['50px', '100%']}>{t('Total staked')}:</Text>
<Flex alignItems="center">
{totalStaked && totalStaked.gte(0) ? (
<>
<Balance fontSize="16px" value={getTotalStakedBalance()} decimals={0} unit={` ${stakingToken.symbol}`} />
<span ref={totalStakedTargetRef}>
<HelpIcon color="textSubtle" width="20px" ml="4px" />
</span>
</>
) : (
<Skeleton width="56px" height="16px" />
)}
{totalStakedTooltipVisible && totalStakedTooltip}
</Flex>
</Flex>
)
return (
<StyledActionPanel expanded={expanded}>
<InfoSection>
{maxStakeRow}
{(isXs || isSm) && aprRow}
{(isXs || isSm || isMd) && totalStakedRow}
{shouldShowBlockCountdown && blocksRow}
{/* <Flex mb="8px" justifyContent={['flex-end', 'flex-end', 'flex-start']}>
<LinkExternal href={`https://pancakeswap.info/token/${getAddress(earningToken.address)}`} bold={false}>
{t('See Token Info')}
</LinkExternal>
</Flex> */}
<Flex mb="8px" justifyContent={['flex-end', 'flex-end', 'flex-start']}>
<LinkExternal href={earningToken.projectLink} bold={false}>
{t('View Project Site')}
</LinkExternal>
</Flex>
{poolContractAddress && (
<Flex mb="8px" justifyContent={['flex-end', 'flex-end', 'flex-start']}>
<LinkExternal
href={`${BASE_BSC_SCAN_URL}/address/${isAutoVault ? cakeVaultContractAddress : poolContractAddress}`}
bold={false}
>
{t('View Contract')}
</LinkExternal>
</Flex>
)}
{account && isMetaMaskInScope && tokenAddress && (
<Flex mb="8px" justifyContent={['flex-end', 'flex-end', 'flex-start']}>
<Button
variant="text"
p="0"
height="auto"
onClick={() => registerToken(tokenAddress, earningToken.symbol, earningToken.decimals)}
>
<Text color="primary">{t('Add to Metamask')}</Text>
<MetamaskIcon ml="4px" />
</Button>
</Flex>
)}
{isDividendPool ? <CompoundingPoolTag /> : isAutoVault ? <CompoundingPoolTag /> : <ManualPoolTag />}
{tagTooltipVisible && tagTooltip}
<span ref={tagTargetRef}>
<HelpIcon ml="4px" width="20px" height="20px" color="textSubtle" />
</span>
</InfoSection>
<ActionContainer>
{showSubtitle && (
<Text mt="4px" mb="16px" color="textSubtle">
{isAutoVault ? t('Automatic restaking') : `${t('Earn')} GLIDE ${t('Stake').toLocaleLowerCase()} GLIDE`}
</Text>
)}
<Harvest {...pool} userDataLoaded={userDataLoaded} />
<Stake pool={pool} userDataLoaded={userDataLoaded} />
</ActionContainer>
</StyledActionPanel>
)
}
Example #28
Source File: index.tsx From glide-frontend with GNU General Public License v3.0 | 4 votes |
CreateProposal = () => {
const [state, setState] = useState<FormState>({
name: '',
body: '',
choices: times(MINIMUM_CHOICES).map(makeChoice),
startDate: null,
startTime: null,
endDate: null,
endTime: null,
snapshot: 0,
})
const [isLoading, setIsLoading] = useState(false)
const [fieldsState, setFieldsState] = useState<{ [key: string]: boolean }>({})
const { t } = useTranslation()
const { account } = useWeb3React()
const initialBlock = useInitialBlock()
const { push } = useHistory()
const { library } = useWeb3Provider()
const { toastSuccess, toastError } = useToast()
const [onPresentVoteDetailsModal] = useModal(<VoteDetailsModal block={state.snapshot} />)
const { name, body, choices, startDate, startTime, endDate, endTime, snapshot } = state
const formErrors = getFormErrors(state, t)
const handleSubmit = async (evt: FormEvent<HTMLFormElement>) => {
evt.preventDefault()
try {
setIsLoading(true)
const proposal = JSON.stringify({
...generatePayloadData(),
type: SnapshotCommand.PROPOSAL,
payload: {
name,
body,
snapshot,
start: combineDateAndTime(startDate, startTime),
end: combineDateAndTime(endDate, endTime),
choices: choices
.filter((choice) => choice.value)
.map((choice) => {
return choice.value
}),
metadata: generateMetaData(),
type: 'single-choice',
},
})
const sig = await signMessage(library, account, proposal)
if (sig) {
const msg: Message = { address: account, msg: proposal, sig }
// Save proposal to snapshot
const data = await sendSnaphotData(msg)
// Redirect user to newly created proposal page
push(`/voting/proposal/${data.ipfsHash}`)
toastSuccess(t('Proposal created!'))
} else {
toastError(t('Error'), t('Unable to sign payload'))
}
} catch (error) {
// @ts-ignore
toastError(t('Error'), error?.message || error?.error)
console.error(error)
setIsLoading(false)
}
}
const updateValue = (key: string, value: string | Choice[] | Date) => {
setState((prevState) => ({
...prevState,
[key]: value,
}))
// Keep track of what fields the user has attempted to edit
setFieldsState((prevFieldsState) => ({
...prevFieldsState,
[key]: true,
}))
}
const handleChange = (evt: ChangeEvent<HTMLInputElement>) => {
const { name: inputName, value } = evt.currentTarget
updateValue(inputName, value)
}
const handleEasyMdeChange = (value: string) => {
updateValue('body', value)
}
const handleChoiceChange = (newChoices: Choice[]) => {
updateValue('choices', newChoices)
}
const handleDateChange = (key: string) => (value: Date) => {
updateValue(key, value)
}
const options = useMemo(
() => ({
hideIcons: account === ADMIN_ADDRESS ? [] : ['guide', 'fullscreen', 'preview', 'side-by-side', 'image'],
}),
[account],
)
useEffect(() => {
if (initialBlock > 0) {
setState((prevState) => ({
...prevState,
snapshot: initialBlock,
}))
}
}, [initialBlock, setState])
return (
<Container py="40px">
<Box mb="48px">
<Breadcrumbs>
<BreadcrumbLink to="/">{t('Home')}</BreadcrumbLink>
<BreadcrumbLink to="/voting">{t('Voting')}</BreadcrumbLink>
<Text>{t('Make a Proposal')}</Text>
</Breadcrumbs>
</Box>
<form onSubmit={handleSubmit}>
<Layout>
<Box>
<Box mb="24px">
<Label htmlFor="name">{t('Title')}</Label>
<Input id="name" name="name" value={name} scale="lg" onChange={handleChange} required />
{formErrors.name && fieldsState.name && <FormErrors errors={formErrors.name} />}
</Box>
<Box mb="24px">
<Label htmlFor="body">{t('Content')}</Label>
<Text color="textSubtle" mb="8px">
{t('Tip: write in Markdown!')}
</Text>
<EasyMde
id="body"
name="body"
onTextChange={handleEasyMdeChange}
value={body}
options={options}
required
/>
{formErrors.body && fieldsState.body && <FormErrors errors={formErrors.body} />}
</Box>
{body && (
<Box mb="24px">
<Card>
<CardHeader>
<Heading as="h3" scale="md">
{t('Preview')}
</Heading>
</CardHeader>
<CardBody p="0" px="24px">
<ReactMarkdown>{body}</ReactMarkdown>
</CardBody>
</Card>
</Box>
)}
<Choices choices={choices} onChange={handleChoiceChange} />
{formErrors.choices && fieldsState.choices && <FormErrors errors={formErrors.choices} />}
</Box>
<Box>
<Card>
<CardHeader>
<Heading as="h3" scale="md">
{t('Actions')}
</Heading>
</CardHeader>
<CardBody>
<Box mb="24px">
<SecondaryLabel>{t('Start Date')}</SecondaryLabel>
<DatePicker
name="startDate"
onChange={handleDateChange('startDate')}
selected={startDate}
placeholderText="YYYY/MM/DD"
/>
{formErrors.startDate && fieldsState.startDate && <FormErrors errors={formErrors.startDate} />}
</Box>
<Box mb="24px">
<SecondaryLabel>{t('Start Time')}</SecondaryLabel>
<TimePicker
name="startTime"
onChange={handleDateChange('startTime')}
selected={startTime}
placeholderText="00:00"
/>
{formErrors.startTime && fieldsState.startTime && <FormErrors errors={formErrors.startTime} />}
</Box>
<Box mb="24px">
<SecondaryLabel>{t('End Date')}</SecondaryLabel>
<DatePicker
name="endDate"
onChange={handleDateChange('endDate')}
selected={endDate}
placeholderText="YYYY/MM/DD"
/>
{formErrors.endDate && fieldsState.endDate && <FormErrors errors={formErrors.endDate} />}
</Box>
<Box mb="24px">
<SecondaryLabel>{t('End Time')}</SecondaryLabel>
<TimePicker
name="endTime"
onChange={handleDateChange('endTime')}
selected={endTime}
placeholderText="00:00"
/>
{formErrors.endTime && fieldsState.endTime && <FormErrors errors={formErrors.endTime} />}
</Box>
{account && (
<Flex alignItems="center" mb="8px">
<Text color="textSubtle" mr="16px">
{t('Creator')}
</Text>
<LinkExternal href={getBscScanLink(account, 'address')}>
{truncateWalletAddress(account)}
</LinkExternal>
</Flex>
)}
<Flex alignItems="center" mb="16px">
<Text color="textSubtle" mr="16px">
{t('Snapshot')}
</Text>
<LinkExternal href={getBscScanLink(snapshot, 'block')}>{snapshot}</LinkExternal>
</Flex>
{account ? (
<>
<Button
type="submit"
width="100%"
isLoading={isLoading}
endIcon={isLoading ? <AutoRenewIcon spin color="currentColor" /> : null}
disabled={!isEmpty(formErrors)}
mb="16px"
>
{t('Publish')}
</Button>
<Text color="failure" as="p" mb="4px">
{t('You need at least %count% voting power to publish a proposal.', { count: VOTE_THRESHOLD })}{' '}
</Text>
<Button scale="sm" type="button" variant="text" onClick={onPresentVoteDetailsModal} p={0}>
{t('Check voting power')}
</Button>
</>
) : (
<ConnectWalletButton width="100%" type="button" />
)}
</CardBody>
</Card>
</Box>
</Layout>
</form>
</Container>
)
}
Example #29
Source File: ManageTokens.tsx From glide-frontend with GNU General Public License v3.0 | 4 votes |
export default function ManageTokens({
setModalView,
setImportToken,
}: {
setModalView: (view: CurrencyModalView) => void
setImportToken: (token: Token) => void
}) {
const { chainId } = useActiveWeb3React()
const { t } = useTranslation()
const [searchQuery, setSearchQuery] = useState<string>('')
// manage focus on modal show
const inputRef = useRef<HTMLInputElement>()
const handleInput = useCallback((event) => {
const input = event.target.value
const checksummedInput = isAddress(input)
setSearchQuery(checksummedInput || input)
}, [])
// if they input an address, use it
const searchToken = useToken(searchQuery)
// all tokens for local lisr
const userAddedTokens: Token[] = useUserAddedTokens()
const removeToken = useRemoveUserAddedToken()
const handleRemoveAll = useCallback(() => {
if (chainId && userAddedTokens) {
userAddedTokens.map((token) => {
return removeToken(chainId, token.address)
})
}
}, [removeToken, userAddedTokens, chainId])
const tokenList = useMemo(() => {
return (
chainId &&
userAddedTokens.map((token) => (
<RowBetween key={token.address} width="100%">
<RowFixed>
<CurrencyLogo currency={token} size="20px" />
<Link external href={getBscScanLink(token.address, 'address', chainId)} color="textSubtle" ml="10px">
{token.symbol}
</Link>
</RowFixed>
<RowFixed>
<IconButton variant="text" onClick={() => removeToken(chainId, token.address)}>
<CloseIcon />
</IconButton>
<LinkExternal href={getBscScanLink(token.address, 'address', chainId)} />
</RowFixed>
</RowBetween>
))
)
}, [userAddedTokens, chainId, removeToken])
const isAddressValid = searchQuery === '' || isAddress(searchQuery)
return (
<Wrapper>
<Column style={{ width: '100%', flex: '1 1' }}>
<AutoColumn gap="14px">
<Row>
<Input
id="token-search-input"
scale="lg"
placeholder="0x0000"
value={searchQuery}
autoComplete="off"
ref={inputRef as RefObject<HTMLInputElement>}
onChange={handleInput}
isWarning={!isAddressValid}
/>
</Row>
{!isAddressValid && <Text color="failure">{t('Enter valid token address')}</Text>}
{searchToken && (
<ImportRow
token={searchToken}
showImportView={() => setModalView(CurrencyModalView.importToken)}
setImportToken={setImportToken}
style={{ height: 'fit-content' }}
/>
)}
</AutoColumn>
{tokenList}
<Footer>
<Text bold color="textSubtle">
{userAddedTokens?.length} {userAddedTokens.length === 1 ? t('Custom Token') : t('Custom Tokens')}
</Text>
{userAddedTokens.length > 0 && (
<Button variant="tertiary" onClick={handleRemoveAll}>
{t('Clear all')}
</Button>
)}
</Footer>
</Column>
</Wrapper>
)
}