@lifi/widget 4.0.0 → 4.2.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (485) hide show
  1. package/dist/esm/App.d.ts +4 -2
  2. package/dist/esm/App.d.ts.map +1 -1
  3. package/dist/esm/App.js +4 -4
  4. package/dist/esm/App.js.map +1 -1
  5. package/dist/esm/AppDefault.js +14 -0
  6. package/dist/esm/AppDefault.js.map +1 -1
  7. package/dist/esm/AppDrawer.d.ts +1 -1
  8. package/dist/esm/AppDrawer.d.ts.map +1 -1
  9. package/dist/esm/AppDrawer.js +5 -6
  10. package/dist/esm/AppDrawer.js.map +1 -1
  11. package/dist/esm/AppDrawerContext.js +2 -2
  12. package/dist/esm/AppDrawerContext.js.map +1 -1
  13. package/dist/esm/components/ActionRow/ActionRow.style.js.map +1 -1
  14. package/dist/esm/components/AmountInput/AmountInput.js +2 -1
  15. package/dist/esm/components/AmountInput/AmountInput.js.map +1 -1
  16. package/dist/esm/components/AmountInput/AmountInput.style.js.map +1 -1
  17. package/dist/esm/components/AmountInput/AmountInputEndAdornment.js +4 -2
  18. package/dist/esm/components/AmountInput/AmountInputEndAdornment.js.map +1 -1
  19. package/dist/esm/components/AmountInput/AmountInputEndAdornment.style.js +1 -1
  20. package/dist/esm/components/AmountInput/AmountInputEndAdornment.style.js.map +1 -1
  21. package/dist/esm/components/AmountInput/PriceFormHelperText.js +4 -2
  22. package/dist/esm/components/AmountInput/PriceFormHelperText.js.map +1 -1
  23. package/dist/esm/components/AmountInput/PriceFormHelperText.style.js.map +1 -1
  24. package/dist/esm/components/AmountInputCard/AmountInputCard.style.js +98 -0
  25. package/dist/esm/components/AmountInputCard/AmountInputCard.style.js.map +1 -0
  26. package/dist/esm/components/AmountInputCard/AmountInputCardPair.js +25 -0
  27. package/dist/esm/components/AmountInputCard/AmountInputCardPair.js.map +1 -0
  28. package/dist/esm/components/AmountInputCard/BalanceDisplay.js +35 -0
  29. package/dist/esm/components/AmountInputCard/BalanceDisplay.js.map +1 -0
  30. package/dist/esm/components/AmountInputCard/BalanceDisplay.style.js +11 -0
  31. package/dist/esm/components/AmountInputCard/BalanceDisplay.style.js.map +1 -0
  32. package/dist/esm/components/AmountInputCard/FiatValueToggle.js +41 -0
  33. package/dist/esm/components/AmountInputCard/FiatValueToggle.js.map +1 -0
  34. package/dist/esm/components/AmountInputCard/PercentageChips.js +80 -0
  35. package/dist/esm/components/AmountInputCard/PercentageChips.js.map +1 -0
  36. package/dist/esm/components/AmountInputCard/PercentageChips.style.js +43 -0
  37. package/dist/esm/components/AmountInputCard/PercentageChips.style.js.map +1 -0
  38. package/dist/esm/components/AmountInputCard/ReceiveAmountCard.js +137 -0
  39. package/dist/esm/components/AmountInputCard/ReceiveAmountCard.js.map +1 -0
  40. package/dist/esm/components/AmountInputCard/SendAmountCard.js +102 -0
  41. package/dist/esm/components/AmountInputCard/SendAmountCard.js.map +1 -0
  42. package/dist/esm/components/AppContainer.js.map +1 -1
  43. package/dist/esm/components/Avatar/AccountAvatar.js.map +1 -1
  44. package/dist/esm/components/Avatar/Avatar.js +12 -3
  45. package/dist/esm/components/Avatar/Avatar.js.map +1 -1
  46. package/dist/esm/components/Avatar/Avatar.style.js.map +1 -1
  47. package/dist/esm/components/Avatar/SmallAvatar.js.map +1 -1
  48. package/dist/esm/components/BaseTransactionButton/BaseTransactionButton.js +1 -0
  49. package/dist/esm/components/BaseTransactionButton/BaseTransactionButton.js.map +1 -1
  50. package/dist/esm/components/BottomSheet/BottomSheet.js +3 -3
  51. package/dist/esm/components/BottomSheet/BottomSheet.js.map +1 -1
  52. package/dist/esm/components/ButtonTertiary.js.map +1 -1
  53. package/dist/esm/components/Card/Card.js.map +1 -1
  54. package/dist/esm/components/Card/CardButton.style.js.map +1 -1
  55. package/dist/esm/components/Card/CardHeader.js.map +1 -1
  56. package/dist/esm/components/Card/CardIconButton.js.map +1 -1
  57. package/dist/esm/components/Card/CardLabel.js.map +1 -1
  58. package/dist/esm/components/Card/CardTitle.js.map +1 -1
  59. package/dist/esm/components/Card/InputCard.js.map +1 -1
  60. package/dist/esm/components/ChainSelect/ChainSelect.js.map +1 -1
  61. package/dist/esm/components/ChainSelect/ChainSelect.style.js.map +1 -1
  62. package/dist/esm/components/ChainSelect/useChainSelect.js.map +1 -1
  63. package/dist/esm/components/Chains/AllChainsAvatar.js.map +1 -1
  64. package/dist/esm/components/Chains/ChainList.js.map +1 -1
  65. package/dist/esm/components/Chains/ChainList.style.js.map +1 -1
  66. package/dist/esm/components/Chains/ChainsExpanded.style.js.map +1 -1
  67. package/dist/esm/components/Chains/VirtualizedChainList.js +2 -1
  68. package/dist/esm/components/Chains/VirtualizedChainList.js.map +1 -1
  69. package/dist/esm/components/ContextMenu.style.js.map +1 -1
  70. package/dist/esm/components/ContractComponent/NFT/NFT.style.js.map +1 -1
  71. package/dist/esm/components/Dialog/Dialog.style.js.map +1 -1
  72. package/dist/esm/components/EmptyListIndicator/EmptyListIndicator.style.js.map +1 -1
  73. package/dist/esm/components/ExecutionStatusCard/StatusIcon.js.map +1 -1
  74. package/dist/esm/components/ExecutionStatusCard/StatusIcon.style.js.map +1 -1
  75. package/dist/esm/components/ExecutionStatusCard/iconKey.js.map +1 -1
  76. package/dist/esm/components/Expansion/Expansion.style.js.map +1 -1
  77. package/dist/esm/components/Header/ActivitiesButton.style.js.map +1 -1
  78. package/dist/esm/components/Header/CloseDrawerButton.js +1 -0
  79. package/dist/esm/components/Header/CloseDrawerButton.js.map +1 -1
  80. package/dist/esm/components/Header/Header.js +7 -10
  81. package/dist/esm/components/Header/Header.js.map +1 -1
  82. package/dist/esm/components/Header/Header.style.js.map +1 -1
  83. package/dist/esm/components/Header/HeaderNavigationTabs.js +39 -0
  84. package/dist/esm/components/Header/HeaderNavigationTabs.js.map +1 -0
  85. package/dist/esm/components/Header/HeaderTabs.js +33 -0
  86. package/dist/esm/components/Header/HeaderTabs.js.map +1 -0
  87. package/dist/esm/components/Header/NavigationHeader.js +7 -5
  88. package/dist/esm/components/Header/NavigationHeader.js.map +1 -1
  89. package/dist/esm/components/Header/SettingsButton.style.js.map +1 -1
  90. package/dist/esm/components/Header/WalletMenu.style.js.map +1 -1
  91. package/dist/esm/components/IconCircle/IconCircle.style.js +1 -1
  92. package/dist/esm/components/IconCircle/IconCircle.style.js.map +1 -1
  93. package/dist/esm/components/IconTypography.js.map +1 -1
  94. package/dist/esm/components/Input.js.map +1 -1
  95. package/dist/esm/components/LimitOrderSettings/LimitOrderSettings.js +99 -0
  96. package/dist/esm/components/LimitOrderSettings/LimitOrderSettings.js.map +1 -0
  97. package/dist/esm/components/LimitOrderSettings/LimitOrderSettings.style.js +52 -0
  98. package/dist/esm/components/LimitOrderSettings/LimitOrderSettings.style.js.map +1 -0
  99. package/dist/esm/components/LimitPriceCard/LimitPriceCard.js +115 -0
  100. package/dist/esm/components/LimitPriceCard/LimitPriceCard.js.map +1 -0
  101. package/dist/esm/components/LimitPriceCard/LimitPriceCard.style.js +89 -0
  102. package/dist/esm/components/LimitPriceCard/LimitPriceCard.style.js.map +1 -0
  103. package/dist/esm/components/LimitPriceCard/LimitPricePresets.js +91 -0
  104. package/dist/esm/components/LimitPriceCard/LimitPricePresets.js.map +1 -0
  105. package/dist/esm/components/ListItem/ListItem.js.map +1 -1
  106. package/dist/esm/components/ListItem/ListItemButton.js.map +1 -1
  107. package/dist/esm/components/ListItemButton.js.map +1 -1
  108. package/dist/esm/components/ListItemText.js.map +1 -1
  109. package/dist/esm/components/Menu.js.map +1 -1
  110. package/dist/esm/components/Messages/AlertMessage.style.js.map +1 -1
  111. package/dist/esm/components/Messages/GasRefuelMessage.style.js.map +1 -1
  112. package/dist/esm/components/Messages/WarningMessages.js.map +1 -1
  113. package/dist/esm/components/PageContainer.js.map +1 -1
  114. package/dist/esm/components/PoweredBy/PoweredBy.js.map +1 -1
  115. package/dist/esm/components/PoweredBy/PoweredBy.style.js.map +1 -1
  116. package/dist/esm/components/ReverseTokensButton/ReverseTokensButton.js +1 -0
  117. package/dist/esm/components/ReverseTokensButton/ReverseTokensButton.js.map +1 -1
  118. package/dist/esm/components/ReverseTokensButton/ReverseTokensButton.style.js.map +1 -1
  119. package/dist/esm/components/RouteCard/RouteDetails.js.map +1 -1
  120. package/dist/esm/components/RouteCard/RouteDetails.style.js +2 -2
  121. package/dist/esm/components/RouteCard/RouteDetails.style.js.map +1 -1
  122. package/dist/esm/components/RouteCard/RouteProviderCard.js +118 -0
  123. package/dist/esm/components/RouteCard/RouteProviderCard.js.map +1 -0
  124. package/dist/esm/components/RouteCard/RouteToken.style.js.map +1 -1
  125. package/dist/esm/components/RouteCard/RouteTokens.js.map +1 -1
  126. package/dist/esm/components/RouteCard/getMatchingLabels.js.map +1 -1
  127. package/dist/esm/components/Routes/LimitOrderRoutes.js +34 -0
  128. package/dist/esm/components/Routes/LimitOrderRoutes.js.map +1 -0
  129. package/dist/esm/components/Routes/Routes.js +2 -2
  130. package/dist/esm/components/Routes/Routes.js.map +1 -1
  131. package/dist/esm/components/Routes/RoutesContent.js.map +1 -1
  132. package/dist/esm/components/Routes/RoutesExpanded.style.js.map +1 -1
  133. package/dist/esm/components/Search/SearchInput.style.js.map +1 -1
  134. package/dist/esm/components/Search/SearchNotFound.style.js.map +1 -1
  135. package/dist/esm/components/SelectTokenButton/SelectTokenButton.style.js.map +1 -1
  136. package/dist/esm/components/SendToWallet/SendToWalletButton.style.js.map +1 -1
  137. package/dist/esm/components/SettingsListItemButton.js.map +1 -1
  138. package/dist/esm/components/SettingsPanel/SettingsPanel.js +51 -0
  139. package/dist/esm/components/SettingsPanel/SettingsPanel.js.map +1 -0
  140. package/dist/esm/components/SettingsPanel/SettingsPanel.style.js +33 -0
  141. package/dist/esm/components/SettingsPanel/SettingsPanel.style.js.map +1 -0
  142. package/dist/esm/components/SettingsPanel/utils.js +14 -0
  143. package/dist/esm/components/SettingsPanel/utils.js.map +1 -0
  144. package/dist/esm/components/Skeleton/WidgetSkeleton.js +50 -47
  145. package/dist/esm/components/Skeleton/WidgetSkeleton.js.map +1 -1
  146. package/dist/esm/components/Skeleton/WidgetSkeleton.style.js.map +1 -1
  147. package/dist/esm/components/Step/StepActions.js.map +1 -1
  148. package/dist/esm/components/Step/StepActions.style.js.map +1 -1
  149. package/dist/esm/components/StepActions/SentToWalletRow.style.js.map +1 -1
  150. package/dist/esm/components/StepActions/StepActionRow.style.js.map +1 -1
  151. package/dist/esm/components/SwapButton/SwapButton.js +50 -0
  152. package/dist/esm/components/SwapButton/SwapButton.js.map +1 -0
  153. package/dist/esm/components/SwapButton/SwapButton.style.js +24 -0
  154. package/dist/esm/components/SwapButton/SwapButton.style.js.map +1 -0
  155. package/dist/esm/components/Switch.js.map +1 -1
  156. package/dist/esm/components/Tabs/NavigationTabs.js +3 -0
  157. package/dist/esm/components/Tabs/NavigationTabs.js.map +1 -1
  158. package/dist/esm/components/Tabs/Tabs.style.js.map +1 -1
  159. package/dist/esm/components/Timer/StepStatusTimer.style.js.map +1 -1
  160. package/dist/esm/components/Token/Token.style.js.map +1 -1
  161. package/dist/esm/components/TokenList/PinTokenButton.js.map +1 -1
  162. package/dist/esm/components/TokenList/TokenDetailsSheet.js +4 -4
  163. package/dist/esm/components/TokenList/TokenDetailsSheet.js.map +1 -1
  164. package/dist/esm/components/TokenList/TokenDetailsSheetContent.js +4 -4
  165. package/dist/esm/components/TokenList/TokenDetailsSheetContent.js.map +1 -1
  166. package/dist/esm/components/TokenList/TokenDetailsSheetContent.style.js.map +1 -1
  167. package/dist/esm/components/TokenList/TokenList.style.js.map +1 -1
  168. package/dist/esm/components/TokenList/TokenListItem.js +2 -2
  169. package/dist/esm/components/TokenList/TokenListItem.js.map +1 -1
  170. package/dist/esm/components/TokenList/VirtualizedTokenList.js.map +1 -1
  171. package/dist/esm/components/TokenList/useTokenSelect.js +3 -3
  172. package/dist/esm/components/TokenList/useTokenSelect.js.map +1 -1
  173. package/dist/esm/components/TokenPillButton/TokenPillButton.js +52 -0
  174. package/dist/esm/components/TokenPillButton/TokenPillButton.js.map +1 -0
  175. package/dist/esm/components/TokenPillButton/TokenPillButton.style.js +39 -0
  176. package/dist/esm/components/TokenPillButton/TokenPillButton.style.js.map +1 -0
  177. package/dist/esm/components/TokenRate/TokenRate.style.js.map +1 -1
  178. package/dist/esm/components/TransactionCard/ActiveTransactionCard.js.map +1 -1
  179. package/dist/esm/components/TransactionCard/ActiveTransactionCard.style.js.map +1 -1
  180. package/dist/esm/components/TransactionCard/TransactionCard.style.js.map +1 -1
  181. package/dist/esm/config/version.d.ts +1 -1
  182. package/dist/esm/config/version.js +1 -1
  183. package/dist/esm/config/version.js.map +1 -1
  184. package/dist/esm/hooks/timer/validate.js.map +1 -1
  185. package/dist/esm/hooks/useAccountsBalancesData.js.map +1 -1
  186. package/dist/esm/hooks/useAvailableChains.js +1 -1
  187. package/dist/esm/hooks/useChainSearch.js +2 -1
  188. package/dist/esm/hooks/useChainSearch.js.map +1 -1
  189. package/dist/esm/hooks/useChains.js +1 -1
  190. package/dist/esm/hooks/useExplorer.js.map +1 -1
  191. package/dist/esm/hooks/useFilteredByTokenBalances.js +1 -1
  192. package/dist/esm/hooks/useFilteredByTokenBalances.js.map +1 -1
  193. package/dist/esm/hooks/useFromTokenSufficiency.js.map +1 -1
  194. package/dist/esm/hooks/useGasSufficiency.js.map +1 -1
  195. package/dist/esm/hooks/useLanguages.js +2 -2
  196. package/dist/esm/hooks/useLanguages.js.map +1 -1
  197. package/dist/esm/hooks/useLimitMarketRate.js +24 -0
  198. package/dist/esm/hooks/useLimitMarketRate.js.map +1 -0
  199. package/dist/esm/hooks/useLinkedLimitFields.js +49 -0
  200. package/dist/esm/hooks/useLinkedLimitFields.js.map +1 -0
  201. package/dist/esm/hooks/useRouteExecution.js.map +1 -1
  202. package/dist/esm/hooks/useRouteExecutionMessage.js.map +1 -1
  203. package/dist/esm/hooks/useRouteRequiredAccountConnection.js.map +1 -1
  204. package/dist/esm/hooks/useRoutes.js +23 -6
  205. package/dist/esm/hooks/useRoutes.js.map +1 -1
  206. package/dist/esm/hooks/useSwapOnly.js +2 -4
  207. package/dist/esm/hooks/useSwapOnly.js.map +1 -1
  208. package/dist/esm/hooks/useToAddressRequirements.js +2 -2
  209. package/dist/esm/hooks/useToAddressRequirements.js.map +1 -1
  210. package/dist/esm/hooks/useToken.js.map +1 -1
  211. package/dist/esm/hooks/useTokenBalance.js.map +1 -1
  212. package/dist/esm/hooks/useTokenBalances.js.map +1 -1
  213. package/dist/esm/hooks/useTokenBalancesQueries.js.map +1 -1
  214. package/dist/esm/hooks/useTokenSearch.js +1 -1
  215. package/dist/esm/hooks/useTokenSearch.js.map +1 -1
  216. package/dist/esm/hooks/useTokens.js +17 -15
  217. package/dist/esm/hooks/useTokens.js.map +1 -1
  218. package/dist/esm/hooks/useTools.js +1 -1
  219. package/dist/esm/hooks/useTransactionDetails.js.map +1 -1
  220. package/dist/esm/hooks/useTransactionHistory.js.map +1 -1
  221. package/dist/esm/hooks/useTransactionList.js.map +1 -1
  222. package/dist/esm/hooks/useWideVariant.js +5 -2
  223. package/dist/esm/hooks/useWideVariant.js.map +1 -1
  224. package/dist/esm/i18n/en.json +25 -0
  225. package/dist/esm/index.d.ts +3 -3
  226. package/dist/esm/pages/ActivitiesPage/ActivitiesPage.js.map +1 -1
  227. package/dist/esm/pages/MainPage/LimitPageContent.js +23 -0
  228. package/dist/esm/pages/MainPage/LimitPageContent.js.map +1 -0
  229. package/dist/esm/pages/MainPage/MainPage.js +19 -22
  230. package/dist/esm/pages/MainPage/MainPage.js.map +1 -1
  231. package/dist/esm/pages/MainPage/MainPageActions.js +28 -0
  232. package/dist/esm/pages/MainPage/MainPageActions.js.map +1 -0
  233. package/dist/esm/pages/MainPage/ReviewButton.js +11 -4
  234. package/dist/esm/pages/MainPage/ReviewButton.js.map +1 -1
  235. package/dist/esm/pages/RoutePriorityPage.js +48 -0
  236. package/dist/esm/pages/RoutePriorityPage.js.map +1 -0
  237. package/dist/esm/pages/RoutesPage/RoutesPage.js.map +1 -1
  238. package/dist/esm/pages/RoutesPage/RoutesPage.style.js.map +1 -1
  239. package/dist/esm/pages/SelectEnabledToolsPage.js.map +1 -1
  240. package/dist/esm/pages/SendToWallet/BookmarkAddressSheet.js +3 -3
  241. package/dist/esm/pages/SendToWallet/BookmarkAddressSheet.js.map +1 -1
  242. package/dist/esm/pages/SendToWallet/ConfirmAddressSheet.js +3 -3
  243. package/dist/esm/pages/SendToWallet/ConfirmAddressSheet.js.map +1 -1
  244. package/dist/esm/pages/SendToWallet/SendToWalletPage.js.map +1 -1
  245. package/dist/esm/pages/SendToWallet/SendToWalletPage.style.js.map +1 -1
  246. package/dist/esm/pages/SettingsPage/BridgeAndExchangeSettings.js +2 -2
  247. package/dist/esm/pages/SettingsPage/BridgeAndExchangeSettings.js.map +1 -1
  248. package/dist/esm/pages/SettingsPage/GasPriceSettings.js +1 -1
  249. package/dist/esm/pages/SettingsPage/ResetSettingsButton.style.js.map +1 -1
  250. package/dist/esm/pages/SettingsPage/RoutePrioritySettings.js +12 -27
  251. package/dist/esm/pages/SettingsPage/RoutePrioritySettings.js.map +1 -1
  252. package/dist/esm/pages/SettingsPage/SettingsCard/SettingCard.style.js.map +1 -1
  253. package/dist/esm/pages/SettingsPage/SettingsCard/SettingCardExpandable.js +3 -3
  254. package/dist/esm/pages/SettingsPage/SettingsCard/SettingCardExpandable.js.map +1 -1
  255. package/dist/esm/pages/SettingsPage/SettingsCard/SettingsAccordian.js +3 -3
  256. package/dist/esm/pages/SettingsPage/SettingsCard/SettingsAccordian.js.map +1 -1
  257. package/dist/esm/pages/SettingsPage/SlippageSettings/SlippagePage.js +133 -0
  258. package/dist/esm/pages/SettingsPage/SlippageSettings/SlippagePage.js.map +1 -0
  259. package/dist/esm/pages/SettingsPage/SlippageSettings/SlippageSettings.js +14 -72
  260. package/dist/esm/pages/SettingsPage/SlippageSettings/SlippageSettings.js.map +1 -1
  261. package/dist/esm/pages/SettingsPage/SlippageSettings/SlippageSettings.style.js +26 -14
  262. package/dist/esm/pages/SettingsPage/SlippageSettings/SlippageSettings.style.js.map +1 -1
  263. package/dist/esm/pages/SettingsPage/ThemeSettings.js +4 -0
  264. package/dist/esm/pages/SettingsPage/ThemeSettings.js.map +1 -1
  265. package/dist/esm/pages/TransactionDetailsPage/ContactSupportButton.style.js.map +1 -1
  266. package/dist/esm/pages/TransactionDetailsPage/TransactionDetailsPage.js.map +1 -1
  267. package/dist/esm/pages/TransactionDetailsPage/TransactionDetailsSkeleton.js.map +1 -1
  268. package/dist/esm/pages/TransactionPage/ConfirmToAddressSheet.js +3 -3
  269. package/dist/esm/pages/TransactionPage/ConfirmToAddressSheet.js.map +1 -1
  270. package/dist/esm/pages/TransactionPage/ExchangeRateBottomSheet.js +16 -15
  271. package/dist/esm/pages/TransactionPage/ExchangeRateBottomSheet.js.map +1 -1
  272. package/dist/esm/pages/TransactionPage/ExchangeRateBottomSheet.style.js.map +1 -1
  273. package/dist/esm/pages/TransactionPage/RouteTracker.js.map +1 -1
  274. package/dist/esm/pages/TransactionPage/TokenValueBottomSheet.js +3 -3
  275. package/dist/esm/pages/TransactionPage/TokenValueBottomSheet.js.map +1 -1
  276. package/dist/esm/pages/TransactionPage/TokenValueBottomSheet.style.js.map +1 -1
  277. package/dist/esm/pages/TransactionPage/TransactionExecutionContent.js +27 -31
  278. package/dist/esm/pages/TransactionPage/TransactionExecutionContent.js.map +1 -1
  279. package/dist/esm/pages/TransactionPage/TransactionReview.js +4 -1
  280. package/dist/esm/pages/TransactionPage/TransactionReview.js.map +1 -1
  281. package/dist/esm/pages/TransactionPage/utils.js.map +1 -1
  282. package/dist/esm/providers/I18nProvider/I18nProvider.js +1 -1
  283. package/dist/esm/providers/I18nProvider/I18nProvider.js.map +1 -1
  284. package/dist/esm/providers/I18nProvider/enResource.d.ts +1 -1
  285. package/dist/esm/providers/I18nProvider/enResource.js +1 -1
  286. package/dist/esm/providers/I18nProvider/i18n.js.map +1 -1
  287. package/dist/esm/providers/I18nProvider/types.d.ts +2 -2
  288. package/dist/esm/providers/QueryClientProvider.js +2 -2
  289. package/dist/esm/providers/QueryClientProvider.js.map +1 -1
  290. package/dist/esm/providers/SDKClientProvider.js +3 -3
  291. package/dist/esm/providers/SDKClientProvider.js.map +1 -1
  292. package/dist/esm/providers/WidgetProvider/WidgetProvider.js +4 -5
  293. package/dist/esm/providers/WidgetProvider/WidgetProvider.js.map +1 -1
  294. package/dist/esm/stores/StoreProvider.js +3 -4
  295. package/dist/esm/stores/StoreProvider.js.map +1 -1
  296. package/dist/esm/stores/bookmarks/BookmarkStore.js +3 -3
  297. package/dist/esm/stores/bookmarks/BookmarkStore.js.map +1 -1
  298. package/dist/esm/stores/bookmarks/createBookmarkStore.js.map +1 -1
  299. package/dist/esm/stores/chains/ChainOrderStore.js +4 -4
  300. package/dist/esm/stores/chains/ChainOrderStore.js.map +1 -1
  301. package/dist/esm/stores/chains/createChainOrderStore.js.map +1 -1
  302. package/dist/esm/stores/form/FormStore.js +1 -1
  303. package/dist/esm/stores/form/FormStore.js.map +1 -1
  304. package/dist/esm/stores/form/URLSearchParamsBuilder.js +14 -3
  305. package/dist/esm/stores/form/URLSearchParamsBuilder.js.map +1 -1
  306. package/dist/esm/stores/form/createFormStore.js +6 -2
  307. package/dist/esm/stores/form/createFormStore.js.map +1 -1
  308. package/dist/esm/stores/form/getDefaultValuesFromQueryString.js +3 -0
  309. package/dist/esm/stores/form/getDefaultValuesFromQueryString.js.map +1 -1
  310. package/dist/esm/stores/form/types.d.ts +9 -1
  311. package/dist/esm/stores/form/types.d.ts.map +1 -1
  312. package/dist/esm/stores/form/types.js.map +1 -1
  313. package/dist/esm/stores/form/useClearAmountFields.js +1 -0
  314. package/dist/esm/stores/form/useClearAmountFields.js.map +1 -1
  315. package/dist/esm/stores/form/useFieldActions.js.map +1 -1
  316. package/dist/esm/stores/form/useFieldValues.js.map +1 -1
  317. package/dist/esm/stores/form/useFormRef.js.map +1 -1
  318. package/dist/esm/stores/form/useFormStore.js +2 -2
  319. package/dist/esm/stores/form/useFormStore.js.map +1 -1
  320. package/dist/esm/stores/header/useHeaderStore.js +3 -3
  321. package/dist/esm/stores/header/useHeaderStore.js.map +1 -1
  322. package/dist/esm/stores/inputMode/useInputModeStore.js.map +1 -1
  323. package/dist/esm/stores/navigationTabs/useNavigationTabLabel.js +22 -0
  324. package/dist/esm/stores/navigationTabs/useNavigationTabLabel.js.map +1 -0
  325. package/dist/esm/stores/navigationTabs/useNavigationTabsStore.js +64 -0
  326. package/dist/esm/stores/navigationTabs/useNavigationTabsStore.js.map +1 -0
  327. package/dist/esm/stores/navigationTabs/utils.js +122 -0
  328. package/dist/esm/stores/navigationTabs/utils.js.map +1 -0
  329. package/dist/esm/stores/pinnedTokens/PinnedTokensStore.js +3 -3
  330. package/dist/esm/stores/pinnedTokens/PinnedTokensStore.js.map +1 -1
  331. package/dist/esm/stores/pinnedTokens/createPinnedTokensStore.js.map +1 -1
  332. package/dist/esm/stores/routes/RouteExecutionStore.js +3 -3
  333. package/dist/esm/stores/routes/RouteExecutionStore.js.map +1 -1
  334. package/dist/esm/stores/routes/createRouteExecutionStore.js.map +1 -1
  335. package/dist/esm/stores/routes/useIntermediateRoutesStore.js.map +1 -1
  336. package/dist/esm/stores/routes/useRouteExecutionIndicator.js.map +1 -1
  337. package/dist/esm/stores/routes/utils.js.map +1 -1
  338. package/dist/esm/stores/settings/SettingsStore.js +3 -3
  339. package/dist/esm/stores/settings/SettingsStore.js.map +1 -1
  340. package/dist/esm/stores/settings/createSettingsStore.js +122 -96
  341. package/dist/esm/stores/settings/createSettingsStore.js.map +1 -1
  342. package/dist/esm/stores/settings/types.d.ts +0 -2
  343. package/dist/esm/stores/settings/types.d.ts.map +1 -1
  344. package/dist/esm/stores/settings/types.js.map +1 -1
  345. package/dist/esm/stores/settings/useSettingsActions.js.map +1 -1
  346. package/dist/esm/themes/createTheme.js.map +1 -1
  347. package/dist/esm/themes/utils.js.map +1 -1
  348. package/dist/esm/types/events.d.ts +10 -1
  349. package/dist/esm/types/events.d.ts.map +1 -1
  350. package/dist/esm/types/events.js +2 -0
  351. package/dist/esm/types/events.js.map +1 -1
  352. package/dist/esm/types/widget.d.ts +28 -2
  353. package/dist/esm/types/widget.d.ts.map +1 -1
  354. package/dist/esm/types/widget.js.map +1 -1
  355. package/dist/esm/utils/compactNumberFormatter.js.map +1 -1
  356. package/dist/esm/utils/converters.js.map +1 -1
  357. package/dist/esm/utils/deepEqual.js.map +1 -1
  358. package/dist/esm/utils/fees.js.map +1 -1
  359. package/dist/esm/utils/format.d.ts +1 -1
  360. package/dist/esm/utils/format.d.ts.map +1 -1
  361. package/dist/esm/utils/format.js +2 -2
  362. package/dist/esm/utils/format.js.map +1 -1
  363. package/dist/esm/utils/getActionMessage.js.map +1 -1
  364. package/dist/esm/utils/getErrorMessage.js.map +1 -1
  365. package/dist/esm/utils/item.js.map +1 -1
  366. package/dist/esm/utils/limitOrder.js +61 -0
  367. package/dist/esm/utils/limitOrder.js.map +1 -0
  368. package/dist/esm/utils/{variant.js → mode.js} +2 -2
  369. package/dist/esm/utils/mode.js.map +1 -0
  370. package/dist/esm/utils/navigationRoutes.d.ts +2 -0
  371. package/dist/esm/utils/navigationRoutes.d.ts.map +1 -1
  372. package/dist/esm/utils/navigationRoutes.js +6 -0
  373. package/dist/esm/utils/navigationRoutes.js.map +1 -1
  374. package/dist/esm/utils/prepareActions.js +1 -1
  375. package/dist/esm/utils/prepareActions.js.map +1 -1
  376. package/dist/esm/utils/timer.js.map +1 -1
  377. package/dist/esm/utils/token.js +1 -1
  378. package/dist/esm/utils/token.js.map +1 -1
  379. package/dist/esm/utils/tokenList.js.map +1 -1
  380. package/package.json +13 -13
  381. package/src/App.tsx +7 -7
  382. package/src/AppDefault.tsx +16 -0
  383. package/src/AppDrawer.tsx +77 -78
  384. package/src/AppDrawerContext.ts +2 -2
  385. package/src/components/AmountInput/AmountInputEndAdornment.style.ts +1 -1
  386. package/src/components/AmountInput/AmountInputEndAdornment.tsx +5 -2
  387. package/src/components/AmountInputCard/AmountInputCard.style.tsx +157 -0
  388. package/src/components/AmountInputCard/AmountInputCardPair.tsx +25 -0
  389. package/src/components/AmountInputCard/BalanceDisplay.style.tsx +9 -0
  390. package/src/components/AmountInputCard/BalanceDisplay.tsx +46 -0
  391. package/src/components/AmountInputCard/FiatValueToggle.tsx +55 -0
  392. package/src/components/AmountInputCard/PercentageChips.style.tsx +60 -0
  393. package/src/components/AmountInputCard/PercentageChips.tsx +100 -0
  394. package/src/components/AmountInputCard/ReceiveAmountCard.tsx +219 -0
  395. package/src/components/AmountInputCard/SendAmountCard.tsx +179 -0
  396. package/src/components/Avatar/Avatar.tsx +8 -3
  397. package/src/components/BaseTransactionButton/BaseTransactionButton.tsx +1 -0
  398. package/src/components/BottomSheet/BottomSheet.tsx +56 -52
  399. package/src/components/Header/CloseDrawerButton.tsx +5 -1
  400. package/src/components/Header/Header.tsx +20 -18
  401. package/src/components/Header/HeaderNavigationTabs.tsx +42 -0
  402. package/src/components/Header/HeaderTabs.tsx +48 -0
  403. package/src/components/Header/NavigationHeader.tsx +11 -8
  404. package/src/components/LimitOrderSettings/LimitOrderSettings.style.tsx +69 -0
  405. package/src/components/LimitOrderSettings/LimitOrderSettings.tsx +124 -0
  406. package/src/components/LimitPriceCard/LimitPriceCard.style.tsx +103 -0
  407. package/src/components/LimitPriceCard/LimitPriceCard.tsx +153 -0
  408. package/src/components/LimitPriceCard/LimitPricePresets.tsx +139 -0
  409. package/src/components/ReverseTokensButton/ReverseTokensButton.tsx +4 -1
  410. package/src/components/RouteCard/RouteProviderCard.tsx +113 -0
  411. package/src/components/Routes/LimitOrderRoutes.tsx +64 -0
  412. package/src/components/Routes/Routes.tsx +3 -2
  413. package/src/components/SettingsPanel/SettingsPanel.style.tsx +41 -0
  414. package/src/components/SettingsPanel/SettingsPanel.tsx +73 -0
  415. package/src/components/SettingsPanel/utils.ts +27 -0
  416. package/src/components/Skeleton/WidgetSkeleton.tsx +1 -1
  417. package/src/components/SwapButton/SwapButton.style.tsx +28 -0
  418. package/src/components/SwapButton/SwapButton.tsx +71 -0
  419. package/src/components/Tabs/NavigationTabs.tsx +3 -0
  420. package/src/components/TokenList/TokenDetailsSheet.tsx +9 -7
  421. package/src/components/TokenList/TokenDetailsSheetContent.tsx +176 -177
  422. package/src/components/TokenList/useTokenSelect.ts +2 -2
  423. package/src/components/TokenPillButton/TokenPillButton.style.tsx +50 -0
  424. package/src/components/TokenPillButton/TokenPillButton.tsx +81 -0
  425. package/src/config/version.ts +1 -1
  426. package/src/hooks/useLimitMarketRate.ts +39 -0
  427. package/src/hooks/useLinkedLimitFields.ts +74 -0
  428. package/src/hooks/useRoutes.ts +45 -4
  429. package/src/hooks/useSwapOnly.ts +2 -5
  430. package/src/hooks/useToAddressRequirements.ts +2 -2
  431. package/src/hooks/useWideVariant.ts +8 -2
  432. package/src/pages/MainPage/LimitPageContent.tsx +18 -0
  433. package/src/pages/MainPage/MainPage.tsx +43 -30
  434. package/src/pages/MainPage/MainPageActions.tsx +35 -0
  435. package/src/pages/MainPage/ReviewButton.tsx +15 -3
  436. package/src/pages/RoutePriorityPage.tsx +55 -0
  437. package/src/pages/SendToWallet/BookmarkAddressSheet.tsx +176 -185
  438. package/src/pages/SendToWallet/ConfirmAddressSheet.tsx +9 -6
  439. package/src/pages/SettingsPage/RoutePrioritySettings.tsx +14 -38
  440. package/src/pages/SettingsPage/SettingsCard/SettingCardExpandable.tsx +58 -65
  441. package/src/pages/SettingsPage/SettingsCard/SettingsAccordian.tsx +4 -4
  442. package/src/pages/SettingsPage/SlippageSettings/SlippagePage.tsx +176 -0
  443. package/src/pages/SettingsPage/SlippageSettings/SlippageSettings.style.tsx +32 -25
  444. package/src/pages/SettingsPage/SlippageSettings/SlippageSettings.tsx +14 -128
  445. package/src/pages/SettingsPage/ThemeSettings.tsx +4 -0
  446. package/src/pages/TransactionPage/ConfirmToAddressSheet.tsx +9 -6
  447. package/src/pages/TransactionPage/ExchangeRateBottomSheet.tsx +53 -58
  448. package/src/pages/TransactionPage/TokenValueBottomSheet.tsx +24 -21
  449. package/src/pages/TransactionPage/TransactionExecutionContent.tsx +8 -6
  450. package/src/providers/QueryClientProvider.tsx +2 -2
  451. package/src/providers/SDKClientProvider.tsx +3 -7
  452. package/src/providers/WidgetProvider/WidgetProvider.tsx +6 -7
  453. package/src/stores/StoreProvider.tsx +3 -10
  454. package/src/stores/bookmarks/BookmarkStore.tsx +4 -4
  455. package/src/stores/chains/ChainOrderStore.tsx +4 -4
  456. package/src/stores/form/FormStore.tsx +2 -2
  457. package/src/stores/form/URLSearchParamsBuilder.tsx +25 -3
  458. package/src/stores/form/createFormStore.ts +7 -3
  459. package/src/stores/form/getDefaultValuesFromQueryString.ts +11 -0
  460. package/src/stores/form/types.ts +14 -1
  461. package/src/stores/form/useClearAmountFields.ts +1 -0
  462. package/src/stores/form/useFormStore.ts +2 -2
  463. package/src/stores/header/useHeaderStore.tsx +3 -5
  464. package/src/stores/navigationTabs/types.ts +33 -0
  465. package/src/stores/navigationTabs/useNavigationTabLabel.ts +28 -0
  466. package/src/stores/navigationTabs/useNavigationTabsStore.tsx +113 -0
  467. package/src/stores/navigationTabs/utils.ts +196 -0
  468. package/src/stores/pinnedTokens/PinnedTokensStore.tsx +4 -4
  469. package/src/stores/routes/RouteExecutionStore.tsx +4 -4
  470. package/src/stores/settings/SettingsStore.tsx +4 -4
  471. package/src/stores/settings/createSettingsStore.ts +48 -12
  472. package/src/stores/settings/types.ts +1 -16
  473. package/src/types/events.ts +12 -0
  474. package/src/types/widget.ts +40 -1
  475. package/src/utils/format.ts +6 -2
  476. package/src/utils/limitOrder.ts +88 -0
  477. package/src/utils/navigationRoutes.ts +6 -0
  478. package/dist/esm/components/Header/SplitNavigationTabs.js +0 -33
  479. package/dist/esm/components/Header/SplitNavigationTabs.js.map +0 -1
  480. package/dist/esm/stores/settings/useSplitModeStore.js +0 -36
  481. package/dist/esm/stores/settings/useSplitModeStore.js.map +0 -1
  482. package/dist/esm/utils/variant.js.map +0 -1
  483. package/src/components/Header/SplitNavigationTabs.tsx +0 -32
  484. package/src/stores/settings/useSplitModeStore.tsx +0 -58
  485. /package/src/utils/{variant.ts → mode.ts} +0 -0
