* fix: fixed info icon * fix: remove margin trading on asset select * fix: force abbreviated values larger than 1_000 to be max two decimals * fix: added AssetRate to Select Option * fix: fixed reduceMotion default setting on resetSettings * fix: disable autoLend on AXL and stATOM * Build(deps): bump @splinetool/runtime from 0.9.443 to 0.9.452 (#484) Bumps @splinetool/runtime from 0.9.443 to 0.9.452. --- updated-dependencies: - dependency-name: "@splinetool/runtime" dependency-type: direct:production update-type: version-update:semver-patch ... Signed-off-by: dependabot[bot] <support@github.com> Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com> * Build(deps-dev): bump prettier from 3.0.2 to 3.0.3 (#483) Bumps [prettier](https://github.com/prettier/prettier) from 3.0.2 to 3.0.3. - [Release notes](https://github.com/prettier/prettier/releases) - [Changelog](https://github.com/prettier/prettier/blob/main/CHANGELOG.md) - [Commits](https://github.com/prettier/prettier/compare/3.0.2...3.0.3) --- updated-dependencies: - dependency-name: prettier dependency-type: direct:development update-type: version-update:semver-patch ... Signed-off-by: dependabot[bot] <support@github.com> Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com> * Build(deps-dev): bump prettier-plugin-tailwindcss from 0.5.3 to 0.5.4 (#481) Bumps [prettier-plugin-tailwindcss](https://github.com/tailwindlabs/prettier-plugin-tailwindcss) from 0.5.3 to 0.5.4. - [Release notes](https://github.com/tailwindlabs/prettier-plugin-tailwindcss/releases) - [Changelog](https://github.com/tailwindlabs/prettier-plugin-tailwindcss/blob/main/CHANGELOG.md) - [Commits](https://github.com/tailwindlabs/prettier-plugin-tailwindcss/compare/v0.5.3...v0.5.4) --- updated-dependencies: - dependency-name: prettier-plugin-tailwindcss dependency-type: direct:development update-type: version-update:semver-patch ... Signed-off-by: dependabot[bot] <support@github.com> Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com> Co-authored-by: Linkie Link <linkielink.dev@gmail.com> * Build(deps): bump @tanstack/react-table from 8.9.3 to 8.10.0 (#482) Bumps [@tanstack/react-table](https://github.com/tanstack/table) from 8.9.3 to 8.10.0. - [Release notes](https://github.com/tanstack/table/releases) - [Commits](https://github.com/tanstack/table/compare/v8.9.3...v8.10.0) --- updated-dependencies: - dependency-name: "@tanstack/react-table" dependency-type: direct:production update-type: version-update:semver-minor ... Signed-off-by: dependabot[bot] <support@github.com> Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com> Co-authored-by: Linkie Link <linkielink.dev@gmail.com> * fix: get the info icon out of the users FACE --------- Signed-off-by: dependabot[bot] <support@github.com> Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com>
215 lines
6.5 KiB
TypeScript
215 lines
6.5 KiB
TypeScript
import BigNumber from 'bignumber.js'
|
|
import moment from 'moment'
|
|
|
|
import { ASSETS } from 'constants/assets'
|
|
import { BN_ZERO } from 'constants/math'
|
|
import { ORACLE_DENOM } from 'constants/oracle'
|
|
import { BNCoin } from 'types/classes/BNCoin'
|
|
import { byDenom } from 'utils/array'
|
|
import { getAllAssets } from 'utils/assets'
|
|
import { BN } from 'utils/helpers'
|
|
|
|
export function truncate(text = '', [h, t]: [number, number] = [6, 6]): string {
|
|
const head = text.slice(0, h)
|
|
if (t === 0) return text.length > h + t ? head + '...' : text
|
|
const tail = text.slice(-1 * t, text.length)
|
|
if (h === 0) return text.length > h + t ? '...' + tail : text
|
|
return text.length > h + t ? [head, tail].join('...') : text
|
|
}
|
|
|
|
export interface FormatOptions {
|
|
decimals?: number
|
|
minDecimals?: number
|
|
maxDecimals?: number
|
|
thousandSeparator?: boolean
|
|
prefix?: string
|
|
suffix?: string
|
|
rounded?: boolean
|
|
abbreviated?: boolean
|
|
}
|
|
|
|
export const produceCountdown = (remainingTime: number) => {
|
|
const duration = moment.duration(remainingTime, 'milliseconds')
|
|
const days = formatValue(duration.asDays(), { minDecimals: 0, maxDecimals: 0 })
|
|
|
|
duration.subtract(days, 'days')
|
|
const hours = formatValue(duration.asHours(), { minDecimals: 0, maxDecimals: 0 })
|
|
|
|
duration.subtract(hours, 'hours')
|
|
const minutes = formatValue(duration.asMinutes(), { minDecimals: 0, maxDecimals: 0 })
|
|
|
|
return `${days}d ${hours}h ${minutes}m`
|
|
}
|
|
|
|
export const formatValue = (amount: number | string, options?: FormatOptions): string => {
|
|
let numberOfZeroDecimals: number | null = null
|
|
const minDecimals = options?.minDecimals ?? 2
|
|
const maxDecimals = options?.maxDecimals ?? 2
|
|
let enforcedDecimals = maxDecimals
|
|
const thousandSeparator = options?.thousandSeparator ?? true
|
|
|
|
if (typeof amount === 'string') {
|
|
const decimals = amount.split('.')[1] ?? null
|
|
if (decimals && Number(decimals) === 0) {
|
|
numberOfZeroDecimals = decimals.length
|
|
}
|
|
}
|
|
let convertedAmount: BigNumber | string = BN(amount).dividedBy(10 ** (options?.decimals ?? 0))
|
|
|
|
const amountSuffix = options?.abbreviated
|
|
? convertedAmount.isGreaterThanOrEqualTo(1_000_000_000)
|
|
? 'B'
|
|
: convertedAmount.isGreaterThanOrEqualTo(1_000_000)
|
|
? 'M'
|
|
: convertedAmount.isGreaterThanOrEqualTo(1_000)
|
|
? 'K'
|
|
: false
|
|
: ''
|
|
|
|
if (amountSuffix === 'B') {
|
|
convertedAmount = convertedAmount.dividedBy(1_000_000_000)
|
|
}
|
|
if (amountSuffix === 'M') {
|
|
convertedAmount = convertedAmount.dividedBy(1_000_000)
|
|
}
|
|
if (amountSuffix === 'K') {
|
|
convertedAmount = convertedAmount.dividedBy(1_000)
|
|
}
|
|
|
|
if (options?.rounded) {
|
|
convertedAmount = convertedAmount.toFixed(maxDecimals)
|
|
} else {
|
|
const amountFractions = convertedAmount.toString().split('.')
|
|
|
|
if (maxDecimals > 0) {
|
|
if (typeof amountFractions[1] !== 'undefined') {
|
|
if (amountFractions[1].length >= maxDecimals) {
|
|
convertedAmount = `${amountFractions[0]}.${amountFractions[1].substr(0, maxDecimals)}`
|
|
}
|
|
if (amountFractions[1].length < minDecimals) {
|
|
convertedAmount = `${amountFractions[0]}.${amountFractions[1].padEnd(minDecimals, '0')}`
|
|
}
|
|
}
|
|
} else {
|
|
convertedAmount = amountFractions[0]
|
|
}
|
|
}
|
|
|
|
if (amountSuffix === 'B' || amountSuffix === 'M' || amountSuffix === 'K') {
|
|
enforcedDecimals = 2
|
|
}
|
|
|
|
if (thousandSeparator) {
|
|
convertedAmount = BN(convertedAmount).toNumber().toLocaleString('en', {
|
|
useGrouping: true,
|
|
minimumFractionDigits: minDecimals,
|
|
maximumFractionDigits: enforcedDecimals,
|
|
})
|
|
}
|
|
|
|
let returnValue = ''
|
|
|
|
if (numberOfZeroDecimals) {
|
|
if (numberOfZeroDecimals < enforcedDecimals) {
|
|
returnValue = Number(returnValue).toFixed(numberOfZeroDecimals)
|
|
} else {
|
|
returnValue = Number(returnValue).toFixed(enforcedDecimals)
|
|
}
|
|
}
|
|
|
|
if (options?.prefix) {
|
|
returnValue = `${options.prefix}${returnValue}`
|
|
}
|
|
|
|
returnValue = `${returnValue}${convertedAmount}`
|
|
if (amountSuffix) {
|
|
returnValue = `${returnValue}${amountSuffix}`
|
|
}
|
|
|
|
if (options?.suffix) {
|
|
returnValue = `${returnValue}${options.suffix}`
|
|
}
|
|
|
|
return returnValue
|
|
}
|
|
|
|
export function formatHealth(health: number) {
|
|
return formatValue(health, {
|
|
minDecimals: 0,
|
|
maxDecimals: 2,
|
|
})
|
|
}
|
|
|
|
export function formatLeverage(leverage: number) {
|
|
return formatValue(leverage, {
|
|
minDecimals: 2,
|
|
suffix: 'x',
|
|
})
|
|
}
|
|
|
|
export function formatPercent(percent: number | string, minDecimals?: number) {
|
|
return formatValue(+percent * 100, {
|
|
minDecimals: minDecimals ?? 0,
|
|
suffix: '%',
|
|
})
|
|
}
|
|
|
|
export function formatAmountWithSymbol(coin: Coin) {
|
|
const asset = ASSETS.find((asset) => asset.denom === coin.denom)
|
|
|
|
return formatValue(coin.amount, {
|
|
decimals: asset?.decimals,
|
|
maxDecimals: asset?.decimals,
|
|
minDecimals: 0,
|
|
suffix: ` ${asset?.symbol}`,
|
|
abbreviated: true,
|
|
rounded: true,
|
|
})
|
|
}
|
|
|
|
export function formatAmountToPrecision(amount: number | string, decimals: number) {
|
|
return Number(BN(amount).toPrecision(decimals))
|
|
}
|
|
|
|
export const convertPercentage = (percent: number) => {
|
|
let percentage = percent
|
|
if (percent >= 100) percentage = 100
|
|
if (percent !== 0 && percent < 0.01) percentage = 0.01
|
|
return Number(formatValue(percentage, { minDecimals: 0, maxDecimals: 0 }))
|
|
}
|
|
|
|
export function magnify(amount: number | string, asset: Asset | PseudoAsset) {
|
|
const _amount = BN(amount)
|
|
return _amount.isZero() ? _amount : _amount.shiftedBy(asset.decimals)
|
|
}
|
|
|
|
export function demagnify(amount: number | string | BigNumber, asset: Asset | PseudoAsset) {
|
|
const _amount = BN(amount)
|
|
return _amount.isZero() ? 0 : _amount.shiftedBy(-1 * asset.decimals).toNumber()
|
|
}
|
|
|
|
export function getCoinValue(coin: BNCoin, prices: BNCoin[]) {
|
|
const asset = getAllAssets().find(byDenom(coin.denom))
|
|
const coinPrice = prices.find(byDenom(coin.denom))
|
|
|
|
if (!coinPrice || !asset) return BN_ZERO
|
|
|
|
const decimals = asset.denom === ORACLE_DENOM ? 0 : asset.decimals * -1
|
|
return coin.amount.shiftedBy(decimals).multipliedBy(coinPrice.amount)
|
|
}
|
|
|
|
export function getCoinAmount(denom: string, value: BigNumber, prices: BNCoin[]) {
|
|
const asset = getAllAssets().find(byDenom(denom))
|
|
const coinPrice = prices.find(byDenom(denom))
|
|
|
|
if (!coinPrice || !asset) return BN_ZERO
|
|
|
|
const decimals = asset.denom === ORACLE_DENOM ? 0 : asset.decimals
|
|
return value.dividedBy(coinPrice.amount).shiftedBy(decimals).integerValue()
|
|
}
|
|
|
|
export function convertLiquidityRateToAPR(rate: number) {
|
|
const rateMulHundred = rate * 100
|
|
return rateMulHundred >= 0.01 ? rateMulHundred : 0.0
|
|
}
|