diff --git a/.i18n-codegen.json b/.i18n-codegen.json index 913ce163e46a..59bea5dd2082 100644 --- a/.i18n-codegen.json +++ b/.i18n-codegen.json @@ -73,6 +73,18 @@ "trans": "Translate", "sourceMap": "inline" } + }, + { + "input": "./packages/plugins/Flow/src/locales/en-US.json", + "output": "./packages/plugins/Flow/src/locales/i18n_generated", + "parser": "i18next", + "generator": { + "type": "i18next/react-hooks", + "hooks": "useI18N", + "namespace": "com.maskbook.flow", + "trans": "Translate", + "sourceMap": "inline" + } } ] } diff --git a/cspell.json b/cspell.json index 0a1a7dbe179b..4f059609b814 100644 --- a/cspell.json +++ b/cspell.json @@ -310,7 +310,11 @@ "noamount", "txts", "redpackets", + "blocto", + "onflow", + "unauthenticate", "mathwallet", + "walletlink", "rpcs" ], "ignoreRegExpList": ["/@servie/"], diff --git a/packages/dashboard/package.json b/packages/dashboard/package.json index bf4e971a3951..d2dd3fbcdd1e 100644 --- a/packages/dashboard/package.json +++ b/packages/dashboard/package.json @@ -17,6 +17,7 @@ "@masknet/plugin-example": "workspace:*", "@masknet/plugin-infra": "workspace:*", "@masknet/plugin-wallet": "workspace:*", + "@masknet/plugin-flow": "workspace:*", "@masknet/public-api": "workspace:*", "@masknet/shared": "workspace:*", "@masknet/shared-base": "workspace:*", diff --git a/packages/web3-shared/evm/hooks/useMnemonicWordsPuzzle.ts b/packages/dashboard/src/hooks/useMnemonicWordsPuzzle.ts similarity index 90% rename from packages/web3-shared/evm/hooks/useMnemonicWordsPuzzle.ts rename to packages/dashboard/src/hooks/useMnemonicWordsPuzzle.ts index 55ca02798a4f..0139e57e742a 100644 --- a/packages/web3-shared/evm/hooks/useMnemonicWordsPuzzle.ts +++ b/packages/dashboard/src/hooks/useMnemonicWordsPuzzle.ts @@ -1,7 +1,11 @@ +/** + * TODO: use @packages/plugin-wallet instead + */ + import { shuffle } from 'lodash-es' import { useCallback, useMemo, useState } from 'react' import { useAsyncRetry } from 'react-use' -import { useWeb3Context } from '../context' +import { WalletRPC } from '../../../mask/src/plugins/Wallet/messages' // How many fields should be filled by the user? const PUZZLE_SIZE = 5 @@ -11,12 +15,11 @@ const TOTAL_SIZE = 12 export function useMnemonicWordsPuzzle() { const [answerWords, setAnswerWords] = useState([]) - const { createMnemonicWords } = useWeb3Context() const { value: words = [], loading: wordsLoading, retry: wordsRetry, - } = useAsyncRetry(() => createMnemonicWords(), []) + } = useAsyncRetry(() => WalletRPC.createMnemonicWords(), []) //#region generate some mask indexes randomly which should be filled by the user const [seed, setSeed] = useState(0) diff --git a/packages/dashboard/src/initialization/Dashboard.tsx b/packages/dashboard/src/initialization/Dashboard.tsx index b62e3fad2001..9168f98d3ba0 100644 --- a/packages/dashboard/src/initialization/Dashboard.tsx +++ b/packages/dashboard/src/initialization/Dashboard.tsx @@ -9,52 +9,72 @@ import { NoEffectUsePortalShadowRootContext, } from '@masknet/theme' import { ErrorBoundary } from '@masknet/shared' +import { + createInjectHooksRenderer, + NetworkPluginID, + PluginsWeb3ContextProvider, + useActivatedPluginsDashboard, + useAllPluginsWeb3State, +} from '@masknet/plugin-infra' +import { Web3Provider } from '@masknet/web3-shared-evm' import i18n from 'i18next' import { I18nextProvider } from 'react-i18next' import './PluginHost' -import { createInjectHooksRenderer, useActivatedPluginsDashboard } from '@masknet/plugin-infra' import { Pages } from '../pages/routes' -import { useAppearance } from '../pages/Personas/api' -import { Web3Provider } from '@masknet/web3-shared-evm' import { Web3Context } from '../web3/context' +import { useAppearance, usePluginID } from '../pages/Personas/api' import { PersonaContext } from '../pages/Personas/hooks/usePersonaContext' +import { fixWeb3State } from '../../../mask/src/plugins/EVM/UI/Web3State' const PluginRender = createInjectHooksRenderer(useActivatedPluginsDashboard, (x) => x.GlobalInjection) export default function DashboardRoot() { - const settings = useAppearance() + const pluginID = usePluginID() + const PluginsWeb3State = useAllPluginsWeb3State() + + // TODO: + // migrate EVM plugin + fixWeb3State(PluginsWeb3State[NetworkPluginID.PLUGIN_EVM], Web3Context) + + //#region theme + const appearance = useAppearance() const mode = useSystemPreferencePalette() - const themes: Record = { + const themes: Record = { dark: MaskDarkTheme, light: MaskLightTheme, default: mode === 'dark' ? MaskDarkTheme : MaskLightTheme, } - const theme = themes[settings] + const theme = themes[appearance] + + applyMaskColorVars(document.body, appearance === 'default' ? mode : appearance) + //#endregion - applyMaskColorVars(document.body, settings === 'default' ? mode : settings) + if (!PluginsWeb3State) return null return ( - - - - - - - - - - - - - - - - - + + + + + + + + + + + + + + + + + + + ) diff --git a/packages/dashboard/src/pages/CreateMaskWallet/components/CreateMnemonic/index.tsx b/packages/dashboard/src/pages/CreateMaskWallet/components/CreateMnemonic/index.tsx index c7750bff3506..a36be6570a61 100644 --- a/packages/dashboard/src/pages/CreateMaskWallet/components/CreateMnemonic/index.tsx +++ b/packages/dashboard/src/pages/CreateMaskWallet/components/CreateMnemonic/index.tsx @@ -4,7 +4,7 @@ import { makeStyles } from '@masknet/theme' import { MaskColorVar } from '@masknet/theme' import { InfoIcon, RefreshIcon } from '@masknet/icons' import { useDashboardI18N } from '../../../../locales' -import { ProviderType, useMnemonicWordsPuzzle } from '@masknet/web3-shared-evm' +import { ProviderType } from '@masknet/web3-shared-evm' import { MnemonicReveal } from '../../../../components/Mnemonic' import { VerifyMnemonicDialog } from '../VerifyMnemonicDialog' import { useAsyncFn, useAsyncRetry } from 'react-use' @@ -13,6 +13,7 @@ import { PluginServices, Services } from '../../../../API' import { RoutePaths } from '../../../../type' import type { Search } from 'history' import { WalletMessages } from '@masknet/plugin-wallet' +import { useMnemonicWordsPuzzle } from '../../../../hooks/useMnemonicWordsPuzzle' // Private key at m/purpose'/coin_type'/account'/change export const HD_PATH_WITHOUT_INDEX_ETHEREUM = "m/44'/60'/0'/0" diff --git a/packages/dashboard/src/pages/Personas/api.ts b/packages/dashboard/src/pages/Personas/api.ts index 901dd704aed8..c4729a5640ef 100644 --- a/packages/dashboard/src/pages/Personas/api.ts +++ b/packages/dashboard/src/pages/Personas/api.ts @@ -4,10 +4,12 @@ import { Services, Messages } from '../../API' export type SocialNetwork = { networkIdentifier: string } + export const [useDefinedSocialNetworkUIs, revalidateSocialNetworkUIs] = createGlobalState( Services.SocialNetwork.getDefinedSocialNetworkUIs, () => () => {}, ) + export const [useOwnedPersonas] = createGlobalState(Services.Identity.queryOwnedPersonaInformation, (x) => Messages.events.ownPersonaChanged.on(x), ) @@ -16,6 +18,14 @@ export const [useAppearance] = createGlobalState(Services.Settings.getTheme, (x) Messages.events.appearanceSettings.on(x), ) +export const [usePluginID] = createGlobalState(Services.Settings.getPluginID, (x) => + Messages.events.pluginIDSettings.on(x), +) + +export const [useNetworkID] = createGlobalState(Services.Settings.getNetworkID, (x) => + Messages.events.networkIDSettings.on(x), +) + export const [useCurrentPersonaIdentifier] = createGlobalState(Services.Settings.getCurrentPersonaIdentifier, (x) => Messages.events.currentPersonaIdentifier.on(x), ) diff --git a/packages/dashboard/src/pages/SignUp/steps/MnemonicRevealForm.tsx b/packages/dashboard/src/pages/SignUp/steps/MnemonicRevealForm.tsx index a63952555d10..c8d239c90377 100644 --- a/packages/dashboard/src/pages/SignUp/steps/MnemonicRevealForm.tsx +++ b/packages/dashboard/src/pages/SignUp/steps/MnemonicRevealForm.tsx @@ -2,7 +2,6 @@ import { memo, useState } from 'react' import { some } from 'lodash-es' import { useNavigate } from 'react-router-dom' import { Button, Stack, Box } from '@mui/material' -import { useMnemonicWordsPuzzle } from '@masknet/web3-shared-evm' import RefreshIcon from '@mui/icons-material/Refresh' import { useCustomSnackbar } from '@masknet/theme' import { RoutePaths } from '../../../type' @@ -13,6 +12,7 @@ import { useDashboardI18N } from '../../../locales' import { DesktopMnemonicConfirm, MnemonicReveal } from '../../../components/Mnemonic' import { SignUpRoutePath } from '../routePath' import { ButtonContainer } from '../../../components/RegisterFrame/ButtonContainer' +import { useMnemonicWordsPuzzle } from '../../../hooks/useMnemonicWordsPuzzle' enum CreateWalletStep { NameAndWords = 0, diff --git a/packages/dashboard/src/pages/Wallets/components/TokenTableRow/ChangeNetworkTip.tsx b/packages/dashboard/src/pages/Wallets/components/TokenTableRow/ChangeNetworkTip.tsx index 71494619023b..8ea354041fbb 100644 --- a/packages/dashboard/src/pages/Wallets/components/TokenTableRow/ChangeNetworkTip.tsx +++ b/packages/dashboard/src/pages/Wallets/components/TokenTableRow/ChangeNetworkTip.tsx @@ -43,7 +43,9 @@ export const ChangeNetworkTip = memo(({ chainId }) => { break case ProviderType.MetaMask: case ProviderType.WalletConnect: - case ProviderType.Injected: + case ProviderType.Coin98: + case ProviderType.WalletLink: + case ProviderType.MathWallet: setConnectWalletDialog({ open: true, providerType, diff --git a/packages/dashboard/src/pages/Wallets/components/WalletStateBar/index.tsx b/packages/dashboard/src/pages/Wallets/components/WalletStateBar/index.tsx index 97e92c099ca1..c0b0fe06e9dc 100644 --- a/packages/dashboard/src/pages/Wallets/components/WalletStateBar/index.tsx +++ b/packages/dashboard/src/pages/Wallets/components/WalletStateBar/index.tsx @@ -10,7 +10,7 @@ import { useWeb3StateContext, } from '@masknet/web3-shared-evm' import { makeStyles, MaskColorVar } from '@masknet/theme' -import { FormattedAddress, LoadingAnimation, ProviderIcon, useRemoteControlledDialog } from '@masknet/shared' +import { FormattedAddress, LoadingAnimation, ImageIcon, useRemoteControlledDialog } from '@masknet/shared' import { PluginMessages } from '../../../../API' import { useRecentTransactions } from '../../hooks/useRecentTransactions' import { useDashboardI18N } from '../../../../locales' @@ -128,7 +128,8 @@ export const WalletStateBarUI: FC = ({ )} - + {/* */} + {walletName} diff --git a/packages/dashboard/src/web3/context.ts b/packages/dashboard/src/web3/context.ts index 20b8237118b6..d76e131164d2 100644 --- a/packages/dashboard/src/web3/context.ts +++ b/packages/dashboard/src/web3/context.ts @@ -13,7 +13,6 @@ import { Web3ProviderType, SendOverrides, RequestOptions, - InjectedProviderType, } from '@masknet/web3-shared-evm' import { Services, Messages, PluginServices, PluginMessages } from '../API' @@ -30,7 +29,8 @@ export const Web3Context: Web3ProviderType = { account: createSubscriptionFromAsync( async () => { const providerType = await Services.Settings.getCurrentSelectedWalletProvider() - if (providerType === ProviderType.Injected) return '' + if ([ProviderType.Coin98, ProviderType.WalletLink, ProviderType.MathWallet].includes(providerType)) + return '' return Services.Settings.getSelectedWalletAddress() }, '', @@ -66,10 +66,6 @@ export const Web3Context: Web3ProviderType = { NetworkType.Ethereum, Messages.events.currentNetworkSettings.on, ), - injectedProviderType: { - getCurrentValue: () => InjectedProviderType.Unknown, - subscribe: () => noop, - }, walletPrimary: createSubscriptionFromAsync( PluginServices.Wallet.getWalletPrimary, null, @@ -111,7 +107,6 @@ export const Web3Context: Web3ProviderType = { getAddressNamesList: PluginServices.Wallet.getAddressNames, getTransactionList: PluginServices.Wallet.getTransactionList, fetchERC20TokensFromTokenLists: Services.Ethereum.fetchERC20TokensFromTokenLists, - createMnemonicWords: PluginServices.Wallet.createMnemonicWords, } export function createExternalProvider() { diff --git a/packages/dashboard/tsconfig.json b/packages/dashboard/tsconfig.json index 21c23f335016..fdd5a8c30d59 100644 --- a/packages/dashboard/tsconfig.json +++ b/packages/dashboard/tsconfig.json @@ -11,8 +11,10 @@ { "path": "../theme/" }, { "path": "../mask/src" }, { "path": "../web3-shared/evm/" }, + { "path": "../web3-shared/flow/" }, { "path": "../icons/" }, { "path": "../plugin-infra" }, + { "path": "../plugins/Flow/" }, { "path": "../plugins/Wallet/" }, { "path": "../backup-format/" }, { "path": "../shared-base" } diff --git a/packages/injected-script/sdk/bridgedEthereum.ts b/packages/injected-script/sdk/bridgedEthereum.ts index 2ec002618d20..ea5bd35560f7 100644 --- a/packages/injected-script/sdk/bridgedEthereum.ts +++ b/packages/injected-script/sdk/bridgedEthereum.ts @@ -65,7 +65,9 @@ export interface BridgedEthereumProvider { /** Add event listener */ on(event: string, callback: (...args: any) => void): () => void /** Access primitive property on the window.ethereum object. */ - getProperty(key: 'isMetaMask' | 'isCoin98' | 'isMathWallet' | 'isWalletLink'): Promise + getProperty( + key: 'isMaskWallet' | 'isMetaMask' | 'isCoin98' | 'isMathWallet' | 'isWalletLink', + ): Promise /** MetaMask only, experimental API. */ _metamaskIsUnlocked(): Promise /** Call window.ethereum.isConnected() */ diff --git a/packages/mask/.webpack/config.ts b/packages/mask/.webpack/config.ts index ea683909e202..60acb91dbdb8 100644 --- a/packages/mask/.webpack/config.ts +++ b/packages/mask/.webpack/config.ts @@ -71,12 +71,15 @@ export function createConfiguration(rawFlags: BuildFlags): Configuration { '@masknet/shared-base': join(__dirname, '../../shared-base/src/'), '@masknet/theme': join(__dirname, '../../theme/src/'), '@masknet/icons': join(__dirname, '../../icons/index.ts'), + '@masknet/web3-kit': join(__dirname, '../../web3-kit/src/'), + '@masknet/web3-shared-evm': join(__dirname, '../../web3-shared/evm/'), + '@masknet/web3-shared-flow': join(__dirname, '../../web3-shared/flow/'), + '@masknet/web3-shared-solana': join(__dirname, '../../web3-shared/solana/'), '@masknet/plugin-infra': join(__dirname, '../../plugin-infra/src/'), '@masknet/plugin-example': join(__dirname, '../../plugins/example/src/'), + '@masknet/plugin-flow': join(__dirname, '../../plugins/Flow/src/'), '@masknet/plugin-wallet': join(__dirname, '../../plugins/Wallet/src/'), '@masknet/external-plugin-previewer': join(__dirname, '../../external-plugin-previewer/src/'), - '@masknet/web3-shared-evm': join(__dirname, '../../web3-shared/evm/'), - '@masknet/web3-shared-solana': join(__dirname, '../../web3-shared/solana/'), '@masknet/public-api': join(__dirname, '../../public-api/src/'), '@masknet/sdk': join(__dirname, '../../mask-sdk/server/'), '@masknet/backup-format': join(__dirname, '../../backup-format/src/'), diff --git a/packages/mask/package.json b/packages/mask/package.json index b0417d4655f9..a67cfe382842 100644 --- a/packages/mask/package.json +++ b/packages/mask/package.json @@ -24,6 +24,7 @@ "@masknet/plugin-example": "workspace:*", "@masknet/plugin-infra": "workspace:*", "@masknet/plugin-wallet": "workspace:*", + "@masknet/plugin-flow": "workspace:*", "@masknet/public-api": "workspace:*", "@masknet/sdk": "workspace:*", "@masknet/shared": "workspace:*", diff --git a/packages/mask/src/UIRoot.tsx b/packages/mask/src/UIRoot.tsx index ee0ec1796371..def43b632bec 100644 --- a/packages/mask/src/UIRoot.tsx +++ b/packages/mask/src/UIRoot.tsx @@ -1,14 +1,17 @@ +import { Suspense } from 'react' import { I18nextProvider } from 'react-i18next' -import { CssBaseline, StyledEngineProvider, Theme, ThemeProvider } from '@mui/material' -import { Web3Provider } from '@masknet/web3-shared-evm' import { CustomSnackbarProvider } from '@masknet/theme' -import { ErrorBoundary, ErrorBoundaryBuildInfoContext } from '@masknet/shared' +import { Web3Provider } from '@masknet/web3-shared-evm' +import { CssBaseline, StyledEngineProvider, Theme, ThemeProvider } from '@mui/material' +import { NetworkPluginID, PluginsWeb3ContextProvider, useAllPluginsWeb3State } from '@masknet/plugin-infra' +import { ErrorBoundary, ErrorBoundaryBuildInfoContext, useValueRef } from '@masknet/shared' import i18nNextInstance from './utils/i18n-next' import { Web3Context } from './web3/context' import { buildInfoMarkdown } from './extension/background-script/Jobs/PrintBuildFlags' -import { Suspense } from 'react' import { activatedSocialNetworkUI } from './social-network' import { FACEBOOK_ID } from './social-network-adaptor/facebook.com/base' +import { pluginIDSettings } from './settings/settings' +import { fixWeb3State } from './plugins/EVM/UI/Web3State' const identity = (jsx: React.ReactNode) => jsx as JSX.Element function compose(init: React.ReactNode, ...f: ((children: React.ReactNode) => JSX.Element)[]) { @@ -49,12 +52,25 @@ export interface MaskUIRootProps extends React.PropsWithChildren<{}> { } export function MaskUIRoot({ children, kind, useTheme }: MaskUIRootProps) { + const pluginID = useValueRef(pluginIDSettings) + const PluginsWeb3State = useAllPluginsWeb3State() + + // TODO: + // migrate EVM plugin + fixWeb3State(PluginsWeb3State[NetworkPluginID.PLUGIN_EVM], Web3Context) + + if (Object.values(NetworkPluginID).some((x) => !PluginsWeb3State[x])) return null + return compose( children, (jsx) => , (jsx) => , (jsx) => , - (jsx) => , + (jsx) => ( + + + + ), (jsx) => , kind === 'page' ? (jsx) => : identity, (jsx) => ( diff --git a/packages/mask/src/components/CompositionDialog/PluginEntryRender.tsx b/packages/mask/src/components/CompositionDialog/PluginEntryRender.tsx index f7d7467e3e9c..05a4fa29d7f6 100644 --- a/packages/mask/src/components/CompositionDialog/PluginEntryRender.tsx +++ b/packages/mask/src/components/CompositionDialog/PluginEntryRender.tsx @@ -1,5 +1,5 @@ import { - useActivatedPluginSNSAdaptorWithOperatingChainSupportedMet, + useActivatedPluginSNSAdaptor_withSupportOperateChain, useActivatedPluginsSNSAdaptor, Plugin, } from '@masknet/plugin-infra' @@ -11,6 +11,7 @@ import { ITO_PluginID } from '../../plugins/ITO/constants' import { ClickableChip } from '../shared/SelectRecipients/ClickableChip' import { makeStyles } from '@masknet/theme' import { useCallback, useState, useRef, forwardRef, memo, useImperativeHandle } from 'react' +import { useChainId } from '@masknet/web3-shared-evm' const useStyles = makeStyles()({ sup: { @@ -24,7 +25,8 @@ export const PluginEntryRender = memo( forwardRef((props, ref) => { const [trackPluginRef] = useSetPluginEntryRenderRef(ref) const pluginField = usePluginI18NField() - const operatingSupportedChainMapping = useActivatedPluginSNSAdaptorWithOperatingChainSupportedMet() + const chainId = useChainId() + const operatingSupportedChainMapping = useActivatedPluginSNSAdaptor_withSupportOperateChain(chainId) const result = [...useActivatedPluginsSNSAdaptor()] .sort((plugin) => { // TODO: support priority order diff --git a/packages/mask/src/components/InjectedComponents/PageInspector.tsx b/packages/mask/src/components/InjectedComponents/PageInspector.tsx index 9039186289c6..1606eb643a8e 100644 --- a/packages/mask/src/components/InjectedComponents/PageInspector.tsx +++ b/packages/mask/src/components/InjectedComponents/PageInspector.tsx @@ -6,12 +6,15 @@ import { useMatchXS, MaskMessages, useI18N } from '../../utils' import { useAutoPasteFailedDialog } from './AutoPasteFailedDialog' const PluginRender = createInjectHooksRenderer(useActivatedPluginsSNSAdaptor, (x) => x.GlobalInjection) + export interface PageInspectorProps {} + export function PageInspector(props: PageInspectorProps) { - const { showSnackbar, closeSnackbar } = useCustomSnackbar() const { t } = useI18N() + const { showSnackbar, closeSnackbar } = useCustomSnackbar() const [autoPasteFailed, JSX] = useAutoPasteFailedDialog() const xsMatched = useMatchXS() + useEffect( () => MaskMessages.events.autoPasteFailed.on((data) => { diff --git a/packages/mask/src/components/InjectedComponents/ToolboxUnstyled.tsx b/packages/mask/src/components/InjectedComponents/ToolboxUnstyled.tsx index 7389dc4562a5..4ffa82395dc7 100644 --- a/packages/mask/src/components/InjectedComponents/ToolboxUnstyled.tsx +++ b/packages/mask/src/components/InjectedComponents/ToolboxUnstyled.tsx @@ -12,18 +12,18 @@ import { ListItemText as MuiListItemText, Box, } from '@mui/material' +import { useWallet, TransactionStatusType } from '@masknet/web3-shared-evm' import { + useActivatedPluginSNSAdaptor_withSupportOperateChain, + useActivatedPluginsSNSAdaptor, + useNetworkDescriptor, + useProviderDescriptor, useAccount, + useChainId, useChainColor, - useChainDetailed, useChainIdValid, - useWallet, - formatEthereumAddress, - TransactionStatusType, -} from '@masknet/web3-shared-evm' -import { - useActivatedPluginSNSAdaptorWithOperatingChainSupportedMet, - useActivatedPluginsSNSAdaptor, + useChainDetailed, + useWeb3State, } from '@masknet/plugin-infra' import { ToolIconURLs } from '../../resources/tool-icon' import { Image } from '../shared/Image' @@ -32,7 +32,7 @@ import { MaskMessages } from '../../utils/messages' import { PLUGIN_ID as TransakPluginID } from '../../plugins/Transak/constants' import { PLUGIN_IDENTIFIER as TraderPluginID } from '../../plugins/Trader/constants' import { useControlledDialog } from '../../utils/hooks/useControlledDialog' -import { useRemoteControlledDialog } from '@masknet/shared' +import { useRemoteControlledDialog, WalletIcon } from '@masknet/shared' import { PluginTransakMessages } from '../../plugins/Transak/messages' import { PluginTraderMessages } from '../../plugins/Trader/messages' import { WalletMessages } from '../../plugins/Wallet/messages' @@ -44,7 +44,6 @@ import { safeUnreachable } from '@dimensiondev/kit' import { usePluginI18NField } from '../../plugin-infra/I18NFieldRender' import { useRecentTransactions } from '../../plugins/Wallet/hooks/useRecentTransactions' import GuideStep from '../GuideStep' -import { WalletIcon } from '../shared/WalletIcon' import { MaskIcon, MaskSharpIconOfSize, WalletSharp } from '../../resources/MaskIcon' import { makeStyles } from '@masknet/theme' import classNames from 'classnames' @@ -117,6 +116,9 @@ export function ToolboxHintUnstyled(props: ToolboxHintProps) { shouldDisplayChainIndicator, } = useToolbox() + const networkDescriptor = useNetworkDescriptor() + const providerDescriptor = useProviderDescriptor() + return ( <> @@ -136,7 +138,15 @@ export function ToolboxHintUnstyled(props: ToolboxHintProps) { - {isWalletValid ? : } + {isWalletValid ? ( + + ) : ( + + )} {mini ? null : ( @@ -312,7 +324,8 @@ function useToolbox() { const ClaimDialogJSX = isClaimAllDialogOpen ? ( ) : null - const shouldDisplayChainIndicator = account && chainIdValid && chainDetailed?.network !== 'mainnet' + const shouldDisplayChainIndicator = + account && chainIdValid && chainDetailed?.network && chainDetailed.network !== 'mainnet' return { openWallet, isWalletValid, diff --git a/packages/mask/src/components/shared/MaskApplicationBox.tsx b/packages/mask/src/components/shared/ApplicationBoard.tsx similarity index 98% rename from packages/mask/src/components/shared/MaskApplicationBox.tsx rename to packages/mask/src/components/shared/ApplicationBoard.tsx index 00785552f2b3..d716a119415b 100644 --- a/packages/mask/src/components/shared/MaskApplicationBox.tsx +++ b/packages/mask/src/components/shared/ApplicationBoard.tsx @@ -1,7 +1,9 @@ -import { Typography } from '@mui/material' import { useCallback, useState } from 'react' -import { makeStyles } from '@masknet/theme' -import { getMaskColor } from '@masknet/theme' +import classNames from 'classnames' +import { Typography } from '@mui/material' +import { makeStyles, getMaskColor } from '@masknet/theme' +import { ChainId, useChainId, useAccount, useWallet } from '@masknet/web3-shared-evm' +import { useRemoteControlledDialog } from '@masknet/shared' import { MaskMessages } from '../../utils/messages' import { useControlledDialog } from '../../utils/hooks/useControlledDialog' import { RedPacketPluginID } from '../../plugins/RedPacket/constants' @@ -12,9 +14,6 @@ import { PluginTraderMessages } from '../../plugins/Trader/messages' import { ClaimAllDialog } from '../../plugins/ITO/SNSAdaptor/ClaimAllDialog' import { EntrySecondLevelDialog } from './EntrySecondLevelDialog' import { NetworkTab } from './NetworkTab' -import { ChainId, useChainId, useAccount, useWallet } from '@masknet/web3-shared-evm' -import { useRemoteControlledDialog } from '@masknet/shared' -import classNames from 'classnames' const useStyles = makeStyles()((theme) => ({ abstractTabWrapper: { @@ -100,7 +99,7 @@ interface MaskApplicationBoxProps { secondEntryChainTabs?: ChainId[] } -export function MaskApplicationBox({ secondEntries, secondEntryChainTabs }: MaskApplicationBoxProps) { +export function ApplicationBoard({ secondEntries, secondEntryChainTabs }: MaskApplicationBoxProps) { const { classes } = useStyles() const currentChainId = useChainId() const account = useAccount() @@ -213,7 +212,7 @@ export function MaskApplicationBox({ secondEntries, secondEntryChainTabs }: Mask ), createEntry('Swap', new URL('./assets/swap.png', import.meta.url).toString(), openSwapDialog), createEntry( - 'Fiat on/off ramp', + 'Fiat on-ramp', new URL('./assets/fiat_ramp.png', import.meta.url).toString(), () => setBuyDialog({ open: true, address: account }), undefined, diff --git a/packages/mask/src/components/shared/EntrySecondLevelDialog.tsx b/packages/mask/src/components/shared/EntrySecondLevelDialog.tsx index 35b46b2665c9..3eaa28361d04 100644 --- a/packages/mask/src/components/shared/EntrySecondLevelDialog.tsx +++ b/packages/mask/src/components/shared/EntrySecondLevelDialog.tsx @@ -2,7 +2,7 @@ import { DialogContent } from '@mui/material' import { makeStyles } from '@masknet/theme' import { InjectedDialog } from './InjectedDialog' import { WalletStatusBox } from './WalletStatusBox' -import { MaskApplicationBox, MaskAppEntry } from './MaskApplicationBox' +import { ApplicationBoard, MaskAppEntry } from './ApplicationBoard' import type { ChainId } from '@masknet/web3-shared-evm' const useStyles = makeStyles()((theme) => ({ @@ -46,7 +46,7 @@ export function EntrySecondLevelDialog(props: EntrySecondLevelDialogProps) { - + ) diff --git a/packages/mask/src/components/shared/WalletIcon.tsx b/packages/mask/src/components/shared/WalletIcon.tsx deleted file mode 100644 index 386820d3dac6..000000000000 --- a/packages/mask/src/components/shared/WalletIcon.tsx +++ /dev/null @@ -1,65 +0,0 @@ -import classNames from 'classnames' -import { makeStyles } from '@masknet/theme' -import { NetworkIcon, ProviderIcon, useValueRef, useStylesExtends } from '@masknet/shared' -import { useChainId, getNetworkTypeFromChainId } from '@masknet/web3-shared-evm' -import { currentInjectedProviderSettings, currentProviderSettings } from '../../plugins/Wallet/settings' - -interface StyleProps { - size: number -} - -const useStyles = makeStyles()((theme, props) => ({ - root: { - position: 'relative', - display: 'flex', - height: props.size, - width: props.size, - }, - mainIcon: { - width: '100%', - height: '100%', - }, - badgeIcon: { - position: 'absolute', - right: -2, - bottom: -2, - }, - providerIcon: {}, - networkIcon: { - borderRadius: '50%', - }, -})) - -interface WalletIconProps extends withClasses<'networkIcon' | 'providerIcon'> { - size?: number - badgeSize?: number -} - -export const WalletIcon = (props: WalletIconProps) => { - const { size = 24, badgeSize = 14 } = props - const chainId = useChainId() - const classes = useStylesExtends(useStyles({ size: badgeSize > size ? badgeSize : size }), props) - const selectedNetwork = getNetworkTypeFromChainId(chainId) - const selectedWalletProvider = useValueRef(currentProviderSettings) - const selectedWalletInjectedProvider = useValueRef(currentInjectedProviderSettings) - - return ( -
- size ? classes.badgeIcon : classes.mainIcon, classes.networkIcon), - }} - size={size} - networkType={selectedNetwork} - /> - size ? classes.mainIcon : classes.badgeIcon, classes.providerIcon), - }} - size={badgeSize} - providerType={selectedWalletProvider} - injectedProviderType={selectedWalletInjectedProvider} - /> -
- ) -} diff --git a/packages/mask/src/components/shared/WalletStatusBox.tsx b/packages/mask/src/components/shared/WalletStatusBox.tsx index ae90f1666532..069a93f4378b 100644 --- a/packages/mask/src/components/shared/WalletStatusBox.tsx +++ b/packages/mask/src/components/shared/WalletStatusBox.tsx @@ -2,22 +2,21 @@ import { useCallback } from 'react' import { useCopyToClipboard } from 'react-use' import { Copy, ExternalLink } from 'react-feather' import classNames from 'classnames' +import { ProviderType } from '@masknet/web3-shared-evm' import { Button, Link, Typography } from '@mui/material' import { makeStyles, getMaskColor } from '@masknet/theme' import { - ProviderType, - resolveInjectedProviderName, - resolveAddressLinkOnExplorer, - useWallet, + useAccount, + useWeb3State, useChainId, -} from '@masknet/web3-shared-evm' -import { FormattedAddress, useRemoteControlledDialog, useValueRef, useSnackbarCallback } from '@masknet/shared' + useNetworkDescriptor, + useProviderDescriptor, + useProviderType, +} from '@masknet/plugin-infra' +import { FormattedAddress, useRemoteControlledDialog, useSnackbarCallback, WalletIcon } from '@masknet/shared' import { WalletMessages } from '../../plugins/Wallet/messages' -import { useInjectedProviderType } from '../../plugins/EVM/hooks' -import { currentProviderSettings } from '../../plugins/Wallet/settings' import { useI18N } from '../../utils' import Services from '../../extension/service' -import { WalletIcon } from './WalletIcon' const useStyles = makeStyles()((theme) => ({ content: { @@ -64,17 +63,8 @@ const useStyles = makeStyles()((theme) => ({ marginRight: theme.spacing(1), color: '#1C68F3', }, - networkIcon: { - backgroundColor: '#F6F8F8 !important', - border: '1px solid #ffffff', - borderRadius: '50%', - position: 'absolute', - right: -6, - bottom: -4, - }, - providerIcon: { - backgroundColor: 'none !important', - }, + networkIcon: {}, + providerIcon: {}, connectButtonWrapper: { display: 'flex', justifyContent: 'center', @@ -88,17 +78,19 @@ export function WalletStatusBox() { const { classes } = useStyles() const chainId = useChainId() - const selectedWallet = useWallet() - const { setDialog: setRenameDialog } = useRemoteControlledDialog(WalletMessages.events.walletRenameDialogUpdated) - const selectedProviderType = useValueRef(currentProviderSettings) - const injectedProviderType = useInjectedProviderType() + const account = useAccount() + + const providerType = useProviderType() + const providerDescriptor = useProviderDescriptor() + const networkDescriptor = useNetworkDescriptor() + const { Utils } = useWeb3State() ?? {} //#region copy addr to clipboard const [, copyToClipboard] = useCopyToClipboard() const onCopy = useSnackbarCallback( async (ev: React.MouseEvent) => { ev.stopPropagation() - copyToClipboard(selectedWallet?.address ?? '') + copyToClipboard(account) }, [], undefined, @@ -121,22 +113,24 @@ export function WalletStatusBox() { //#endregion const onDisconnect = useCallback(async () => { - if (selectedProviderType !== ProviderType.WalletConnect) return + if (providerType !== ProviderType.WalletConnect) return setWalletConnectDialog({ open: true, uri: await Services.Ethereum.createConnectionURI(), }) - }, [selectedProviderType, setWalletConnectDialog]) + }, [providerType, setWalletConnectDialog]) const onChange = useCallback(() => { openSelectProviderDialog() }, [openSelectProviderDialog]) - return selectedWallet ? ( + return account ? (
- - {selectedProviderType === ProviderType.Injected - ? resolveInjectedProviderName(injectedProviderType) - : selectedWallet.name} - - { - setRenameDialog({ - open: true, - wallet: selectedWallet, - }) - }} - /> + {providerDescriptor?.name}
- + @@ -183,7 +163,7 @@ export function WalletStatusBox() {
- {selectedProviderType === ProviderType.WalletConnect ? ( + {providerType === ProviderType.WalletConnect ? (