@@ -0,0 +1,100 @@
1
+ import { formatUnits } from '@lifi/sdk'
2
+ import { useAccount } from '@lifi/wallet-management'
3
+ import { type JSX, memo } from 'react'
4
+ import { useTranslation } from 'react-i18next'
5
+ import { useAvailableChains } from '../../hooks/useAvailableChains.js'
6
+ import { useGasRecommendation } from '../../hooks/useGasRecommendation.js'
7
+ import { useLinkedLimitFields } from '../../hooks/useLinkedLimitFields.js'
8
+ import { useTokenAddressBalance } from '../../hooks/useTokenAddressBalance.js'
9
+ import { useWidgetConfig } from '../../providers/WidgetProvider/WidgetProvider.js'
10
+ import type { FormTypeProps } from '../../stores/form/types.js'
11
+ import { FormKeyHelper } from '../../stores/form/types.js'
12
+ import { useFieldActions } from '../../stores/form/useFieldActions.js'
13
+ import { useFieldValues } from '../../stores/form/useFieldValues.js'
14
+ import type { DisabledUIConfig } from '../../types/widget.js'
15
+ import { Chip, ChipContainer } from './PercentageChips.style.js'
16
+
17
+ export const PercentageChips: React.NamedExoticComponent<FormTypeProps> = memo(
18
+ ({ formType }: FormTypeProps): JSX.Element | null => {
19
+ const { t } = useTranslation()
20
+ const { getChainById } = useAvailableChains()
21
+ const { setFieldValue } = useFieldActions()
22
+ const { disabledUI, mode } = useWidgetConfig()
23
+ const { setSendAmount } = useLinkedLimitFields()
24
+
25
+ const amountKey = FormKeyHelper.getAmountKey(formType)
26
+ const isDisabled = !!disabledUI?.[amountKey as keyof DisabledUIConfig]
27
+
28
+ const [chainId, tokenAddress] = useFieldValues(
29
+ FormKeyHelper.getChainKey(formType),
30
+ FormKeyHelper.getTokenKey(formType)
31
+ )
32
+
33
+ const chain = getChainById(chainId)
34
+ const { account } = useAccount({ chainType: chain?.chainType })
35
+
36
+ const { data } = useGasRecommendation(chainId)
37
+ const { token } = useTokenAddressBalance(chainId, tokenAddress)
38
+
39
+ const getMaxAmount = (): bigint => {
40
+ if (!token?.amount) {
41
+ return 0n
42
+ }
43
+ let maxAmount = token.amount
44
+ if (chain?.nativeToken.address === tokenAddress && data?.recommended) {
45
+ const recommendedAmount = BigInt(data.recommended.amount)
46
+ if (token.amount > recommendedAmount) {
47
+ maxAmount = token.amount - recommendedAmount
48
+ }
49
+ }
50
+ return maxAmount
51
+ }
52
+
53
+ // In limit mode the send amount must flow through the linked-field
54
+ // derivation so the receive amount recomputes; otherwise it is a plain
55
+ // form-field write.
56
+ const applyAmount = (value: string): void => {
57
+ if (mode === 'limit') {
58
+ setSendAmount(value)
59
+ } else {
60
+ setFieldValue(amountKey, value, { isTouched: true })
61
+ }
62
+ }
63
+
64
+ const handlePercentage = (percentage: number): void => {
65
+ const maxAmount = getMaxAmount()
66
+ if (maxAmount && token?.decimals) {
67
+ const percentageAmount = (maxAmount * BigInt(percentage)) / 100n
68
+ applyAmount(formatUnits(percentageAmount, token.decimals))
69
+ }
70
+ }
71
+
72
+ const handleMax = (): void => {
73
+ const maxAmount = getMaxAmount()
74
+ if (maxAmount && token?.decimals) {
75
+ applyAmount(formatUnits(maxAmount, token.decimals))
76
+ }
77
+ }
78
+
79
+ if (formType !== 'from' || isDisabled || !token || !account?.isConnected) {
80
+ return null
81
+ }
82
+
83
+ return (
84
+ <ChipContainer>
85
+ <Chip data-delay="0" onClick={() => handlePercentage(25)}>
86
+ 25%
87
+ </Chip>
88
+ <Chip data-delay="1" onClick={() => handlePercentage(50)}>
89
+ 50%
90
+ </Chip>
91
+ <Chip data-delay="2" onClick={() => handlePercentage(75)}>
92
+ 75%
93
+ </Chip>
94
+ <Chip data-delay="3" onClick={handleMax}>
95
+ {t('button.max')}
96
+ </Chip>
97
+ </ChipContainer>
98
+ )
99
+ }
100
+ )
@@ -0,0 +1,219 @@
1
+ import type { Route } from '@lifi/sdk'
2
+ import InfoOutlinedIcon from '@mui/icons-material/InfoOutlined'
3
+ import SwapVertIcon from '@mui/icons-material/SwapVert'
4
+ import type { CardProps } from '@mui/material'
5
+ import { Box, Skeleton, Tooltip } from '@mui/material'
6
+ import { type JSX, type ReactNode, useLayoutEffect, useRef } from 'react'
7
+ import { useTranslation } from 'react-i18next'
8
+ import { useRoutes } from '../../hooks/useRoutes.js'
9
+ import { useWidgetConfig } from '../../providers/WidgetProvider/WidgetProvider.js'
10
+ import { useFieldValues } from '../../stores/form/useFieldValues.js'
11
+ import { useInputModeStore } from '../../stores/inputMode/useInputModeStore.js'
12
+ import { formatTokenAmount, formatTokenPrice } from '../../utils/format.js'
13
+ import { getPriceImpact } from '../../utils/getPriceImpact.js'
14
+ import { fitInputText } from '../../utils/input.js'
15
+ import { CardTitle } from '../Card/CardTitle.js'
16
+ import { ProgressToNextUpdate } from '../ProgressToNextUpdate.js'
17
+ import { TokenPillButton } from '../TokenPillButton/TokenPillButton.js'
18
+ import {
19
+ AmountCard,
20
+ AmountDisplay,
21
+ amountHeight,
22
+ CardBodyRow,
23
+ CardFooterRow,
24
+ CardHeaderRow,
25
+ FooterText,
26
+ footerFontSize,
27
+ maxInputFontSize,
28
+ minInputFontSize,
29
+ ToggleButton,
30
+ } from './AmountInputCard.style.js'
31
+
32
+ const formType = 'to' as const
33
+
34
+ type ReceiveCardProps = CardProps & { mask?: boolean }
35
+
36
+ const ReceiveAmountCardLayout = ({
37
+ cardProps,
38
+ title,
39
+ headerEnd,
40
+ amount,
41
+ footerStart,
42
+ footerEnd,
43
+ }: {
44
+ cardProps: ReceiveCardProps
45
+ title: string
46
+ headerEnd?: ReactNode
47
+ amount: ReactNode
48
+ footerStart: ReactNode
49
+ footerEnd?: ReactNode
50
+ }): JSX.Element => (
51
+ <AmountCard {...cardProps} formType={formType}>
52
+ <CardHeaderRow>
53
+ <CardTitle sx={{ padding: 0 }}>{title}</CardTitle>
54
+ {headerEnd}
55
+ </CardHeaderRow>
56
+ <CardBodyRow>
57
+ {amount}
58
+ <TokenPillButton formType={formType} />
59
+ </CardBodyRow>
60
+ <CardFooterRow>
61
+ {footerStart}
62
+ {footerEnd}
63
+ </CardFooterRow>
64
+ </AmountCard>
65
+ )
66
+
67
+ const PriceImpactBadge = ({
68
+ priceImpact,
69
+ }: {
70
+ priceImpact: number | undefined
71
+ }): JSX.Element | null => {
72
+ const { t } = useTranslation()
73
+ if (priceImpact === undefined) {
74
+ return null
75
+ }
76
+ return (
77
+ <Box sx={{ display: 'flex', alignItems: 'center', gap: 0.5 }}>
78
+ <FooterText>
79
+ {t('format.percent', { value: priceImpact, usePlusSign: true })}
80
+ </FooterText>
81
+ <Tooltip title={t('tooltip.priceImpact')}>
82
+ <InfoOutlinedIcon
83
+ sx={{ fontSize: 16, color: 'text.secondary', cursor: 'help' }}
84
+ />
85
+ </Tooltip>
86
+ </Box>
87
+ )
88
+ }
89
+
90
+ const useReceivePriceImpact = (
91
+ route: Route | undefined
92
+ ): number | undefined => {
93
+ const { hiddenUI } = useWidgetConfig()
94
+ if (!route || hiddenUI?.routeCardPriceImpact) {
95
+ return undefined
96
+ }
97
+ return getPriceImpact({
98
+ fromAmount: BigInt(route.fromAmount),
99
+ toAmount: BigInt(route.toAmount),
100
+ fromToken: route.fromToken,
101
+ toToken: route.toToken,
102
+ })
103
+ }
104
+
105
+ /**
106
+ * The receive amount is a read-only quote derived from the best route, with a
107
+ * fiat/token toggle and price impact in the footer. In limit mode the amount is
108
+ * still the quote for the current limit (the limit price drives it via the
109
+ * dedicated price card); it is never edited here, and the header shows the
110
+ * refetch progress indicator with a "Buy" title.
111
+ */
112
+ export const ReceiveAmountCard: React.FC<ReceiveCardProps> = (
113
+ props
114
+ ): JSX.Element => {
115
+ const { t } = useTranslation()
116
+ const amountRef = useRef<HTMLSpanElement>(null)
117
+ const { inputMode, toggleInputMode } = useInputModeStore()
118
+ const showFiat = inputMode[formType] === 'price'
119
+ const { hiddenUI, mode } = useWidgetConfig()
120
+ const isLimit = mode === 'limit'
121
+
122
+ const [selectedRouteId] = useFieldValues('selectedRouteId')
123
+ const { routes, isFetching, dataUpdatedAt, refetchTime, refetch } =
124
+ useRoutes()
125
+ // Reflect the route the user selected in the routes list (falling back to the
126
+ // best route), so the buy amount matches the highlighted provider card.
127
+ const route = routes?.find((r) => r.id === selectedRouteId) ?? routes?.[0]
128
+ const priceImpact = useReceivePriceImpact(route)
129
+ const showPriceImpact = !hiddenUI?.routeCardPriceImpact
130
+
131
+ const receiveAmount = route?.toAmount
132
+ ? formatTokenAmount(BigInt(route.toAmount), route.toToken.decimals)
133
+ : undefined
134
+ // Only show skeletons on the initial fetch.
135
+ const showSkeleton = isFetching && !receiveAmount
136
+
137
+ const fiatValue =
138
+ receiveAmount && route?.toToken.priceUSD
139
+ ? formatTokenPrice(receiveAmount, route.toToken.priceUSD)
140
+ : 0
141
+ const canToggle = !!receiveAmount && !!route?.toToken.priceUSD
142
+
143
+ const mainDisplay = showFiat
144
+ ? t('format.currency', { value: fiatValue })
145
+ : t('format.tokenAmount', { value: receiveAmount || '0' })
146
+ const footerDisplay = showFiat
147
+ ? t('format.tokenAmount', { value: receiveAmount || '0' })
148
+ : t('format.currency', { value: fiatValue })
149
+
150
+ // biome-ignore lint/correctness/useExhaustiveDependencies: effect must run on value change
151
+ useLayoutEffect(() => {
152
+ if (amountRef.current) {
153
+ fitInputText(maxInputFontSize, minInputFontSize, amountRef.current)
154
+ }
155
+ }, [mainDisplay])
156
+
157
+ return (
158
+ <ReceiveAmountCardLayout
159
+ cardProps={props}
160
+ title={isLimit ? t('header.buy') : t('header.receive')}
161
+ headerEnd={
162
+ isLimit && (isFetching || routes?.length) ? (
163
+ <ProgressToNextUpdate
164
+ updatedAt={dataUpdatedAt || Date.now()}
165
+ timeToUpdate={refetchTime}
166
+ isLoading={isFetching}
167
+ onClick={() => refetch()}
168
+ sx={{ padding: 0 }}
169
+ />
170
+ ) : undefined
171
+ }
172
+ amount={
173
+ showSkeleton ? (
174
+ <Skeleton variant="rounded" height={amountHeight} sx={{ flex: 1 }} />
175
+ ) : (
176
+ <AmountDisplay
177
+ ref={amountRef}
178
+ sx={{ color: 'text.primary', opacity: receiveAmount ? 1 : 0.5 }}
179
+ >
180
+ {mainDisplay}
181
+ </AmountDisplay>
182
+ )
183
+ }
184
+ footerStart={
185
+ showSkeleton ? (
186
+ <Skeleton
187
+ variant="text"
188
+ width={72}
189
+ sx={{ fontSize: footerFontSize }}
190
+ />
191
+ ) : (
192
+ <ToggleButton
193
+ clickable={canToggle}
194
+ onClick={canToggle ? () => toggleInputMode(formType) : undefined}
195
+ aria-label={canToggle ? 'Toggle fiat value' : undefined}
196
+ >
197
+ <FooterText>{footerDisplay}</FooterText>
198
+ {canToggle ? (
199
+ <SwapVertIcon sx={{ fontSize: 14, color: 'text.secondary' }} />
200
+ ) : null}
201
+ </ToggleButton>
202
+ )
203
+ }
204
+ footerEnd={
205
+ showSkeleton ? (
206
+ showPriceImpact ? (
207
+ <Skeleton
208
+ variant="text"
209
+ width={56}
210
+ sx={{ fontSize: footerFontSize }}
211
+ />
212
+ ) : null
213
+ ) : (
214
+ <PriceImpactBadge priceImpact={priceImpact} />
215
+ )
216
+ }
217
+ />
218
+ )
219
+ }
@@ -0,0 +1,179 @@
1
+ import type { CardProps } from '@mui/material'
2
+ import type { ChangeEvent, JSX } from 'react'
3
+ import { useLayoutEffect, useRef, useState } from 'react'
4
+ import { useTranslation } from 'react-i18next'
5
+ import { useLinkedLimitFields } from '../../hooks/useLinkedLimitFields.js'
6
+ import { useToken } from '../../hooks/useToken.js'
7
+ import { useWidgetConfig } from '../../providers/WidgetProvider/WidgetProvider.js'
8
+ import { FormKeyHelper } from '../../stores/form/types.js'
9
+ import { useFieldActions } from '../../stores/form/useFieldActions.js'
10
+ import { useFieldValues } from '../../stores/form/useFieldValues.js'
11
+ import { useInputModeStore } from '../../stores/inputMode/useInputModeStore.js'
12
+ import {
13
+ formatInputAmount,
14
+ formatTokenPrice,
15
+ priceToTokenAmount,
16
+ usdDecimals,
17
+ } from '../../utils/format.js'
18
+ import { fitInputText } from '../../utils/input.js'
19
+ import { CardTitle } from '../Card/CardTitle.js'
20
+ import { TokenPillButton } from '../TokenPillButton/TokenPillButton.js'
21
+ import {
22
+ AmountCard,
23
+ CardBodyRow,
24
+ CardFooterRow,
25
+ CardHeaderRow,
26
+ LargeInput,
27
+ maxInputFontSize,
28
+ minInputFontSize,
29
+ } from './AmountInputCard.style.js'
30
+ import { BalanceDisplay } from './BalanceDisplay.js'
31
+ import { FiatValueToggle } from './FiatValueToggle.js'
32
+ import { PercentageChips } from './PercentageChips.js'
33
+
34
+ export const SendAmountCard: React.FC<CardProps & { mask?: boolean }> = (
35
+ props
36
+ ): JSX.Element => {
37
+ const { t } = useTranslation()
38
+ const { disabledUI, mode, modeOptions } = useWidgetConfig()
39
+ const ref = useRef<HTMLInputElement>(null)
40
+ const isEditingRef = useRef(false)
41
+ const [formattedPriceInput, setFormattedPriceInput] = useState('')
42
+
43
+ const formType = 'from' as const
44
+
45
+ const [chainId, tokenAddress, value] = useFieldValues(
46
+ FormKeyHelper.getChainKey(formType),
47
+ FormKeyHelper.getTokenKey(formType),
48
+ FormKeyHelper.getAmountKey(formType)
49
+ )
50
+
51
+ const { token } = useToken(chainId, tokenAddress)
52
+ const { setFieldValue } = useFieldActions()
53
+ const { inputMode } = useInputModeStore()
54
+ const { setSendAmount } = useLinkedLimitFields()
55
+ const currentInputMode = inputMode[formType]
56
+ const disabled = disabledUI?.fromAmount
57
+
58
+ // In limit mode the send amount drives the linked receive amount; otherwise
59
+ // it is a plain form-field write.
60
+ const applyFromAmount = (value: string): void => {
61
+ if (mode === 'limit') {
62
+ setSendAmount(value)
63
+ } else {
64
+ setFieldValue('fromAmount', value, { isDirty: true, isTouched: true })
65
+ }
66
+ }
67
+
68
+ const title =
69
+ mode === 'limit'
70
+ ? t('header.sell')
71
+ : mode === 'custom' && modeOptions?.custom?.type === 'deposit'
72
+ ? t('header.deposit')
73
+ : t('header.send')
74
+
75
+ let displayValue: string
76
+ if (isEditingRef.current) {
77
+ if (currentInputMode === 'price') {
78
+ displayValue = formattedPriceInput
79
+ } else {
80
+ displayValue = value as string
81
+ }
82
+ } else {
83
+ if (currentInputMode === 'price') {
84
+ const priceValue = formatTokenPrice(value as string, token?.priceUSD)
85
+ displayValue = formatInputAmount(
86
+ priceValue.toFixed(usdDecimals),
87
+ usdDecimals
88
+ )
89
+ } else {
90
+ displayValue = value as string
91
+ }
92
+ }
93
+
94
+ const handleChange = (
95
+ event: ChangeEvent<HTMLInputElement | HTMLTextAreaElement>
96
+ ): void => {
97
+ const { value: inputValue } = event.target
98
+ isEditingRef.current = true
99
+
100
+ if (currentInputMode === 'price') {
101
+ const cleanInputValue = inputValue.replace('$', '')
102
+ const formattedValue = formatInputAmount(
103
+ cleanInputValue,
104
+ usdDecimals,
105
+ true
106
+ )
107
+ const tokenValue = priceToTokenAmount(formattedValue, token?.priceUSD)
108
+ setFormattedPriceInput(formattedValue)
109
+ applyFromAmount(tokenValue)
110
+ } else {
111
+ const formattedValue = formatInputAmount(
112
+ inputValue,
113
+ token?.decimals,
114
+ true
115
+ )
116
+ applyFromAmount(formattedValue)
117
+ }
118
+ }
119
+
120
+ const handleBlur = (
121
+ event: ChangeEvent<HTMLInputElement | HTMLTextAreaElement>
122
+ ): void => {
123
+ const { value: inputValue } = event.target
124
+ isEditingRef.current = false
125
+
126
+ if (currentInputMode === 'price') {
127
+ const cleanInputValue = inputValue.replace('$', '')
128
+ const formattedValue = formatInputAmount(cleanInputValue, usdDecimals)
129
+ const tokenValue = priceToTokenAmount(formattedValue, token?.priceUSD)
130
+ const formattedAmount = formatInputAmount(tokenValue, token?.decimals)
131
+ applyFromAmount(formattedAmount)
132
+ } else {
133
+ const formattedValue = formatInputAmount(inputValue, token?.decimals)
134
+ applyFromAmount(formattedValue)
135
+ }
136
+ }
137
+
138
+ // biome-ignore lint/correctness/useExhaustiveDependencies: effect must run on value change
139
+ useLayoutEffect(() => {
140
+ if (ref.current) {
141
+ fitInputText(maxInputFontSize, minInputFontSize, ref.current)
142
+ }
143
+ }, [displayValue])
144
+
145
+ return (
146
+ <AmountCard {...props} formType={formType}>
147
+ <CardHeaderRow>
148
+ <CardTitle sx={{ padding: 0 }}>{title}</CardTitle>
149
+ <PercentageChips formType={formType} />
150
+ </CardHeaderRow>
151
+ <CardBodyRow>
152
+ <LargeInput
153
+ inputRef={ref}
154
+ size="small"
155
+ autoComplete="off"
156
+ placeholder={currentInputMode === 'price' ? '$0' : '0'}
157
+ inputProps={{ inputMode: 'decimal' }}
158
+ onChange={handleChange}
159
+ onBlur={handleBlur}
160
+ value={
161
+ currentInputMode === 'price'
162
+ ? displayValue
163
+ ? `$${displayValue}`
164
+ : ''
165
+ : displayValue
166
+ }
167
+ name="fromAmount"
168
+ disabled={disabled}
169
+ required
170
+ />
171
+ <TokenPillButton formType={formType} />
172
+ </CardBodyRow>
173
+ <CardFooterRow>
174
+ <FiatValueToggle formType={formType} />
175
+ <BalanceDisplay formType={formType} />
176
+ </CardFooterRow>
177
+ </AmountCard>
178
+ )
179
+ }
@@ -8,15 +8,20 @@ import { SmallAvatarSkeleton } from './SmallAvatar.js'
8
8
  export const AvatarBadgedDefault: React.FC<{
9
9
  sx?: SxProps<Theme>
10
10
  chain?: ExtendedChain
11
- }> = ({ sx, chain }) => {
11
+ avatarSize?: number
12
+ badgeSize?: number
13
+ }> = ({ sx, chain, avatarSize, badgeSize }) => {
12
14
  return (
13
15
  <Badge
14
16
  overlap="circular"
15
17
  anchorOrigin={{ vertical: 'bottom', horizontal: 'right' }}
16
- badgeContent={<ChainBadgeContent chain={chain} />}
18
+ badgeContent={<ChainBadgeContent chain={chain} size={badgeSize} />}
17
19
  sx={sx}
18
20
  >
19
- <AvatarDefault />
21
+ <AvatarDefault
22
+ badgeSize={badgeSize}
23
+ sx={avatarSize ? { width: avatarSize, height: avatarSize } : undefined}
24
+ />
20
25
  </Badge>
21
26
  )
22
27
  }
@@ -64,6 +64,7 @@ export const BaseTransactionButton: React.FC<BaseTransactionButtonProps> = ({
64
64
  loadingPosition="center"
65
65
  fullWidth
66
66
  sx={sx}
67
+ data-testid="widget-transaction-button"
67
68
  >
68
69
  {getButtonText()}
69
70
  </Button>
@@ -1,7 +1,6 @@
1
1
  import { Drawer } from '@mui/material'
2
- import type { ForwardRefExoticComponent, RefAttributes } from 'react'
2
+ import type { JSX, Ref } from 'react'
3
3
  import {
4
- forwardRef,
5
4
  startTransition,
6
5
  useCallback,
7
6
  useImperativeHandle,
@@ -12,56 +11,61 @@ import { useGetScrollableContainer } from '../../hooks/useScrollableContainer.js
12
11
  import { modalProps, slotProps } from '../Dialog/Dialog.js'
13
12
  import type { BottomSheetBase, BottomSheetProps } from './types.js'
14
13
 
15
- export const BottomSheet: ForwardRefExoticComponent<
16
- Omit<BottomSheetProps, 'ref'> & RefAttributes<BottomSheetBase>
17
- > = forwardRef<BottomSheetBase, BottomSheetProps>(
18
- ({ elementRef, children, open, onClose, keepMounted = false }, ref) => {
19
- const getContainer = useGetScrollableContainer()
20
- const openRef = useRef(open)
21
- const [drawerOpen, setDrawerOpen] = useState(open)
22
- const [isInert, setIsInert] = useState(!open)
14
+ export const BottomSheet = ({
15
+ elementRef,
16
+ children,
17
+ open,
18
+ onClose,
19
+ keepMounted = false,
20
+ ref,
21
+ }: Omit<BottomSheetProps, 'ref'> & {
22
+ ref?: Ref<BottomSheetBase>
23
+ }): JSX.Element => {
24
+ const getContainer = useGetScrollableContainer()
25
+ const openRef = useRef(open)
26
+ const [drawerOpen, setDrawerOpen] = useState(open)
27
+ const [isInert, setIsInert] = useState(!open)
23
28
 
24
- const close = useCallback(() => {
25
- // Set inert first to prevent focus issues
26
- setIsInert(true)
27
- // Push the state update to the next event loop tick
28
- // to ensure the inert is applied to before the drawer is closed
29
- startTransition(() => {
30
- setDrawerOpen(false)
31
- openRef.current = false
32
- onClose?.()
33
- })
34
- }, [onClose])
29
+ const close = useCallback(() => {
30
+ // Set inert first to prevent focus issues
31
+ setIsInert(true)
32
+ // Push the state update to the next event loop tick
33
+ // to ensure the inert is applied to before the drawer is closed
34
+ startTransition(() => {
35
+ setDrawerOpen(false)
36
+ openRef.current = false
37
+ onClose?.()
38
+ })
39
+ }, [onClose])
35
40
 
36
- useImperativeHandle(
37
- ref,
38
- () => ({
39
- isOpen: () => openRef.current,
40
- open: () => {
41
- setIsInert(false)
42
- setDrawerOpen(true)
43
- openRef.current = true
44
- },
45
- close,
46
- }),
47
- [close]
48
- )
41
+ useImperativeHandle(
42
+ ref,
43
+ () => ({
44
+ isOpen: () => openRef.current,
45
+ open: () => {
46
+ setIsInert(false)
47
+ setDrawerOpen(true)
48
+ openRef.current = true
49
+ },
50
+ close,
51
+ }),
52
+ [close]
53
+ )
49
54
 
50
- return (
51
- <Drawer
52
- container={getContainer}
53
- ref={elementRef}
54
- anchor="bottom"
55
- open={drawerOpen}
56
- onClose={close}
57
- ModalProps={modalProps}
58
- slotProps={slotProps}
59
- disableAutoFocus
60
- keepMounted={keepMounted}
61
- inert={isInert}
62
- >
63
- {children}
64
- </Drawer>
65
- )
66
- }
67
- )
55
+ return (
56
+ <Drawer
57
+ container={getContainer}
58
+ ref={elementRef}
59
+ anchor="bottom"
60
+ open={drawerOpen}
61
+ onClose={close}
62
+ ModalProps={modalProps}
63
+ slotProps={slotProps}
64
+ disableAutoFocus
65
+ keepMounted={keepMounted}
66
+ inert={isInert}
67
+ >
68
+ {children}
69
+ </Drawer>
70
+ )
71
+ }
@@ -23,7 +23,11 @@ export const CloseDrawerButton = ({
23
23
 
24
24
  return showInNavigationHeader || showInWalletHeader ? (
25
25
  <Tooltip title={t('button.close')}>
26
- <IconButton size="medium" onClick={closeDrawer}>
26
+ <IconButton
27
+ size="medium"
28
+ data-testid="widget-close-drawer-button"
29
+ onClick={closeDrawer}
30
+ >
27
31
  <CloseRounded />
28
32
  </IconButton>
29
33
  </Tooltip>