From 56cfa6fa395220840b22ff102d6277532eff1de5 Mon Sep 17 00:00:00 2001 From: shawnbusuttil Date: Tue, 13 Feb 2024 17:31:35 +0000 Subject: [PATCH 01/10] feat: use new register screen for create wallet flow --- .../wallet-setup/components/WalletSetup.tsx | 2 +- .../components/WalletSetupWizard.tsx | 197 +----------------- .../WalletSetupNamePasswordStep.tsx | 4 +- .../WalletSetup/WalletSetupStepLayout.tsx | 1 - .../ui/components/WalletSetup/wallet-steps.ts | 20 +- 5 files changed, 14 insertions(+), 210 deletions(-) diff --git a/apps/browser-extension-wallet/src/views/browser-view/features/wallet-setup/components/WalletSetup.tsx b/apps/browser-extension-wallet/src/views/browser-view/features/wallet-setup/components/WalletSetup.tsx index d83107573..469a3e5e2 100644 --- a/apps/browser-extension-wallet/src/views/browser-view/features/wallet-setup/components/WalletSetup.tsx +++ b/apps/browser-extension-wallet/src/views/browser-view/features/wallet-setup/components/WalletSetup.tsx @@ -31,7 +31,7 @@ export interface WalletSetupProps { initialStep?: WalletSetupSteps; } -export const WalletSetup = ({ initialStep = WalletSetupSteps.Legal }: WalletSetupProps): React.ReactElement => { +export const WalletSetup = ({ initialStep = WalletSetupSteps.Register }: WalletSetupProps): React.ReactElement => { const history = useHistory(); const { path } = useRouteMatch(); const [isConfirmRestoreOpen, setIsConfirmRestoreOpen] = useState(false); diff --git a/apps/browser-extension-wallet/src/views/browser-view/features/wallet-setup/components/WalletSetupWizard.tsx b/apps/browser-extension-wallet/src/views/browser-view/features/wallet-setup/components/WalletSetupWizard.tsx index eec47d192..223ae91f1 100644 --- a/apps/browser-extension-wallet/src/views/browser-view/features/wallet-setup/components/WalletSetupWizard.tsx +++ b/apps/browser-extension-wallet/src/views/browser-view/features/wallet-setup/components/WalletSetupWizard.tsx @@ -5,15 +5,10 @@ import { wordlists } from 'bip39'; import { useLocalStorage, useTimeSpentOnPage, useWalletManager } from '@hooks'; import { MnemonicStage, - WalletSetupAnalyticsStep, WalletSetupCreationStep, WalletSetupFinalStep, - WalletSetupLegalStep, - WalletSetupMnemonicIntroStep, WalletSetupNamePasswordStep, - WalletSetupPasswordStep, WalletSetupRecoveryPhraseLengthStep, - WalletSetupRegisterStep, WalletSetupSteps, walletSetupWizard } from '@lace/core'; @@ -23,37 +18,19 @@ import { WarningModal } from '@src/views/browser-view/components/WarningModal'; import { EnhancedAnalyticsOptInStatus, PostHogAction, - postHogOnboardingActions, - UserTrackingType + postHogOnboardingActions } from '@providers/AnalyticsProvider/analyticsTracker'; import { config } from '@src/config'; import { PinExtension } from './PinExtension'; import { Fallback } from './Fallback'; -import { passwordTranslationMap } from '../constants'; import { deleteFromLocalStorage, getValueFromLocalStorage } from '@src/utils/local-storage'; import { ILocalStorage } from '@src/types'; import { useAnalyticsContext } from '@providers'; import { ENHANCED_ANALYTICS_OPT_IN_STATUS_LS_KEY } from '@providers/AnalyticsProvider/config'; import * as process from 'process'; import { SendOnboardingAnalyticsEvent, SetupType } from '../types'; -import { useExperimentsContext } from '@providers/ExperimentsProvider'; -import { CombinedSetupNamePasswordVariants, ExperimentName } from '@providers/ExperimentsProvider/types'; -import { isScriptAddress } from '@cardano-sdk/wallet'; -import { filter, firstValueFrom } from 'rxjs'; -import { useWalletStore } from '@src/stores'; - -const isCombinedPasswordNameStepEnabled = process.env.USE_COMBINED_PASSWORD_NAME_STEP_COMPONENT === 'true'; -const walletSetupWizardForABTest = { - ...walletSetupWizard, - [WalletSetupSteps.PreMnemonic]: { ...walletSetupWizard['pre-mnemonic'], prev: WalletSetupSteps.Register }, - [WalletSetupSteps.RecoveryPhraseLength]: { - ...walletSetupWizard['recovery-phrase-length'], - prev: WalletSetupSteps.Register - }, - [WalletSetupSteps.Mnemonic]: { ...walletSetupWizard.mnemonic, prev: WalletSetupSteps.Register } -}; const WalletSetupModeStep = React.lazy(() => import('@lace/core').then((module) => ({ default: module.WalletSetupModeStep })) @@ -88,7 +65,7 @@ export const WalletSetupWizard = ({ onCancel, setupType, sendAnalytics, - initialStep = WalletSetupSteps.Legal + initialStep = WalletSetupSteps.Register }: WalletSetupWizardProps): React.ReactElement => { const [currentStep, setCurrentStep] = useState( setupType === SetupType.FORGOT_PASSWORD ? WalletSetupSteps.Password : initialStep @@ -96,14 +73,12 @@ export const WalletSetupWizard = ({ const [walletName, setWalletName] = useState(getValueFromLocalStorage('wallet')?.name); const [password, setPassword] = useState(''); const [walletInstance, setWalletInstance] = useState(); - const [isAnalyticsAccepted, setIsAnalyticsAccepted] = useState(false); + const [isAnalyticsAccepted] = useState(false); const [mnemonicLength, setMnemonicLength] = useState(DEFAULT_MNEMONIC_LENGTH); const [mnemonic, setMnemonic] = useState([]); const [walletIsCreating, setWalletIsCreating] = useState(false); const [resetMnemonicStage, setResetMnemonicStage] = useState(''); const [isResetMnemonicModalOpen, setIsResetMnemonicModalOpen] = useState(false); - const { getExperimentVariant } = useExperimentsContext(); - const [shouldDisplayTestVariantForExperiment, setShouldDisplayTestVariantForExperiment] = useState(); const { createWallet } = useWalletManager(); const { setStayOnAllDonePage } = useWalletStore(); @@ -126,24 +101,6 @@ export const WalletSetupWizard = ({ ); }, [mnemonicLength, setupType]); - const walletSetupLegalStepTranslations = { - title: t('core.walletSetupLegalStep.title'), - toolTipText: t('core.walletSetupLegalStep.toolTipText') - }; - - const walletSetupAnalyticsStepTranslations = { - back: t('core.walletSetupAnalyticsStep.back'), - agree: t('core.walletSetupAnalyticsStep.agree'), - title: t('core.walletSetupAnalyticsStep.title'), - description: t('core.walletSetupAnalyticsStep.description'), - optionsTitle: t('core.walletSetupAnalyticsStep.optionsTitle'), - privacyPolicy: t('core.walletSetupAnalyticsStep.privacyPolicy'), - allowOptout: t('core.walletSetupAnalyticsStep.allowOptout'), - collectPrivateKeys: t('core.walletSetupAnalyticsStep.collectPrivateKeys'), - collectIp: t('core.walletSetupAnalyticsStep.collectIp'), - personalData: t('core.walletSetupAnalyticsStep.personalData') - }; - const walletSetupMnemonicStepTranslations = { writePassphrase: t('core.walletSetupMnemonicStep.writePassphrase'), body: t('core.walletSetupMnemonicStep.body'), @@ -179,47 +136,12 @@ export const WalletSetupWizard = ({ followDiscord: t('core.walletSetupFinalStep.followDiscord') }; - const walletSetupMnemonicIntroStepTranslations = { - title: t('core.walletSetupMnemonicIntroStep.title'), - description: t('core.walletSetupMnemonicIntroStep.description'), - linkText: t('core.walletSetupMnemonicIntroStep.link') - }; - - const walletSetupRegisterStepTranslations = { - title: t('core.walletSetupRegisterStep.title'), - description: t('core.walletSetupRegisterStep.description'), - walletName: t('core.walletSetupRegisterStep.walletName'), - nameRequired: t('core.walletSetupRegisterStep.nameRequired'), - nameMaxLength: t('core.walletSetupRegisterStep.nameMaxLength') - }; - - const walletSetupPasswordStepTranslations = { - title: t('core.walletSetupRegisterStep.titlePassword'), - description: t('core.walletSetupRegisterStep.passwordDescription'), - password: t('core.walletSetupRegisterStep.password'), - confirmPassword: t('core.walletSetupRegisterStep.confirmPassword'), - noMatchPassword: t('core.walletSetupRegisterStep.noMatchPassword'), - validationMessage: t('core.walletSetupRegisterStep.validationMessage') - }; - const walletSetupRecoveryPhraseLengthStepTranslations = { title: t('core.walletSetupRecoveryPhraseLengthStep.title'), description: t('core.walletSetupRecoveryPhraseLengthStep.description'), wordPassphrase: t('core.walletSetupRecoveryPhraseLengthStep.wordPassphrase') }; - const passwordFeedbackTranslation = (translationKeys: string[]) => { - const translations = []; - - for (const key of translationKeys) { - if (passwordTranslationMap[key]) { - translations.push(t(passwordTranslationMap[key])); - } - } - - return translations; - }; - const moveForward = useCallback(() => { const nextStep = walletSetupWizard[currentStep].next; if (nextStep) { @@ -228,9 +150,7 @@ export const WalletSetupWizard = ({ }, [currentStep, setCurrentStep]); const moveBack = () => { - const prevStep = isCombinedPasswordNameStepEnabled - ? walletSetupWizardForABTest[currentStep].prev - : walletSetupWizard[currentStep].prev; + const prevStep = walletSetupWizard[currentStep].prev; if (prevStep) { setCurrentStep(prevStep); @@ -248,24 +168,6 @@ export const WalletSetupWizard = ({ EnhancedAnalyticsOptInStatus.OptedOut ); - const handleAnalyticsChoice = async (isAccepted: boolean) => { - setIsAnalyticsAccepted(isAccepted); - await analytics.setOptedInForEnhancedAnalytics( - isAccepted ? EnhancedAnalyticsOptInStatus.OptedIn : EnhancedAnalyticsOptInStatus.OptedOut - ); - - const postHogAnalyticsAgreeAction = postHogOnboardingActions[setupType]?.ANALYTICS_AGREE_CLICK; - const postHogAnalyticcSkipAction = postHogOnboardingActions[setupType]?.ANALYTICS_SKIP_CLICK; - - const postHogAction = isAccepted ? postHogAnalyticsAgreeAction : postHogAnalyticcSkipAction; - const postHogProperties = { - // eslint-disable-next-line camelcase - $set: { user_tracking_type: isAccepted ? UserTrackingType.Enhanced : UserTrackingType.Basic } - }; - await sendAnalytics(postHogAction, postHogProperties); - moveForward(); - }; - const goToMyWallet = useCallback( async (cardanoWallet: Wallet.CardanoWallet = walletInstance) => { setStayOnAllDonePage(false); @@ -332,7 +234,7 @@ export const WalletSetupWizard = ({ const createFlowPasswordNextStep = () => { setupType === SetupType.CREATE - ? skipTo(WalletSetupSteps.PreMnemonic) + ? skipTo(WalletSetupSteps.Mnemonic) : useDifferentMnemonicLengths ? skipTo(WalletSetupSteps.RecoveryPhraseLength) : skipTo(WalletSetupSteps.Mnemonic); @@ -345,18 +247,6 @@ export const WalletSetupWizard = ({ createFlowPasswordNextStep(); }; - const handlePasswordStepNextButtonClick = (result: { password: string }) => { - sendAnalytics(postHogOnboardingActions[setupType]?.WALLET_PASSWORD_NEXT_CLICK); - setPassword(result.password); - createFlowPasswordNextStep(); - }; - - const handleRegisterStepNextButtonClick = (result: { walletName: string }) => { - sendAnalytics(postHogOnboardingActions[setupType]?.WALLET_NAME_NEXT_CLICK); - setWalletName(result.walletName); - moveForward(); - }; - useEffect(() => { if (password && currentStep === WalletSetupSteps.Create && !walletIsCreating) { setWalletIsCreating(true); @@ -404,7 +294,7 @@ export const WalletSetupWizard = ({ mnemonic={mnemonic} onReset={(resetStage) => { setResetMnemonicStage(resetStage); - setIsResetMnemonicModalOpen(true); + resetStage === 'input' ? setIsResetMnemonicModalOpen(true) : skipTo(WalletSetupSteps.Register); }} onNext={moveForward} onStepNext={(stage: MnemonicStage, step: number) => { @@ -434,54 +324,8 @@ export const WalletSetupWizard = ({ ); }; - const shouldDisplayExperiment = useCallback(async () => { - const experimentValue = isAnalyticsAccepted - ? (await getExperimentVariant( - ExperimentName.COMBINED_NAME_PASSWORD_ONBOARDING_SCREEN - )) === 'test' - : false; - - setShouldDisplayTestVariantForExperiment(experimentValue); - }, [getExperimentVariant, isAnalyticsAccepted]); - - useEffect(() => { - shouldDisplayExperiment(); - }, [shouldDisplayExperiment]); - return ( : undefined}> - {currentStep === WalletSetupSteps.Legal && ( - { - sendAnalytics(postHogOnboardingActions[setupType]?.LACE_TERMS_OF_USE_NEXT_CLICK); - moveForward(); - }} - translations={walletSetupLegalStepTranslations} - /> - )} - {currentStep === WalletSetupSteps.Analytics && ( - handleAnalyticsChoice(false)} - onAccept={() => handleAnalyticsChoice(true)} - onBack={moveBack} - translations={walletSetupAnalyticsStepTranslations} - /> - )} - {currentStep === WalletSetupSteps.PreMnemonic && ( - { - analytics.sendEventToPostHog(postHogOnboardingActions[setupType]?.PASSPHRASE_INTRO_NEXT_CLICK); - moveForward(); - }} - translations={walletSetupMnemonicIntroStepTranslations} - onClickVideo={() => - analytics.sendEventToPostHog(postHogOnboardingActions[setupType]?.PASSPHRASE_INTRO_PLAY_VIDEO_CLICK) - } - videoSrc={process.env.YOUTUBE_RECOVERY_PHRASE_VIDEO_URL} - /> - )} {currentStep === WalletSetupSteps.Mnemonic && ( }>{renderedMnemonicStep()} )} @@ -490,34 +334,9 @@ export const WalletSetupWizard = ({ )} - - {shouldDisplayTestVariantForExperiment ? ( - <> - {currentStep === WalletSetupSteps.Register && ( - - )} - - ) : ( - <> - {currentStep === WalletSetupSteps.Register && ( - - )} - {currentStep === WalletSetupSteps.Password && ( - - )} - + {currentStep === WalletSetupSteps.Register && ( + )} - {currentStep === WalletSetupSteps.RecoveryPhraseLength && ( void; } +const INITIAL_WALLET_NAME = 'Wallet 1'; + export const WalletSetupNamePasswordStep = ({ onBack, onNext, - initialWalletName = '', + initialWalletName = INITIAL_WALLET_NAME, onChange }: WalletSetupNamePasswordStepProps): React.ReactElement => { const { t } = useTranslate(); diff --git a/packages/core/src/ui/components/WalletSetup/WalletSetupStepLayout.tsx b/packages/core/src/ui/components/WalletSetup/WalletSetupStepLayout.tsx index 199322469..067237619 100644 --- a/packages/core/src/ui/components/WalletSetup/WalletSetupStepLayout.tsx +++ b/packages/core/src/ui/components/WalletSetup/WalletSetupStepLayout.tsx @@ -47,7 +47,6 @@ const removeLegalAndAnalyticsStep = ( const getTimelineSteps = (currentStep: WalletTimelineSteps, isHardwareWallet: boolean, flow: WalletSetupFlow) => { const inMemoryWalletSteps = [ - { key: WalletTimelineSteps.LEGAL_AND_ANALYTICS, name: i18n.t('package.core.walletSetupStep.legalAndAnalytics') }, { key: WalletTimelineSteps.WALLET_SETUP, name: i18n.t('package.core.walletSetupStep.walletSetup') }, { key: WalletTimelineSteps.RECOVERY_PHRASE, name: i18n.t('package.core.walletSetupStep.recoveryPhrase') }, { key: WalletTimelineSteps.ALL_DONE, name: i18n.t('package.core.walletSetupStep.allDone') } diff --git a/packages/core/src/ui/components/WalletSetup/wallet-steps.ts b/packages/core/src/ui/components/WalletSetup/wallet-steps.ts index 6e1e14cd1..e8df66969 100644 --- a/packages/core/src/ui/components/WalletSetup/wallet-steps.ts +++ b/packages/core/src/ui/components/WalletSetup/wallet-steps.ts @@ -1,31 +1,15 @@ import { WalletSetupSteps, WalletSetupWizard } from './wallet-steps.common'; export const walletSetupWizard: WalletSetupWizard = { - [WalletSetupSteps.Legal]: { - next: WalletSetupSteps.Analytics - }, - [WalletSetupSteps.Analytics]: { - prev: WalletSetupSteps.Legal, - next: WalletSetupSteps.Register - }, [WalletSetupSteps.Register]: { - prev: WalletSetupSteps.Analytics, - next: WalletSetupSteps.Password - }, - [WalletSetupSteps.Password]: { - prev: WalletSetupSteps.Register, next: WalletSetupSteps.RecoveryPhraseLength }, [WalletSetupSteps.RecoveryPhraseLength]: { - prev: WalletSetupSteps.Password, - next: WalletSetupSteps.Mnemonic - }, - [WalletSetupSteps.PreMnemonic]: { - prev: WalletSetupSteps.Password, + prev: WalletSetupSteps.Register, next: WalletSetupSteps.Mnemonic }, [WalletSetupSteps.Mnemonic]: { - prev: WalletSetupSteps.PreMnemonic, + prev: WalletSetupSteps.RecoveryPhraseLength, next: WalletSetupSteps.Create }, [WalletSetupSteps.Create]: { From da026eae30e0acd598af6e9b97eb94c04a8bc31a Mon Sep 17 00:00:00 2001 From: shawnbusuttil Date: Thu, 15 Feb 2024 16:49:04 +0000 Subject: [PATCH 02/10] refactor: remove env variable related and redundant analytics references --- apps/browser-extension-wallet/.env.defaults | 1 - .../.env.developerpreview | 1 - apps/browser-extension-wallet/.env.example | 2 +- .../components/WalletSetupWizard.tsx | 27 ++++++++----------- .../features/wallet-setup/constants.ts | 17 ------------ 5 files changed, 12 insertions(+), 36 deletions(-) delete mode 100644 apps/browser-extension-wallet/src/views/browser-view/features/wallet-setup/constants.ts diff --git a/apps/browser-extension-wallet/.env.defaults b/apps/browser-extension-wallet/.env.defaults index f31c60662..0296fc349 100644 --- a/apps/browser-extension-wallet/.env.defaults +++ b/apps/browser-extension-wallet/.env.defaults @@ -22,7 +22,6 @@ USE_HIDE_MY_BALANCE=true USE_ADA_HANDLE=true USE_DATA_CHECK=false USE_POSTHOG_ANALYTICS=true -USE_COMBINED_PASSWORD_NAME_STEP_COMPONENT=false # TODO Remove redundant feature flags when Trezor and Ledger are supported (https://input-output.atlassian.net/browse/LW-9480) USE_MULTI_DELEGATION_STAKING_LEDGER=false USE_MULTI_DELEGATION_STAKING_TREZOR=false diff --git a/apps/browser-extension-wallet/.env.developerpreview b/apps/browser-extension-wallet/.env.developerpreview index 80566178a..402fe136f 100644 --- a/apps/browser-extension-wallet/.env.developerpreview +++ b/apps/browser-extension-wallet/.env.developerpreview @@ -23,7 +23,6 @@ USE_MULTI_DELEGATION_STAKING=true USE_ADA_HANDLE=false USE_DATA_CHECK=false USE_POSTHOG_ANALYTICS=true -USE_COMBINED_PASSWORD_NAME_STEP_COMPONENT=false USE_MULTI_DELEGATION_STAKING_ACTIVITY=false USE_POSTHOG_ANALYTICS_FOR_OPTED_OUT=false diff --git a/apps/browser-extension-wallet/.env.example b/apps/browser-extension-wallet/.env.example index 740202ad9..3fbdeb7c6 100644 --- a/apps/browser-extension-wallet/.env.example +++ b/apps/browser-extension-wallet/.env.example @@ -25,7 +25,7 @@ USE_HANDLE_AB=false USE_DATA_CHECK=false USE_POSTHOG_ANALYTICS=true USE_POSTHOG_ANALYTICS_FOR_OPTED_OUT=false -USE_COMBINED_PASSWORD_NAME_STEP_COMPONENT=false +USE_MATOMO_ANALYTICS_FOR_OPTED_OUT=false USE_MULTI_DELEGATION_STAKING_ACTIVITY=true USE_MULTI_DELEGATION_STAKING_GRID_VIEW=false USE_ROS_STAKING_COLUMN=false diff --git a/apps/browser-extension-wallet/src/views/browser-view/features/wallet-setup/components/WalletSetupWizard.tsx b/apps/browser-extension-wallet/src/views/browser-view/features/wallet-setup/components/WalletSetupWizard.tsx index 223ae91f1..dba73f64c 100644 --- a/apps/browser-extension-wallet/src/views/browser-view/features/wallet-setup/components/WalletSetupWizard.tsx +++ b/apps/browser-extension-wallet/src/views/browser-view/features/wallet-setup/components/WalletSetupWizard.tsx @@ -31,6 +31,9 @@ import { useAnalyticsContext } from '@providers'; import { ENHANCED_ANALYTICS_OPT_IN_STATUS_LS_KEY } from '@providers/AnalyticsProvider/config'; import * as process from 'process'; import { SendOnboardingAnalyticsEvent, SetupType } from '../types'; +import { isScriptAddress } from '@cardano-sdk/wallet'; +import { filter, firstValueFrom } from 'rxjs'; +import { useWalletStore } from '@src/stores'; const WalletSetupModeStep = React.lazy(() => import('@lace/core').then((module) => ({ default: module.WalletSetupModeStep })) @@ -73,12 +76,15 @@ export const WalletSetupWizard = ({ const [walletName, setWalletName] = useState(getValueFromLocalStorage('wallet')?.name); const [password, setPassword] = useState(''); const [walletInstance, setWalletInstance] = useState(); - const [isAnalyticsAccepted] = useState(false); const [mnemonicLength, setMnemonicLength] = useState(DEFAULT_MNEMONIC_LENGTH); const [mnemonic, setMnemonic] = useState([]); const [walletIsCreating, setWalletIsCreating] = useState(false); const [resetMnemonicStage, setResetMnemonicStage] = useState(''); const [isResetMnemonicModalOpen, setIsResetMnemonicModalOpen] = useState(false); + const [enhancedAnalyticsStatus, { updateLocalStorage: setDoesUserAllowAnalytics }] = useLocalStorage( + ENHANCED_ANALYTICS_OPT_IN_STATUS_LS_KEY, + EnhancedAnalyticsOptInStatus.OptedOut + ); const { createWallet } = useWalletManager(); const { setStayOnAllDonePage } = useWalletStore(); @@ -163,15 +169,10 @@ export const WalletSetupWizard = ({ setCurrentStep(walletStep); }; - const [, { updateLocalStorage: setDoesUserAllowAnalytics }] = useLocalStorage( - ENHANCED_ANALYTICS_OPT_IN_STATUS_LS_KEY, - EnhancedAnalyticsOptInStatus.OptedOut - ); - const goToMyWallet = useCallback( async (cardanoWallet: Wallet.CardanoWallet = walletInstance) => { setStayOnAllDonePage(false); - if (isAnalyticsAccepted) { + if (enhancedAnalyticsStatus === EnhancedAnalyticsOptInStatus.OptedIn) { analytics.sendAliasEvent(); const addresses = await firstValueFrom(cardanoWallet.wallet.addresses$.pipe(filter((a) => a.length > 0))); const hdWalletDiscovered = addresses.some((addr) => !isScriptAddress(addr) && addr.index > 0); @@ -180,12 +181,13 @@ export const WalletSetupWizard = ({ } } }, - [analytics, isAnalyticsAccepted, setStayOnAllDonePage, walletInstance] + [analytics, enhancedAnalyticsStatus, setStayOnAllDonePage, walletInstance] ); const handleCompleteCreation = useCallback(async () => { try { setStayOnAllDonePage(true); + const wallet = await createWallet({ name: walletName, mnemonic, @@ -193,12 +195,6 @@ export const WalletSetupWizard = ({ chainId: DEFAULT_CHAIN_ID }); setWalletInstance(wallet); - setDoesUserAllowAnalytics( - isAnalyticsAccepted ? EnhancedAnalyticsOptInStatus.OptedIn : EnhancedAnalyticsOptInStatus.OptedOut - ); - await analytics.setOptedInForEnhancedAnalytics( - isAnalyticsAccepted ? EnhancedAnalyticsOptInStatus.OptedIn : EnhancedAnalyticsOptInStatus.OptedOut - ); wallet.wallet.addresses$.subscribe((addresses) => { if (addresses.length === 0) return; @@ -225,7 +221,6 @@ export const WalletSetupWizard = ({ mnemonic, password, setDoesUserAllowAnalytics, - isAnalyticsAccepted, analytics, setupType, goToMyWallet, @@ -383,4 +378,4 @@ export const WalletSetupWizard = ({ )} ); -}; +}; \ No newline at end of file diff --git a/apps/browser-extension-wallet/src/views/browser-view/features/wallet-setup/constants.ts b/apps/browser-extension-wallet/src/views/browser-view/features/wallet-setup/constants.ts deleted file mode 100644 index d4d8117a3..000000000 --- a/apps/browser-extension-wallet/src/views/browser-view/features/wallet-setup/constants.ts +++ /dev/null @@ -1,17 +0,0 @@ -export const passwordTranslationMap: Record = { - 'feedback.1': 'core.password.feedback.1', - 'feedback.2': 'core.password.feedback.2', - 'feedback.3': 'core.password.feedback.3', - 'feedback.4': 'core.password.feedback.4', - 'feedback.5': 'core.password.feedback.5', - 'feedback.6': 'core.password.feedback.6', - 'feedback.7': 'core.password.feedback.7', - 'feedback.8': 'core.password.feedback.8', - 'feedback.9': 'core.password.feedback.9', - 'feedback.10': 'core.password.feedback.10', - 'feedback.11': 'core.password.feedback.11', - 'feedback.12': 'core.password.feedback.12', - 'feedback.13': 'core.password.feedback.13', - 'feedback.14': 'core.password.feedback.14', - 'feedback.15': 'core.password.feedback.15' -}; From 286b760b40bab41c257fd52f97a9752b136e3920 Mon Sep 17 00:00:00 2001 From: shawnbusuttil Date: Tue, 27 Feb 2024 13:09:19 +0000 Subject: [PATCH 03/10] refactor: update per analytics --- .../wallet-setup/components/WalletSetup.tsx | 8 +------ .../components/WalletSetupWizard.tsx | 3 +-- .../components/__tests__/WalletSetup.test.tsx | 2 +- .../ui/components/WalletSetup/wallet-steps.ts | 6 ++++- .../WalletSetupRevamp/wallet-steps-revamp.ts | 22 +++++++++++++++++++ 5 files changed, 30 insertions(+), 11 deletions(-) create mode 100644 packages/core/src/ui/components/WalletSetupRevamp/wallet-steps-revamp.ts diff --git a/apps/browser-extension-wallet/src/views/browser-view/features/wallet-setup/components/WalletSetup.tsx b/apps/browser-extension-wallet/src/views/browser-view/features/wallet-setup/components/WalletSetup.tsx index 469a3e5e2..76210ab73 100644 --- a/apps/browser-extension-wallet/src/views/browser-view/features/wallet-setup/components/WalletSetup.tsx +++ b/apps/browser-extension-wallet/src/views/browser-view/features/wallet-setup/components/WalletSetup.tsx @@ -1,10 +1,4 @@ -import { - useTranslate, - WalletSetupOptionsStep, - WalletSetupSteps, - WalletSetupFlowProvider, - WalletSetupFlow -} from '@lace/core'; +import { WalletSetupStepsRevamp as WalletSetupSteps, WalletSetupFlowProvider, WalletSetupFlow } from '@lace/core'; import { useAnalyticsContext } from '@providers/AnalyticsProvider'; import { PostHogAction, diff --git a/apps/browser-extension-wallet/src/views/browser-view/features/wallet-setup/components/WalletSetupWizard.tsx b/apps/browser-extension-wallet/src/views/browser-view/features/wallet-setup/components/WalletSetupWizard.tsx index dba73f64c..dba62c0c2 100644 --- a/apps/browser-extension-wallet/src/views/browser-view/features/wallet-setup/components/WalletSetupWizard.tsx +++ b/apps/browser-extension-wallet/src/views/browser-view/features/wallet-setup/components/WalletSetupWizard.tsx @@ -9,8 +9,7 @@ import { WalletSetupFinalStep, WalletSetupNamePasswordStep, WalletSetupRecoveryPhraseLengthStep, - WalletSetupSteps, - walletSetupWizard + WalletSetupStepsRevamp as WalletSetupSteps, } from '@lace/core'; import { Wallet } from '@lace/cardano'; import { WalletSetupLayout } from '@src/views/browser-view/components/Layout'; diff --git a/apps/browser-extension-wallet/src/views/browser-view/features/wallet-setup/components/__tests__/WalletSetup.test.tsx b/apps/browser-extension-wallet/src/views/browser-view/features/wallet-setup/components/__tests__/WalletSetup.test.tsx index cf77906b0..bdefe5bd9 100644 --- a/apps/browser-extension-wallet/src/views/browser-view/features/wallet-setup/components/__tests__/WalletSetup.test.tsx +++ b/apps/browser-extension-wallet/src/views/browser-view/features/wallet-setup/components/__tests__/WalletSetup.test.tsx @@ -10,7 +10,7 @@ import { ThemeProvider } from '@providers/ThemeProvider'; import { MemoryRouter } from 'react-router-dom'; import { WalletSetup } from '../WalletSetup'; import { I18nextProvider } from 'react-i18next'; -import { WalletSetupSteps } from '@lace/core'; +import { WalletSetupStepsRevamp as WalletSetupSteps } from '@lace/core'; import { render, fireEvent, waitFor } from '@testing-library/react'; jest.mock('@stores', () => ({ diff --git a/packages/core/src/ui/components/WalletSetup/wallet-steps.ts b/packages/core/src/ui/components/WalletSetup/wallet-steps.ts index e8df66969..124f5dbf2 100644 --- a/packages/core/src/ui/components/WalletSetup/wallet-steps.ts +++ b/packages/core/src/ui/components/WalletSetup/wallet-steps.ts @@ -8,8 +8,12 @@ export const walletSetupWizard: WalletSetupWizard = { prev: WalletSetupSteps.Register, next: WalletSetupSteps.Mnemonic }, + [WalletSetupSteps.PreMnemonic]: { + prev: WalletSetupSteps.Register, + next: WalletSetupSteps.Mnemonic + }, [WalletSetupSteps.Mnemonic]: { - prev: WalletSetupSteps.RecoveryPhraseLength, + prev: WalletSetupSteps.PreMnemonic, next: WalletSetupSteps.Create }, [WalletSetupSteps.Create]: { diff --git a/packages/core/src/ui/components/WalletSetupRevamp/wallet-steps-revamp.ts b/packages/core/src/ui/components/WalletSetupRevamp/wallet-steps-revamp.ts new file mode 100644 index 000000000..e2d8e0be6 --- /dev/null +++ b/packages/core/src/ui/components/WalletSetupRevamp/wallet-steps-revamp.ts @@ -0,0 +1,22 @@ +import { WalletSetupStepsRevamp, WalletSetupWizardRevamp } from './wallet-steps-revamp.common'; + +export const walletSetupWizardRevamp: WalletSetupWizardRevamp = { + [WalletSetupStepsRevamp.Register]: { + next: WalletSetupStepsRevamp.RecoveryPhraseLength + }, + [WalletSetupStepsRevamp.RecoveryPhraseLength]: { + prev: WalletSetupStepsRevamp.Register, + next: WalletSetupStepsRevamp.Mnemonic + }, + [WalletSetupStepsRevamp.Mnemonic]: { + prev: WalletSetupStepsRevamp.RecoveryPhraseLength, + next: WalletSetupStepsRevamp.Create + }, + [WalletSetupStepsRevamp.Create]: { + prev: WalletSetupStepsRevamp.Mnemonic, + next: WalletSetupStepsRevamp.Finish + }, + [WalletSetupStepsRevamp.Finish]: { + prev: WalletSetupStepsRevamp.Create + } +}; From 52db2f52df546459c87a0299c40439f727267030 Mon Sep 17 00:00:00 2001 From: shawnbusuttil Date: Wed, 28 Feb 2024 11:48:44 +0000 Subject: [PATCH 04/10] refactor: stabilize branch --- .../wallet-setup/components/WalletSetup.tsx | 8 ++++++- .../components/WalletSetupWizard.tsx | 5 +++-- .../components/__tests__/WalletSetup.test.tsx | 4 ++-- .../WalletSetupRevamp/wallet-steps-revamp.ts | 22 ------------------- 4 files changed, 12 insertions(+), 27 deletions(-) delete mode 100644 packages/core/src/ui/components/WalletSetupRevamp/wallet-steps-revamp.ts diff --git a/apps/browser-extension-wallet/src/views/browser-view/features/wallet-setup/components/WalletSetup.tsx b/apps/browser-extension-wallet/src/views/browser-view/features/wallet-setup/components/WalletSetup.tsx index 76210ab73..7abab18e2 100644 --- a/apps/browser-extension-wallet/src/views/browser-view/features/wallet-setup/components/WalletSetup.tsx +++ b/apps/browser-extension-wallet/src/views/browser-view/features/wallet-setup/components/WalletSetup.tsx @@ -1,4 +1,10 @@ -import { WalletSetupStepsRevamp as WalletSetupSteps, WalletSetupFlowProvider, WalletSetupFlow } from '@lace/core'; +import { + WalletSetupSteps, + WalletSetupFlowProvider, + WalletSetupFlow, + useTranslate, + WalletSetupOptionsStep +} from '@lace/core'; import { useAnalyticsContext } from '@providers/AnalyticsProvider'; import { PostHogAction, diff --git a/apps/browser-extension-wallet/src/views/browser-view/features/wallet-setup/components/WalletSetupWizard.tsx b/apps/browser-extension-wallet/src/views/browser-view/features/wallet-setup/components/WalletSetupWizard.tsx index dba62c0c2..a66fe7bf0 100644 --- a/apps/browser-extension-wallet/src/views/browser-view/features/wallet-setup/components/WalletSetupWizard.tsx +++ b/apps/browser-extension-wallet/src/views/browser-view/features/wallet-setup/components/WalletSetupWizard.tsx @@ -9,7 +9,8 @@ import { WalletSetupFinalStep, WalletSetupNamePasswordStep, WalletSetupRecoveryPhraseLengthStep, - WalletSetupStepsRevamp as WalletSetupSteps, + WalletSetupSteps, + walletSetupWizard } from '@lace/core'; import { Wallet } from '@lace/cardano'; import { WalletSetupLayout } from '@src/views/browser-view/components/Layout'; @@ -377,4 +378,4 @@ export const WalletSetupWizard = ({ )} ); -}; \ No newline at end of file +}; diff --git a/apps/browser-extension-wallet/src/views/browser-view/features/wallet-setup/components/__tests__/WalletSetup.test.tsx b/apps/browser-extension-wallet/src/views/browser-view/features/wallet-setup/components/__tests__/WalletSetup.test.tsx index bdefe5bd9..9f3bc37f5 100644 --- a/apps/browser-extension-wallet/src/views/browser-view/features/wallet-setup/components/__tests__/WalletSetup.test.tsx +++ b/apps/browser-extension-wallet/src/views/browser-view/features/wallet-setup/components/__tests__/WalletSetup.test.tsx @@ -10,7 +10,7 @@ import { ThemeProvider } from '@providers/ThemeProvider'; import { MemoryRouter } from 'react-router-dom'; import { WalletSetup } from '../WalletSetup'; import { I18nextProvider } from 'react-i18next'; -import { WalletSetupStepsRevamp as WalletSetupSteps } from '@lace/core'; +import { WalletSetupSteps } from '@lace/core'; import { render, fireEvent, waitFor } from '@testing-library/react'; jest.mock('@stores', () => ({ @@ -54,7 +54,7 @@ const SetupContainerTest = () => ( - + diff --git a/packages/core/src/ui/components/WalletSetupRevamp/wallet-steps-revamp.ts b/packages/core/src/ui/components/WalletSetupRevamp/wallet-steps-revamp.ts deleted file mode 100644 index e2d8e0be6..000000000 --- a/packages/core/src/ui/components/WalletSetupRevamp/wallet-steps-revamp.ts +++ /dev/null @@ -1,22 +0,0 @@ -import { WalletSetupStepsRevamp, WalletSetupWizardRevamp } from './wallet-steps-revamp.common'; - -export const walletSetupWizardRevamp: WalletSetupWizardRevamp = { - [WalletSetupStepsRevamp.Register]: { - next: WalletSetupStepsRevamp.RecoveryPhraseLength - }, - [WalletSetupStepsRevamp.RecoveryPhraseLength]: { - prev: WalletSetupStepsRevamp.Register, - next: WalletSetupStepsRevamp.Mnemonic - }, - [WalletSetupStepsRevamp.Mnemonic]: { - prev: WalletSetupStepsRevamp.RecoveryPhraseLength, - next: WalletSetupStepsRevamp.Create - }, - [WalletSetupStepsRevamp.Create]: { - prev: WalletSetupStepsRevamp.Mnemonic, - next: WalletSetupStepsRevamp.Finish - }, - [WalletSetupStepsRevamp.Finish]: { - prev: WalletSetupStepsRevamp.Create - } -}; From 2b9750542dd4209ef40d1baf5ae58fccb76443a0 Mon Sep 17 00:00:00 2001 From: shawnbusuttil Date: Wed, 28 Feb 2024 11:55:16 +0000 Subject: [PATCH 05/10] refactor: remove last occurrence of password step --- .../features/wallet-setup/components/WalletSetupWizard.tsx | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/apps/browser-extension-wallet/src/views/browser-view/features/wallet-setup/components/WalletSetupWizard.tsx b/apps/browser-extension-wallet/src/views/browser-view/features/wallet-setup/components/WalletSetupWizard.tsx index a66fe7bf0..acc2df0b7 100644 --- a/apps/browser-extension-wallet/src/views/browser-view/features/wallet-setup/components/WalletSetupWizard.tsx +++ b/apps/browser-extension-wallet/src/views/browser-view/features/wallet-setup/components/WalletSetupWizard.tsx @@ -261,7 +261,7 @@ export const WalletSetupWizard = ({ onCancel={() => useDifferentMnemonicLengths ? skipTo(WalletSetupSteps.RecoveryPhraseLength) - : skipTo(WalletSetupSteps.Password) + : skipTo(WalletSetupSteps.Register) } onSubmit={moveForward} onStepNext={(step: number) => { From 8ce9bb5ecd94568d99175ec888f15d452f198420 Mon Sep 17 00:00:00 2001 From: shawnbusuttil Date: Wed, 28 Feb 2024 19:09:27 +0000 Subject: [PATCH 06/10] fix: forgot password flow broken --- .../features/wallet-setup/components/WalletSetupWizard.tsx | 4 +--- .../core/src/ui/components/WalletSetup/wallet-steps.common.ts | 1 - 2 files changed, 1 insertion(+), 4 deletions(-) diff --git a/apps/browser-extension-wallet/src/views/browser-view/features/wallet-setup/components/WalletSetupWizard.tsx b/apps/browser-extension-wallet/src/views/browser-view/features/wallet-setup/components/WalletSetupWizard.tsx index acc2df0b7..6facc14cc 100644 --- a/apps/browser-extension-wallet/src/views/browser-view/features/wallet-setup/components/WalletSetupWizard.tsx +++ b/apps/browser-extension-wallet/src/views/browser-view/features/wallet-setup/components/WalletSetupWizard.tsx @@ -70,9 +70,7 @@ export const WalletSetupWizard = ({ sendAnalytics, initialStep = WalletSetupSteps.Register }: WalletSetupWizardProps): React.ReactElement => { - const [currentStep, setCurrentStep] = useState( - setupType === SetupType.FORGOT_PASSWORD ? WalletSetupSteps.Password : initialStep - ); + const [currentStep, setCurrentStep] = useState(initialStep); const [walletName, setWalletName] = useState(getValueFromLocalStorage('wallet')?.name); const [password, setPassword] = useState(''); const [walletInstance, setWalletInstance] = useState(); diff --git a/packages/core/src/ui/components/WalletSetup/wallet-steps.common.ts b/packages/core/src/ui/components/WalletSetup/wallet-steps.common.ts index b41208b11..819d50aa4 100644 --- a/packages/core/src/ui/components/WalletSetup/wallet-steps.common.ts +++ b/packages/core/src/ui/components/WalletSetup/wallet-steps.common.ts @@ -5,7 +5,6 @@ export enum WalletSetupSteps { PreMnemonic = 'pre-mnemonic', Mnemonic = 'mnemonic', Register = 'register', - Password = 'password', RecoveryPhraseLength = 'recovery-phrase-length', Create = 'create', Finish = 'finish' From 3e229277af7b9eefc65a6d86841554936f7c3189 Mon Sep 17 00:00:00 2001 From: John Oshalusi Date: Thu, 29 Feb 2024 10:41:05 +0100 Subject: [PATCH 07/10] fix: password input suffix --- .../src/providers/ExperimentsProvider/context.tsx | 8 +------- .../wallet-setup/components/WalletSetupWizard.tsx | 3 +-- .../WalletSetupNamePasswordStep/styles.module.scss | 11 +++++++++++ 3 files changed, 13 insertions(+), 9 deletions(-) diff --git a/apps/browser-extension-wallet/src/providers/ExperimentsProvider/context.tsx b/apps/browser-extension-wallet/src/providers/ExperimentsProvider/context.tsx index 4819b6423..492330c5f 100644 --- a/apps/browser-extension-wallet/src/providers/ExperimentsProvider/context.tsx +++ b/apps/browser-extension-wallet/src/providers/ExperimentsProvider/context.tsx @@ -1,4 +1,4 @@ -import React, { createContext, useCallback, useContext, useEffect, useMemo, useState } from 'react'; +import React, { createContext, useCallback, useEffect, useMemo, useState } from 'react'; import { usePostHogClientContext } from '@providers/PostHogClientProvider'; import { ExperimentName, ExperimentsConfigStatus } from './types'; @@ -11,12 +11,6 @@ type ExperimentsContext = { // eslint-disable-next-line unicorn/no-null const ExperimentsContext = createContext(null); -export const useExperimentsContext = (): ExperimentsContext => { - const postHogClientContext = useContext(ExperimentsContext); - if (postHogClientContext === null) throw new Error('ExperimentsContext not defined'); - return postHogClientContext; -}; - interface ExperimentsProviderProps { children: React.ReactNode; } diff --git a/apps/browser-extension-wallet/src/views/browser-view/features/wallet-setup/components/WalletSetupWizard.tsx b/apps/browser-extension-wallet/src/views/browser-view/features/wallet-setup/components/WalletSetupWizard.tsx index 6facc14cc..382982098 100644 --- a/apps/browser-extension-wallet/src/views/browser-view/features/wallet-setup/components/WalletSetupWizard.tsx +++ b/apps/browser-extension-wallet/src/views/browser-view/features/wallet-setup/components/WalletSetupWizard.tsx @@ -79,7 +79,7 @@ export const WalletSetupWizard = ({ const [walletIsCreating, setWalletIsCreating] = useState(false); const [resetMnemonicStage, setResetMnemonicStage] = useState(''); const [isResetMnemonicModalOpen, setIsResetMnemonicModalOpen] = useState(false); - const [enhancedAnalyticsStatus, { updateLocalStorage: setDoesUserAllowAnalytics }] = useLocalStorage( + const [enhancedAnalyticsStatus] = useLocalStorage( ENHANCED_ANALYTICS_OPT_IN_STATUS_LS_KEY, EnhancedAnalyticsOptInStatus.OptedOut ); @@ -218,7 +218,6 @@ export const WalletSetupWizard = ({ walletName, mnemonic, password, - setDoesUserAllowAnalytics, analytics, setupType, goToMyWallet, diff --git a/packages/core/src/ui/components/WalletSetup/WalletSetupNamePasswordStep/styles.module.scss b/packages/core/src/ui/components/WalletSetup/WalletSetupNamePasswordStep/styles.module.scss index c046b3071..adddf63a1 100644 --- a/packages/core/src/ui/components/WalletSetup/WalletSetupNamePasswordStep/styles.module.scss +++ b/packages/core/src/ui/components/WalletSetup/WalletSetupNamePasswordStep/styles.module.scss @@ -1,3 +1,5 @@ +@import '../../../styles/theme.scss'; + .walletPasswordAndNameContainer { display: flex; flex-direction: column; @@ -35,3 +37,12 @@ .paddingLeft { padding-left: 24px !important; } + +.input { + width: 100% !important; + max-width: none !important; + + :global(.ant-input-suffix) { + margin-left: size_unit(2); + } +} From 9d6c35c18bc96d71404087f8ffcf092f990042c7 Mon Sep 17 00:00:00 2001 From: John Oshalusi Date: Fri, 1 Mar 2024 12:27:15 +0100 Subject: [PATCH 08/10] feat: [lw-9740] remove legal and analytics page from onboarding flow --- .../src/lib/translations/en.json | 30 ++- .../analyticsTracker/events.ts | 13 +- .../analyticsTracker/types.ts | 7 +- .../src/providers/AnalyticsProvider/config.ts | 2 +- .../src/types/local-storage.ts | 2 +- .../components/HardwareWalletFlow.tsx | 74 +------ .../components/WalletSetup.module.scss | 10 + .../wallet-setup/components/WalletSetup.tsx | 190 +++++------------- .../components/WalletSetupMainPage.tsx | 165 +++++++++++++++ .../components/WalletSetupWizard.tsx | 83 +------- .../components/__tests__/WalletSetup.test.tsx | 106 ---------- packages/common/src/analytics/types.ts | 4 + .../onboarding/hardware-wallet.component.svg | 26 ++- .../AnalyticsConfirmationBanner.module.scss | 43 ++++ .../AnalyticsConfirmationBanner.tsx | 51 +++++ .../WalletSetup/LegalTranslations.tsx | 42 ++++ .../WalletAnalyticsInfo.module.scss | 19 ++ .../WalletSetup/WalletAnalyticsInfo.tsx | 43 ++++ .../WalletSetupAnalyticsStep.module.scss | 30 --- .../WalletSetup/WalletSetupAnalyticsStep.tsx | 81 -------- .../WalletSetupLegalStep.module.scss | 47 ----- .../WalletSetup/WalletSetupLegalStep.tsx | 88 -------- .../src/ui/components/WalletSetup/index.ts | 5 +- .../WalletSetup/wallet-steps.common.ts | 2 - .../ui/components/WalletSetup/wallet-steps.ts | 8 - .../WalletSetupOptionsStepRevamp.module.scss | 56 ++++++ .../WalletSetupOptionsStepRevamp.tsx | 79 ++++++++ .../ui/components/WalletSetupRevamp/index.ts | 1 + packages/core/src/ui/lib/translations/en.json | 7 +- packages/core/src/ui/utils/types.ts | 13 -- 30 files changed, 623 insertions(+), 704 deletions(-) create mode 100644 apps/browser-extension-wallet/src/views/browser-view/features/wallet-setup/components/WalletSetupMainPage.tsx delete mode 100644 apps/browser-extension-wallet/src/views/browser-view/features/wallet-setup/components/__tests__/WalletSetup.test.tsx create mode 100644 packages/core/src/ui/components/WalletSetup/AnalyticsConfirmationBanner.module.scss create mode 100644 packages/core/src/ui/components/WalletSetup/AnalyticsConfirmationBanner.tsx create mode 100644 packages/core/src/ui/components/WalletSetup/LegalTranslations.tsx create mode 100644 packages/core/src/ui/components/WalletSetup/WalletAnalyticsInfo.module.scss create mode 100644 packages/core/src/ui/components/WalletSetup/WalletAnalyticsInfo.tsx delete mode 100644 packages/core/src/ui/components/WalletSetup/WalletSetupAnalyticsStep.module.scss delete mode 100644 packages/core/src/ui/components/WalletSetup/WalletSetupAnalyticsStep.tsx delete mode 100644 packages/core/src/ui/components/WalletSetup/WalletSetupLegalStep.module.scss delete mode 100644 packages/core/src/ui/components/WalletSetup/WalletSetupLegalStep.tsx create mode 100644 packages/core/src/ui/components/WalletSetupRevamp/WalletSetupOptionsStepRevamp.module.scss create mode 100644 packages/core/src/ui/components/WalletSetupRevamp/WalletSetupOptionsStepRevamp.tsx diff --git a/apps/browser-extension-wallet/src/lib/translations/en.json b/apps/browser-extension-wallet/src/lib/translations/en.json index 09d0d360f..f344b758e 100644 --- a/apps/browser-extension-wallet/src/lib/translations/en.json +++ b/apps/browser-extension-wallet/src/lib/translations/en.json @@ -1152,6 +1152,10 @@ "registered": "Registered" } }, + "analyticsConfirmationBanner": { + "message": "Help us improve the quality and performance of Lace by sharing analytics data from your browser.", + "learnMore": "Learn more" + }, "core": { "general": { "saveButton": "Save", @@ -1226,22 +1230,14 @@ "walletBasicInfo": { "balance": "Balance" }, - "walletSetupLegalStep": { - "title": "Lace Terms of Use", - "toolTipText": "Please read and accept the terms" - }, - "walletSetupAnalyticsStep": { - "title": "Give us a hand to improve your experience", - "description": "By sharing analytics data from your browser, you can help us improve the quality and performance of Lace. For more information on our privacy practices, please see our", - "back": "Back", - "agree": "Agree", - "optionsTitle": "Lace will:", - "optionsFooter1": "For more information on our privacy practices, please see our", - "privacyPolicy": "Privacy Policy.", - "allowOptout": "Only collect pseudonymous analytics info", - "collectPrivateKeys": "Not access your private keys", - "collectIp": "Not record your IP address", - "personalData": "Not sell your personal data" + "walletAnalyticsInfo": { + "title": "Help us improve your experience", + "description": "Please opt in to share your data with us. We'll collect anonymous analytics info from your browser extension to\n help us improve the quality and performance of Lace.", + "gotIt": "Got it", + "allowOptout": "Always allow you to opt-out via Settings", + "collectPrivateKeys": "Never collect private keys", + "collectIp": "Never collect your IP address", + "personalData": "Never sell your personal data" }, "walletSetupConnectHardwareWalletStep": { "title": "Connect hardware wallet", @@ -1286,7 +1282,7 @@ "enterPassphrase": "Enter your secret passphrase" }, "walletSetupOptionsStep": { - "title": "Hello Web3", + "title": "Let's explore Web3 together", "subTitle": "Choose an option to get started", "newWallet": { "title": "New wallet", diff --git a/apps/browser-extension-wallet/src/providers/AnalyticsProvider/analyticsTracker/events.ts b/apps/browser-extension-wallet/src/providers/AnalyticsProvider/analyticsTracker/events.ts index bf4f3b707..f7330be03 100644 --- a/apps/browser-extension-wallet/src/providers/AnalyticsProvider/analyticsTracker/events.ts +++ b/apps/browser-extension-wallet/src/providers/AnalyticsProvider/analyticsTracker/events.ts @@ -1,11 +1,12 @@ import { PostHogAction, PostHogOnboardingActionsType } from './types'; export const postHogOnboardingActions: PostHogOnboardingActionsType = { + landing: { + ANALYTICS_AGREE_CLICK: PostHogAction.LandingAnalyticsAgreeClick, + ANALYTICS_REJECT_CLICK: PostHogAction.LandingAnalyticsRejectClick + }, create: { - ANALYTICS_AGREE_CLICK: PostHogAction.OnboardingCreateAnalyticsAgreeClick, - ANALYTICS_SKIP_CLICK: PostHogAction.OnboardingCreateAnalyticsSkipClick, SETUP_OPTION_CLICK: PostHogAction.OnboardingCreateClick, - LACE_TERMS_OF_USE_NEXT_CLICK: PostHogAction.OnboardingCreateLaceTermsOfUseNextClick, WALLET_NAME_NEXT_CLICK: PostHogAction.OnboardingCreateWalletNameNextClick, WALLET_PASSWORD_NEXT_CLICK: PostHogAction.OnboardingCreateWalletPasswordNextClick, PASSPHRASE_INTRO_NEXT_CLICK: PostHogAction.OnboardingCreatePassphraseIntroNextClick, @@ -20,10 +21,7 @@ export const postHogOnboardingActions: PostHogOnboardingActionsType = { PASSPHRASE_INTRO_PLAY_VIDEO_CLICK: PostHogAction.OnboardingCreatePassphraseIntroPlayVideoClick }, restore: { - ANALYTICS_AGREE_CLICK: PostHogAction.OnboardingRestoreAnalyticsAgreeClick, - ANALYTICS_SKIP_CLICK: PostHogAction.OnboardingRestoreAnalyticsSkipClick, SETUP_OPTION_CLICK: PostHogAction.OnboardingRestoreClick, - LACE_TERMS_OF_USE_NEXT_CLICK: PostHogAction.OnboardingRestoreLaceTermsOfUseNextClick, WALLET_NAME_NEXT_CLICK: PostHogAction.OnboardingRestoreWalletNameNextClick, WALLET_PASSWORD_NEXT_CLICK: PostHogAction.OnboardingRestoreWalletPasswordNextClick, RECOVERY_PASSPHRASE_LENGTH_NEXT_CLICK: PostHogAction.OnboardingRestoreRecoveryPhraseLengthNextClick, @@ -36,10 +34,7 @@ export const postHogOnboardingActions: PostHogOnboardingActionsType = { WALLET_NAME_PASSWORD_NEXT_CLICK: PostHogAction.OnboardingRestoreWalletNamePasswordNextClick }, hw: { - ANALYTICS_AGREE_CLICK: PostHogAction.OnboardingHWAnalyticsAgreeClick, - ANALYTICS_SKIP_CLICK: PostHogAction.OnboardingHWAnalyticsSkipClick, WALLET_NAME_NEXT_CLICK: PostHogAction.OnboardingHWNameNextClick, - LACE_TERMS_OF_USE_NEXT_CLICK: PostHogAction.OnboardinHWLaceTermsOfUseNextClick, CONNECT_HW_NEXT_CLICK: PostHogAction.OnboardingHWConnectNextClick, SETUP_HW_WALLET_NEXT_CLICK: PostHogAction.OnboardingHWSelectAccountNextClick, SETUP_OPTION_CLICK: PostHogAction.OnboardingHWClick, diff --git a/apps/browser-extension-wallet/src/providers/AnalyticsProvider/analyticsTracker/types.ts b/apps/browser-extension-wallet/src/providers/AnalyticsProvider/analyticsTracker/types.ts index 6ee641d4e..688b519e4 100644 --- a/apps/browser-extension-wallet/src/providers/AnalyticsProvider/analyticsTracker/types.ts +++ b/apps/browser-extension-wallet/src/providers/AnalyticsProvider/analyticsTracker/types.ts @@ -12,7 +12,8 @@ export type Metadata = { export enum EnhancedAnalyticsOptInStatus { OptedIn = 'ACCEPTED', - OptedOut = 'REJECTED' + OptedOut = 'REJECTED', + NotSet = 'NOT_SET' } export enum UserTrackingType { @@ -37,11 +38,11 @@ export enum TxCreationType { External = 'external' } -export type OnboardingFlows = 'create' | 'restore' | 'hw' | 'forgot_password'; +export type OnboardingFlows = 'create' | 'restore' | 'hw' | 'forgot_password' | 'landing'; export type PostHogActionsKeys = | 'SETUP_OPTION_CLICK' | 'ANALYTICS_AGREE_CLICK' - | 'ANALYTICS_SKIP_CLICK' + | 'ANALYTICS_REJECT_CLICK' | 'LACE_TERMS_OF_USE_NEXT_CLICK' | 'WALLET_NAME_NEXT_CLICK' | 'WALLET_PASSWORD_NEXT_CLICK' diff --git a/apps/browser-extension-wallet/src/providers/AnalyticsProvider/config.ts b/apps/browser-extension-wallet/src/providers/AnalyticsProvider/config.ts index 19afd8151..9f97f6a49 100644 --- a/apps/browser-extension-wallet/src/providers/AnalyticsProvider/config.ts +++ b/apps/browser-extension-wallet/src/providers/AnalyticsProvider/config.ts @@ -1 +1 @@ -export const ENHANCED_ANALYTICS_OPT_IN_STATUS_LS_KEY = 'analyticsAccepted'; +export const ENHANCED_ANALYTICS_OPT_IN_STATUS_LS_KEY = 'analyticsStatus'; diff --git a/apps/browser-extension-wallet/src/types/local-storage.ts b/apps/browser-extension-wallet/src/types/local-storage.ts index 3598fff91..f378b6223 100644 --- a/apps/browser-extension-wallet/src/types/local-storage.ts +++ b/apps/browser-extension-wallet/src/types/local-storage.ts @@ -47,7 +47,7 @@ export interface ILocalStorage { lastStaking?: LastStakingInfo; mode?: 'light' | 'dark'; hideBalance?: boolean; - analyticsAccepted?: EnhancedAnalyticsOptInStatus; + analyticsStatus?: EnhancedAnalyticsOptInStatus; isForgotPasswordFlow?: boolean; multidelegationFirstVisit?: boolean; multidelegationFirstVisitSincePortfolioPersistence?: boolean; diff --git a/apps/browser-extension-wallet/src/views/browser-view/features/wallet-setup/components/HardwareWalletFlow.tsx b/apps/browser-extension-wallet/src/views/browser-view/features/wallet-setup/components/HardwareWalletFlow.tsx index 458c4704e..ec0ea495d 100644 --- a/apps/browser-extension-wallet/src/views/browser-view/features/wallet-setup/components/HardwareWalletFlow.tsx +++ b/apps/browser-extension-wallet/src/views/browser-view/features/wallet-setup/components/HardwareWalletFlow.tsx @@ -3,15 +3,13 @@ /* eslint-disable react/no-multi-comp */ import { useWalletManager, useTimeSpentOnPage, useLocalStorage } from '@hooks'; import { - WalletSetupAnalyticsStep, WalletSetupCreationStep, - WalletSetupLegalStep, WalletSetupFinalStep, WalletSetupConnectHardwareWalletStep, WalletSetupSelectAccountsStepRevamp } from '@lace/core'; import React, { useState, useCallback, useEffect } from 'react'; -import { Switch, Route, useHistory, useLocation } from 'react-router-dom'; +import { Switch, Route, useHistory, useLocation, Redirect } from 'react-router-dom'; import { Wallet } from '@lace/cardano'; import { WalletSetupLayout } from '@src/views/browser-view/components/Layout'; import { ErrorDialog, HWErrorCode } from './ErrorDialog'; @@ -35,7 +33,7 @@ export interface HardwareWalletFlowProps { sendAnalytics: SendOnboardingAnalyticsEvent; } -type HardwareWalletStep = 'legal' | 'analytics' | 'connect' | 'setup' | 'create' | 'finish'; +type HardwareWalletStep = 'connect' | 'setup' | 'create' | 'finish'; const TOTAL_ACCOUNTS = 50; @@ -49,7 +47,6 @@ export const HardwareWalletFlow = ({ const history = useHistory(); const location = useLocation(); const { t } = useTranslation(); - const [isAnalyticsAccepted, setIsAnalyticsAccepted] = useState(false); const [isErrorDialogVisible, setIsErrorDialogVisible] = useState(false); const [hardwareWalletErrorCode, setHardwareWalletErrorCode] = useState('common'); const [isStartOverDialogVisible, setIsStartOverDialogVisible] = useState(false); @@ -72,24 +69,6 @@ export const HardwareWalletFlow = ({ setIsErrorDialogVisible(true); }; - const walletSetupLegalStepTranslations = { - title: t('core.walletSetupLegalStep.title'), - toolTipText: t('core.walletSetupLegalStep.toolTipText') - }; - - const walletSetupAnalyticsStepTranslations = { - back: t('core.walletSetupAnalyticsStep.back'), - agree: t('core.walletSetupAnalyticsStep.agree'), - title: t('core.walletSetupAnalyticsStep.title'), - description: t('core.walletSetupAnalyticsStep.description'), - optionsTitle: t('core.walletSetupAnalyticsStep.optionsTitle'), - allowOptout: t('core.walletSetupAnalyticsStep.allowOptout'), - privacyPolicy: t('core.walletSetupAnalyticsStep.privacyPolicy'), - collectPrivateKeys: t('core.walletSetupAnalyticsStep.collectPrivateKeys'), - collectIp: t('core.walletSetupAnalyticsStep.collectIp'), - personalData: t('core.walletSetupAnalyticsStep.personalData') - }; - const walletSetupConnectHardwareWalletStepTranslations = { title: t('core.walletSetupConnectHardwareWalletStep.title'), subTitle: t(`core.walletSetupConnectHardwareWalletStep.${isTrezorHWSupported() ? 'subTitleFull' : 'subTitle'}`), @@ -122,25 +101,11 @@ export const HardwareWalletFlow = ({ [history] ); - const [, { updateLocalStorage: setDoesUserAllowAnalytics }] = useLocalStorage( + const [enhancedAnalyticsStatus] = useLocalStorage( ENHANCED_ANALYTICS_OPT_IN_STATUS_LS_KEY, EnhancedAnalyticsOptInStatus.OptedOut ); - const handleAnalyticsChoice = (isAccepted: boolean) => { - setIsAnalyticsAccepted(isAccepted); - analytics.setOptedInForEnhancedAnalytics( - isAccepted ? EnhancedAnalyticsOptInStatus.OptedIn : EnhancedAnalyticsOptInStatus.OptedOut - ); - - const postHogAction = isAccepted - ? postHogOnboardingActions.hw.ANALYTICS_AGREE_CLICK - : postHogOnboardingActions.hw.ANALYTICS_SKIP_CLICK; - - sendAnalytics(postHogAction); - navigateTo('connect'); - }; - const handleCreateWallet = async (name: string) => { try { setStayOnAllDonePage(true); @@ -151,11 +116,6 @@ export const HardwareWalletFlow = ({ connectedDevice }); setWalletCreated(cardanoWallet); - const analyticsOptInStatus = isAnalyticsAccepted - ? EnhancedAnalyticsOptInStatus.OptedIn - : EnhancedAnalyticsOptInStatus.OptedOut; - setDoesUserAllowAnalytics(analyticsOptInStatus); - await analytics.setOptedInForEnhancedAnalytics(analyticsOptInStatus); navigateTo('finish'); } catch (error) { console.error('ERROR creating hardware wallet', { error }); @@ -189,7 +149,7 @@ export const HardwareWalletFlow = ({ console.error('We were not able to send the analytics event'); } finally { await handleFinishCreation(); - if (isAnalyticsAccepted) { + if (enhancedAnalyticsStatus === EnhancedAnalyticsOptInStatus.OptedIn) { await analytics.sendAliasEvent(); } // Workaround to enable staking with Ledger right after the onboarding LW-5564 @@ -209,30 +169,10 @@ export const HardwareWalletFlow = ({ }, [onHardwareWalletDisconnect]); const hardwareWalletStepRenderFunctions: Record JSX.Element> = { - legal: () => ( - onCancel()} - onNext={() => { - sendAnalytics(postHogOnboardingActions.hw.LACE_TERMS_OF_USE_NEXT_CLICK); - navigateTo('analytics'); - }} - translations={walletSetupLegalStepTranslations} - isHardwareWallet - /> - ), - analytics: () => ( - handleAnalyticsChoice(false)} - onAccept={() => handleAnalyticsChoice(true)} - onBack={() => navigateTo('legal')} - translations={walletSetupAnalyticsStepTranslations} - isHardwareWallet - /> - ), connect: () => ( navigateTo('analytics')} + onBack={onCancel} onConnect={handleConnect} onNext={() => { analytics.sendEventToPostHog(postHogOnboardingActions.hw.CONNECT_HW_NEXT_CLICK); @@ -273,7 +213,6 @@ export const HardwareWalletFlow = ({ setConnectedDevice(undefined); setAccountIndex(0); setWalletCreated(undefined); - /* eslint-enable unicorn/no-useless-undefined */ history.replace(route('connect')); }; @@ -301,12 +240,11 @@ export const HardwareWalletFlow = ({ /> - {hardwareWalletStepRenderFunctions.analytics()} {hardwareWalletStepRenderFunctions.connect()} {hardwareWalletStepRenderFunctions.setup()} {hardwareWalletStepRenderFunctions.create()} {hardwareWalletStepRenderFunctions.finish()} - {hardwareWalletStepRenderFunctions.legal()} + diff --git a/apps/browser-extension-wallet/src/views/browser-view/features/wallet-setup/components/WalletSetup.module.scss b/apps/browser-extension-wallet/src/views/browser-view/features/wallet-setup/components/WalletSetup.module.scss index 1972a066d..98fe65a72 100644 --- a/apps/browser-extension-wallet/src/views/browser-view/features/wallet-setup/components/WalletSetup.module.scss +++ b/apps/browser-extension-wallet/src/views/browser-view/features/wallet-setup/components/WalletSetup.module.scss @@ -36,3 +36,13 @@ color: var(--text-color-primary, #3d3b39) !important; } } + +.learnMore { + text-decoration: underline; + cursor: pointer; + margin-left: size_unit(0.5); +} + +.analyticsModalTitle { + text-align: start; +} diff --git a/apps/browser-extension-wallet/src/views/browser-view/features/wallet-setup/components/WalletSetup.tsx b/apps/browser-extension-wallet/src/views/browser-view/features/wallet-setup/components/WalletSetup.tsx index d83107573..f447b4850 100644 --- a/apps/browser-extension-wallet/src/views/browser-view/features/wallet-setup/components/WalletSetup.tsx +++ b/apps/browser-extension-wallet/src/views/browser-view/features/wallet-setup/components/WalletSetup.tsx @@ -1,29 +1,19 @@ -import { - useTranslate, - WalletSetupOptionsStep, - WalletSetupSteps, - WalletSetupFlowProvider, - WalletSetupFlow -} from '@lace/core'; +import { WalletSetupSteps, WalletSetupFlowProvider, WalletSetupFlow } from '@lace/core'; import { useAnalyticsContext } from '@providers/AnalyticsProvider'; -import { - PostHogAction, - postHogOnboardingActions, - PostHogProperties -} from '@providers/AnalyticsProvider/analyticsTracker'; import { walletRoutePaths } from '@routes/wallet-paths'; import { ILocalStorage } from '@src/types'; import { deleteFromLocalStorage, getValueFromLocalStorage } from '@src/utils/local-storage'; -import { WalletSetupLayout } from '@src/views/browser-view/components/Layout'; -import { WarningModal } from '@src/views/browser-view/components/WarningModal'; -import React, { useCallback, useEffect, useState } from 'react'; -import { Route, Switch, useHistory, useRouteMatch } from 'react-router-dom'; +import React, { useCallback, useEffect } from 'react'; +import { Redirect, Route, Switch, useHistory, useRouteMatch } from 'react-router-dom'; import { HardwareWalletFlow } from './HardwareWalletFlow'; import { Portal } from './Portal'; import { SendOnboardingAnalyticsEvent, SetupType } from '../types'; -import styles from './WalletSetup.module.scss'; import { WalletSetupWizard } from './WalletSetupWizard'; import { getUserIdService } from '@providers/AnalyticsProvider/getUserIdService'; +import { ENHANCED_ANALYTICS_OPT_IN_STATUS_LS_KEY } from '@providers/AnalyticsProvider/config'; +import { WalletSetupMainPage } from './WalletSetupMainPage'; +import { useLocalStorage } from '@hooks'; +import { EnhancedAnalyticsOptInStatus } from '@providers/AnalyticsProvider/analyticsTracker'; const userIdService = getUserIdService(); // This initial step is needed for configure the step that we want to snapshot @@ -31,34 +21,15 @@ export interface WalletSetupProps { initialStep?: WalletSetupSteps; } -export const WalletSetup = ({ initialStep = WalletSetupSteps.Legal }: WalletSetupProps): React.ReactElement => { +export const WalletSetup = ({ initialStep = WalletSetupSteps.Register }: WalletSetupProps): React.ReactElement => { const history = useHistory(); const { path } = useRouteMatch(); - const [isConfirmRestoreOpen, setIsConfirmRestoreOpen] = useState(false); - const [isDappConnectorWarningOpen, setIsDappConnectorWarningOpen] = useState(false); - const isForgotPasswordFlow = getValueFromLocalStorage('isForgotPasswordFlow'); - const { t: translate, Trans } = useTranslate(); const analytics = useAnalyticsContext(); - - const walletSetupOptionsStepTranslations = { - title: translate('core.walletSetupOptionsStep.title'), - subTitle: translate('core.walletSetupOptionsStep.subTitle'), - newWallet: { - title: translate('core.walletSetupOptionsStep.newWallet.title'), - description: translate('core.walletSetupOptionsStep.newWallet.description'), - button: translate('core.walletSetupOptionsStep.newWallet.button') - }, - hardwareWallet: { - title: translate('core.walletSetupOptionsStep.hardwareWallet.title'), - description: translate('core.walletSetupOptionsStep.hardwareWallet.description'), - button: translate('core.walletSetupOptionsStep.hardwareWallet.button') - }, - restoreWallet: { - title: translate('core.walletSetupOptionsStep.restoreWallet.title'), - description: translate('core.walletSetupOptionsStep.restoreWallet.description'), - button: translate('core.walletSetupOptionsStep.restoreWallet.button') - } - }; + const isForgotPasswordFlow = getValueFromLocalStorage('isForgotPasswordFlow'); + const [enhancedAnalyticsStatus] = useLocalStorage( + ENHANCED_ANALYTICS_OPT_IN_STATUS_LS_KEY, + EnhancedAnalyticsOptInStatus.NotSet + ); useEffect(() => { const handleEnterKeyPress = (event: KeyboardEvent) => { @@ -89,7 +60,7 @@ export const WalletSetup = ({ initialStep = WalletSetupSteps.Legal }: WalletSetu const clearWallet = useCallback(() => { deleteFromLocalStorage('wallet'); - deleteFromLocalStorage('analyticsAccepted'); + deleteFromLocalStorage(ENHANCED_ANALYTICS_OPT_IN_STATUS_LS_KEY); deleteFromLocalStorage('isForgotPasswordFlow'); }, []); @@ -105,116 +76,45 @@ export const WalletSetup = ({ initialStep = WalletSetupSteps.Legal }: WalletSetu const cancelWalletFlow = () => history.push(walletRoutePaths.setup.home); - const handleStartHardwareOnboarding = () => { - setIsDappConnectorWarningOpen(true); - analytics.sendEventToPostHog(postHogOnboardingActions.hw?.SETUP_OPTION_CLICK); - }; - - const sendAnalytics = async (args: { postHogAction: PostHogAction; postHogProperties?: PostHogProperties }) => { - await analytics.sendEventToPostHog(args.postHogAction, args?.postHogProperties); - }; - const sendAnalyticsHandler: SendOnboardingAnalyticsEvent = async (postHogAction, postHogProperties) => - await sendAnalytics({ postHogAction, postHogProperties }); - - const handleRestoreWallet = () => { - setIsConfirmRestoreOpen(true); - analytics.sendEventToPostHog(postHogOnboardingActions.restore?.SETUP_OPTION_CLICK); - }; - - const handleCreateNewWallet = () => { - sendAnalytics({ - postHogAction: postHogOnboardingActions.create.SETUP_OPTION_CLICK - }); - history.push(walletRoutePaths.setup.create); - }; - - const handleCancelRestoreWarning = () => { - setIsConfirmRestoreOpen(false); - analytics.sendEventToPostHog(postHogOnboardingActions.restore?.RESTORE_MULTI_ADDR_CANCEL_CLICK); - }; - - const handleConfirmRestoreWarning = () => { - setIsConfirmRestoreOpen(false); - sendAnalytics({ - postHogAction: postHogOnboardingActions.create.RESTORE_MULTI_ADDR_OK_CLICK - }); - history.push(walletRoutePaths.setup.restore); - }; + await analytics.sendEventToPostHog(postHogAction, postHogProperties); return ( - - - -

- - }} - i18nKey="browserView.walletSetup.confirmRestoreModal.content" - /> -

- - } - visible={isConfirmRestoreOpen} - confirmLabel={translate('browserView.walletSetup.confirmRestoreModal.confirm')} - onCancel={handleCancelRestoreWarning} - onConfirm={handleConfirmRestoreWarning} - /> - -

- -

- - } - visible={isDappConnectorWarningOpen} - confirmLabel={translate('browserView.walletSetup.confirmExperimentalHwDapp.confirm')} - onCancel={() => setIsDappConnectorWarningOpen(false)} - onConfirm={() => { - setIsDappConnectorWarningOpen(false); - history.push(walletRoutePaths.setup.hardware); - }} - /> -
-
- - - - - - - - location.reload()} - sendAnalytics={sendAnalyticsHandler} - /> + + {enhancedAnalyticsStatus === EnhancedAnalyticsOptInStatus.NotSet ? ( + + ) : ( + <> + + + + + + + + location.reload()} + sendAnalytics={sendAnalyticsHandler} + /> + + + )}
diff --git a/apps/browser-extension-wallet/src/views/browser-view/features/wallet-setup/components/WalletSetupMainPage.tsx b/apps/browser-extension-wallet/src/views/browser-view/features/wallet-setup/components/WalletSetupMainPage.tsx new file mode 100644 index 000000000..49e7545fd --- /dev/null +++ b/apps/browser-extension-wallet/src/views/browser-view/features/wallet-setup/components/WalletSetupMainPage.tsx @@ -0,0 +1,165 @@ +import React, { ReactElement, useState } from 'react'; +import { WalletSetupLayout, WarningModal } from '@views/browser/components'; +import { + AnalyticsConfirmationBanner, + useTranslate, + WalletAnalyticsInfo, + WalletSetupOptionsStepRevamp +} from '@lace/core'; +import styles from '@views/browser/features/wallet-setup/components/WalletSetup.module.scss'; +import { walletRoutePaths } from '@routes'; +import { + EnhancedAnalyticsOptInStatus, + PostHogAction, + postHogOnboardingActions, + PostHogProperties +} from '@providers/AnalyticsProvider/analyticsTracker'; +import { useAnalyticsContext } from '@providers'; +import { useLocalStorage } from '@hooks'; +import { ENHANCED_ANALYTICS_OPT_IN_STATUS_LS_KEY } from '@providers/AnalyticsProvider/config'; +import { useHistory } from 'react-router-dom'; + +export const WalletSetupMainPage = (): ReactElement => { + const history = useHistory(); + const [isConfirmRestoreOpen, setIsConfirmRestoreOpen] = useState(false); + const [isDappConnectorWarningOpen, setIsDappConnectorWarningOpen] = useState(false); + const [isAnalyticsModalOpen, setIsAnalyticsModalOpen] = useState(false); + const { t: translate, Trans } = useTranslate(); + + const analytics = useAnalyticsContext(); + const [enhancedAnalyticsStatus, { updateLocalStorage: setDoesUserAllowAnalytics }] = useLocalStorage( + ENHANCED_ANALYTICS_OPT_IN_STATUS_LS_KEY, + EnhancedAnalyticsOptInStatus.NotSet + ); + + const walletSetupOptionsStepTranslations = { + title: translate('core.walletSetupOptionsStep.title'), + subTitle: translate('core.walletSetupOptionsStep.subTitle'), + newWallet: { + title: translate('core.walletSetupOptionsStep.newWallet.title'), + description: translate('core.walletSetupOptionsStep.newWallet.description'), + button: translate('core.walletSetupOptionsStep.newWallet.button') + }, + hardwareWallet: { + title: translate('core.walletSetupOptionsStep.hardwareWallet.title'), + description: translate('core.walletSetupOptionsStep.hardwareWallet.description'), + button: translate('core.walletSetupOptionsStep.hardwareWallet.button') + }, + restoreWallet: { + title: translate('core.walletSetupOptionsStep.restoreWallet.title'), + description: translate('core.walletSetupOptionsStep.restoreWallet.description'), + button: translate('core.walletSetupOptionsStep.restoreWallet.button') + } + }; + + const handleStartHardwareOnboarding = () => { + setIsDappConnectorWarningOpen(true); + analytics.sendEventToPostHog(postHogOnboardingActions.hw?.SETUP_OPTION_CLICK); + }; + + const sendAnalytics = async (args: { postHogAction: PostHogAction; postHogProperties?: PostHogProperties }) => { + await analytics.sendEventToPostHog(args.postHogAction, args?.postHogProperties); + }; + + const handleAnalyticsChoice = async (isAccepted: boolean) => { + const analyticsStatus = isAccepted ? EnhancedAnalyticsOptInStatus.OptedIn : EnhancedAnalyticsOptInStatus.OptedOut; + setDoesUserAllowAnalytics(analyticsStatus); + + // TODO: https://input-output.atlassian.net/browse/LW-9761 send proper analytics + // The code removed here was sending analytics to PostHog and it's still useful. You can find it in git history of this file. + }; + + const handleRestoreWallet = () => { + setIsConfirmRestoreOpen(true); + analytics.sendEventToPostHog(postHogOnboardingActions.restore?.SETUP_OPTION_CLICK); + }; + + const handleCreateNewWallet = () => { + sendAnalytics({ + postHogAction: postHogOnboardingActions.create.SETUP_OPTION_CLICK + }); + history.push(walletRoutePaths.setup.create); + }; + + const handleCancelRestoreWarning = () => { + setIsConfirmRestoreOpen(false); + analytics.sendEventToPostHog(postHogOnboardingActions.restore?.RESTORE_MULTI_ADDR_CANCEL_CLICK); + }; + + const handleConfirmRestoreWarning = () => { + setIsConfirmRestoreOpen(false); + sendAnalytics({ + postHogAction: postHogOnboardingActions.create.RESTORE_MULTI_ADDR_OK_CLICK + }); + history.push(walletRoutePaths.setup.restore); + }; + + return ( + <> + + + +

+ + }} + i18nKey="browserView.walletSetup.confirmRestoreModal.content" + /> +

+ + } + visible={isConfirmRestoreOpen} + confirmLabel={translate('browserView.walletSetup.confirmRestoreModal.confirm')} + onCancel={handleCancelRestoreWarning} + onConfirm={handleConfirmRestoreWarning} + /> + +

+ +

+ + } + visible={isDappConnectorWarningOpen} + confirmLabel={translate('browserView.walletSetup.confirmExperimentalHwDapp.confirm')} + onCancel={() => setIsDappConnectorWarningOpen(false)} + onConfirm={() => { + setIsDappConnectorWarningOpen(false); + history.push(walletRoutePaths.setup.hardware); + }} + /> +
+ + {translate('analyticsConfirmationBanner.message')} + setIsAnalyticsModalOpen(true)}> + {translate('analyticsConfirmationBanner.learnMore')} + + + } + onConfirm={() => handleAnalyticsChoice(true)} + onReject={() => handleAnalyticsChoice(false)} + show={enhancedAnalyticsStatus === EnhancedAnalyticsOptInStatus.NotSet} + /> + {translate('core.walletAnalyticsInfo.title')}} + content={} + visible={isAnalyticsModalOpen} + confirmLabel={translate('core.walletAnalyticsInfo.gotIt')} + onConfirm={() => setIsAnalyticsModalOpen(false)} + /> + + ); +}; diff --git a/apps/browser-extension-wallet/src/views/browser-view/features/wallet-setup/components/WalletSetupWizard.tsx b/apps/browser-extension-wallet/src/views/browser-view/features/wallet-setup/components/WalletSetupWizard.tsx index 397a7b839..bdb3c6136 100644 --- a/apps/browser-extension-wallet/src/views/browser-view/features/wallet-setup/components/WalletSetupWizard.tsx +++ b/apps/browser-extension-wallet/src/views/browser-view/features/wallet-setup/components/WalletSetupWizard.tsx @@ -5,10 +5,8 @@ import { wordlists } from 'bip39'; import { useLocalStorage, useTimeSpentOnPage, useWalletManager } from '@hooks'; import { MnemonicStage, - WalletSetupAnalyticsStep, WalletSetupCreationStep, WalletSetupFinalStep, - WalletSetupLegalStep, WalletSetupMnemonicIntroStep, WalletSetupNamePasswordStep, WalletSetupPasswordStep, @@ -23,8 +21,7 @@ import { WarningModal } from '@src/views/browser-view/components/WarningModal'; import { EnhancedAnalyticsOptInStatus, PostHogAction, - postHogOnboardingActions, - UserTrackingType + postHogOnboardingActions } from '@providers/AnalyticsProvider/analyticsTracker'; import { config } from '@src/config'; @@ -42,6 +39,7 @@ import { CombinedSetupNamePasswordVariants, ExperimentName } from '@providers/Ex import { isScriptAddress } from '@cardano-sdk/wallet'; import { filter, firstValueFrom } from 'rxjs'; import { useWalletStore } from '@src/stores'; +// import { walletSetupWizardRevamp } from '@lace/core/dist/ui/components/WalletSetupRevamp/wallet-steps-revamp'; const isCombinedPasswordNameStepEnabled = process.env.USE_COMBINED_PASSWORD_NAME_STEP_COMPONENT === 'true'; const walletSetupWizardForABTest = { @@ -87,7 +85,7 @@ export const WalletSetupWizard = ({ onCancel, setupType, sendAnalytics, - initialStep = WalletSetupSteps.Legal + initialStep = WalletSetupSteps.Register }: WalletSetupWizardProps): React.ReactElement => { const [currentStep, setCurrentStep] = useState( setupType === SetupType.FORGOT_PASSWORD ? WalletSetupSteps.Password : initialStep @@ -95,7 +93,7 @@ export const WalletSetupWizard = ({ const [walletName, setWalletName] = useState(getValueFromLocalStorage('wallet')?.name); const [password, setPassword] = useState(''); const [walletInstance, setWalletInstance] = useState(); - const [isAnalyticsAccepted, setIsAnalyticsAccepted] = useState(false); + const [mnemonicLength, setMnemonicLength] = useState(DEFAULT_MNEMONIC_LENGTH); const [mnemonic, setMnemonic] = useState([]); const [walletIsCreating, setWalletIsCreating] = useState(false); @@ -108,10 +106,15 @@ export const WalletSetupWizard = ({ const { setStayOnAllDonePage } = useWalletStore(); const analytics = useAnalyticsContext(); const { t } = useTranslation(); + const [enhancedAnalyticsStatus] = useLocalStorage( + ENHANCED_ANALYTICS_OPT_IN_STATUS_LS_KEY, + EnhancedAnalyticsOptInStatus.OptedOut + ); const { updateEnteredAtTime } = useTimeSpentOnPage(); const useDifferentMnemonicLengths = process.env.USE_DIFFERENT_MNEMONIC_LENGTHS === 'true'; + const isAnalyticsAccepted = enhancedAnalyticsStatus === EnhancedAnalyticsOptInStatus.OptedIn; useEffect(() => { updateEnteredAtTime(); @@ -125,24 +128,6 @@ export const WalletSetupWizard = ({ ); }, [mnemonicLength, setupType]); - const walletSetupLegalStepTranslations = { - title: t('core.walletSetupLegalStep.title'), - toolTipText: t('core.walletSetupLegalStep.toolTipText') - }; - - const walletSetupAnalyticsStepTranslations = { - back: t('core.walletSetupAnalyticsStep.back'), - agree: t('core.walletSetupAnalyticsStep.agree'), - title: t('core.walletSetupAnalyticsStep.title'), - description: t('core.walletSetupAnalyticsStep.description'), - optionsTitle: t('core.walletSetupAnalyticsStep.optionsTitle'), - privacyPolicy: t('core.walletSetupAnalyticsStep.privacyPolicy'), - allowOptout: t('core.walletSetupAnalyticsStep.allowOptout'), - collectPrivateKeys: t('core.walletSetupAnalyticsStep.collectPrivateKeys'), - collectIp: t('core.walletSetupAnalyticsStep.collectIp'), - personalData: t('core.walletSetupAnalyticsStep.personalData') - }; - const walletSetupMnemonicStepTranslations = { writePassphrase: t('core.walletSetupMnemonicStep.writePassphrase'), body: t('core.walletSetupMnemonicStep.body'), @@ -242,29 +227,6 @@ export const WalletSetupWizard = ({ setCurrentStep(walletStep); }; - const [, { updateLocalStorage: setDoesUserAllowAnalytics }] = useLocalStorage( - ENHANCED_ANALYTICS_OPT_IN_STATUS_LS_KEY, - EnhancedAnalyticsOptInStatus.OptedOut - ); - - const handleAnalyticsChoice = async (isAccepted: boolean) => { - setIsAnalyticsAccepted(isAccepted); - await analytics.setOptedInForEnhancedAnalytics( - isAccepted ? EnhancedAnalyticsOptInStatus.OptedIn : EnhancedAnalyticsOptInStatus.OptedOut - ); - - const postHogAnalyticsAgreeAction = postHogOnboardingActions[setupType]?.ANALYTICS_AGREE_CLICK; - const postHogAnalyticcSkipAction = postHogOnboardingActions[setupType]?.ANALYTICS_SKIP_CLICK; - - const postHogAction = isAccepted ? postHogAnalyticsAgreeAction : postHogAnalyticcSkipAction; - const postHogProperties = { - // eslint-disable-next-line camelcase - $set: { user_tracking_type: isAccepted ? UserTrackingType.Enhanced : UserTrackingType.Basic } - }; - await sendAnalytics(postHogAction, postHogProperties); - moveForward(); - }; - const goToMyWallet = useCallback( async (cardanoWallet: Wallet.CardanoWallet = walletInstance) => { setStayOnAllDonePage(false); @@ -290,12 +252,6 @@ export const WalletSetupWizard = ({ chainId: DEFAULT_CHAIN_ID }); setWalletInstance(wallet); - setDoesUserAllowAnalytics( - isAnalyticsAccepted ? EnhancedAnalyticsOptInStatus.OptedIn : EnhancedAnalyticsOptInStatus.OptedOut - ); - await analytics.setOptedInForEnhancedAnalytics( - isAnalyticsAccepted ? EnhancedAnalyticsOptInStatus.OptedIn : EnhancedAnalyticsOptInStatus.OptedOut - ); wallet.wallet.addresses$.subscribe((addresses) => { if (addresses.length === 0) return; @@ -321,8 +277,6 @@ export const WalletSetupWizard = ({ walletName, mnemonic, password, - setDoesUserAllowAnalytics, - isAnalyticsAccepted, analytics, setupType, goToMyWallet, @@ -424,7 +378,6 @@ export const WalletSetupWizard = ({ ? sendAnalytics(postHogOnboardingActions[setupType]?.ENTER_PASSPHRASE_17_NEXT_CLICK) : sendAnalytics(postHogOnboardingActions[setupType]?.WRITE_PASSPHRASE_17_NEXT_CLICK); } - /* eslint-enable no-magic-numbers */ }} translations={walletSetupMnemonicStepTranslations} suggestionList={wordList} @@ -449,24 +402,6 @@ export const WalletSetupWizard = ({ return ( - {currentStep === WalletSetupSteps.Legal && ( - { - sendAnalytics(postHogOnboardingActions[setupType]?.LACE_TERMS_OF_USE_NEXT_CLICK); - moveForward(); - }} - translations={walletSetupLegalStepTranslations} - /> - )} - {currentStep === WalletSetupSteps.Analytics && ( - handleAnalyticsChoice(false)} - onAccept={() => handleAnalyticsChoice(true)} - onBack={moveBack} - translations={walletSetupAnalyticsStepTranslations} - /> - )} {currentStep === WalletSetupSteps.PreMnemonic && ( ({ - ...jest.requireActual('@stores'), - useWalletStore: jest.fn().mockReturnValue({}) -})); - -jest.mock('@providers/AnalyticsProvider/getUserIdService', () => ({ - ...jest.requireActual('@providers/AnalyticsProvider/getUserIdService'), - getUserIdService: jest.fn().mockReturnValue(userIdServiceMock) -})); - -jest.mock('@hooks', () => ({ - ...jest.requireActual('@hooks'), - useWalletManager: jest.fn().mockReturnValue({}) -})); - -jest.mock('react-router-dom', () => ({ - // eslint-disable-next-line @typescript-eslint/no-explicit-any - ...jest.requireActual('react-router-dom'), - useRouteMatch: jest.fn().mockReturnValue({ path: '/setup' }) -})); - -jest.mock('@providers/ExperimentsProvider', () => ({ - // eslint-disable-next-line @typescript-eslint/no-explicit-any - ...jest.requireActual('@providers/ExperimentsProvider'), - useExperimentsContext: jest - .fn() - .mockReturnValue({ getExperimentVariant: jest.fn(), overrideExperimentVariant: jest.fn() }) -})); - -jest.mock('@providers/PostHogClientProvider', () => ({ - // eslint-disable-next-line @typescript-eslint/no-explicit-any - ...jest.requireActual('@providers/PostHogClientProvider'), - usePostHogClientContext: () => postHogClientMocks -})); - -const SetupContainerTest = () => ( - - - - - - - - - - - -); - -describe('Testing Analytics Agreement step', () => { - beforeEach(() => { - jest.clearAllMocks(); - }); - - test('should call send event for posthog', async () => { - const { findByTestId } = render(); - const nextAnalyticsAccept = await findByTestId('wallet-setup-step-btn-next'); - fireEvent.click(nextAnalyticsAccept); - - await waitFor(() => expect(postHogClientMocks.sendEvent).toHaveBeenCalledTimes(1)); - await waitFor(() => expect(postHogClientMocks.sendPageNavigationEvent).toHaveBeenCalledTimes(1)); - await waitFor(() => expect(userIdServiceMock.extendLifespan).toHaveBeenCalledTimes(2)); - }); - - test('should call makePersistent when clicking agree', async () => { - const { findByTestId } = render(); - - // since AnalyticsProvider already made a call to setOptedInForEnhancedAnalytics on render, we need to clear the mocks to make the proper test - userIdServiceMock.makePersistent.mockReset(); - userIdServiceMock.makeTemporary.mockReset(); - - const agreeAnalyticsBtn = await findByTestId('wallet-setup-step-btn-next'); - fireEvent.click(agreeAnalyticsBtn); - - await waitFor(() => expect(userIdServiceMock.makePersistent).toHaveBeenCalled()); - await waitFor(() => expect(userIdServiceMock.makeTemporary).not.toHaveBeenCalled()); - }); - - test('should call makeTemporary when clicking skip', async () => { - const { findByTestId } = render(); - - userIdServiceMock.makePersistent.mockReset(); - userIdServiceMock.makeTemporary.mockReset(); - - const skipAnalyticsBtn = await findByTestId('wallet-setup-step-btn-skip'); - fireEvent.click(skipAnalyticsBtn); - - await waitFor(() => expect(userIdServiceMock.makePersistent).not.toHaveBeenCalled()); - await waitFor(() => expect(userIdServiceMock.makeTemporary).toHaveBeenCalledTimes(1)); - }); -}); diff --git a/packages/common/src/analytics/types.ts b/packages/common/src/analytics/types.ts index ac17cb584..8b255cb64 100644 --- a/packages/common/src/analytics/types.ts +++ b/packages/common/src/analytics/types.ts @@ -1,4 +1,8 @@ export enum PostHogAction { + // Landing page + // todo: These landing analytics events have not been implemented, the would be implemented on LW-9761 + LandingAnalyticsAgreeClick = 'landing | agree | click', + LandingAnalyticsRejectClick = 'landing | reject | click', // Hardware wallet connect OnboardingHWAnalyticsAgreeClick = 'onboarding | hardware wallet | analytics | agree | click', OnboardingHWAnalyticsSkipClick = 'onboarding | hardware wallet | analytics | skip | click', diff --git a/packages/core/src/ui/assets/icons/onboarding/hardware-wallet.component.svg b/packages/core/src/ui/assets/icons/onboarding/hardware-wallet.component.svg index 6f983361d..8005b3b64 100644 --- a/packages/core/src/ui/assets/icons/onboarding/hardware-wallet.component.svg +++ b/packages/core/src/ui/assets/icons/onboarding/hardware-wallet.component.svg @@ -1,9 +1,19 @@ - - - - - - - - + + + + + + + + + + + + + + + + + + diff --git a/packages/core/src/ui/components/WalletSetup/AnalyticsConfirmationBanner.module.scss b/packages/core/src/ui/components/WalletSetup/AnalyticsConfirmationBanner.module.scss new file mode 100644 index 000000000..0a06fa8ff --- /dev/null +++ b/packages/core/src/ui/components/WalletSetup/AnalyticsConfirmationBanner.module.scss @@ -0,0 +1,43 @@ +@import '../../../../../common/src/ui/styles/abstracts/typography'; + +.confirmationBanner { + position: fixed; + padding: 0 size_unit(2); + bottom: 0; + left: 0; + width: 100%; + height: 100px; + background: var(--primary-default, #7E5BF0); + display: flex; + justify-content: space-between; + align-items: center; + z-index: 100; +} + +.overlay { + position: fixed; + top: 0; + left: 0; + width: 100%; + height: 100%; + background: rgba(0, 0, 0, 0.5); + z-index: 99; +} + +.confirmationBannerMessage { + @include text-body-bold; + color: var(--text-color-white, #ffffff); +} + +.buttons { + display: flex; + gap: size_unit(1); +} + +.secondaryButton { + background: var(--text-color-white, #ffffff) !important; + color:var(--primary-default, #7f5af0) !important; + &:hover { + color: #3D3B39 !important; + } +} diff --git a/packages/core/src/ui/components/WalletSetup/AnalyticsConfirmationBanner.tsx b/packages/core/src/ui/components/WalletSetup/AnalyticsConfirmationBanner.tsx new file mode 100644 index 000000000..16dee63a5 --- /dev/null +++ b/packages/core/src/ui/components/WalletSetup/AnalyticsConfirmationBanner.tsx @@ -0,0 +1,51 @@ +import React, { ReactPortal, useState } from 'react'; +import { createPortal } from 'react-dom'; +import styles from './AnalyticsConfirmationBanner.module.scss'; +import { useTranslate } from '@ui/hooks'; +import { Button } from '@lace/common'; + +type ConfirmationBannerProps = { + message: string | React.ReactElement; + onConfirm: () => void; + onReject: () => void; + show?: boolean; +}; + +export const AnalyticsConfirmationBanner = ({ + message, + onConfirm, + onReject, + show = true +}: ConfirmationBannerProps): ReactPortal | null => { + const [isVisible, setIsVisible] = useState(show); + const { t } = useTranslate(); + + const handleConfirm = () => { + setIsVisible(false); + onConfirm(); + }; + + const handleReject = () => { + setIsVisible(false); + onReject(); + }; + + return isVisible + ? createPortal( + <> +
+
+
{message}
+
+ + +
+
+ , + document.body + ) + : // eslint-disable-next-line unicorn/no-null + null; +}; diff --git a/packages/core/src/ui/components/WalletSetup/LegalTranslations.tsx b/packages/core/src/ui/components/WalletSetup/LegalTranslations.tsx new file mode 100644 index 000000000..30295cd64 --- /dev/null +++ b/packages/core/src/ui/components/WalletSetup/LegalTranslations.tsx @@ -0,0 +1,42 @@ +import React from 'react'; +import { useTranslate } from '@ui/hooks'; + +export const LegalTranslations = (): React.ReactElement => { + const { Trans } = useTranslate(); + return ( + , + strong: , + i: , + b: , + div:
, + u: , + uunderline: , + a: , + privacyPolicy: ( + + ), + iogdmcapolicy: ( + + ), + rulesstreamlinedarbitration: , + rulescomprehensivearbitration: ( + + ), + jamsadr: , + contactform: + }} + /> + ); +}; diff --git a/packages/core/src/ui/components/WalletSetup/WalletAnalyticsInfo.module.scss b/packages/core/src/ui/components/WalletSetup/WalletAnalyticsInfo.module.scss new file mode 100644 index 000000000..2076e7d5e --- /dev/null +++ b/packages/core/src/ui/components/WalletSetup/WalletAnalyticsInfo.module.scss @@ -0,0 +1,19 @@ +@import '../../styles/theme.scss'; + +.container { + text-align: start; +} + +.description { + margin-bottom: size_unit(2); +} + +.options { + display: flex; + flex-direction: column; + gap: size_unit(2); + .flex { + display: flex; + gap: size_unit(1); + } +} diff --git a/packages/core/src/ui/components/WalletSetup/WalletAnalyticsInfo.tsx b/packages/core/src/ui/components/WalletSetup/WalletAnalyticsInfo.tsx new file mode 100644 index 000000000..7aa90a2eb --- /dev/null +++ b/packages/core/src/ui/components/WalletSetup/WalletAnalyticsInfo.tsx @@ -0,0 +1,43 @@ +import React, { ReactElement } from 'react'; +import Check from '../../assets/icons/check.svg'; +import NotAllowed from '../../assets/icons/x.svg'; +import styles from './WalletAnalyticsInfo.module.scss'; +import { useTranslate } from '@ui/hooks'; + +export const WalletAnalyticsInfo = (): ReactElement => { + const { t } = useTranslate(); + const infoTexts = [ + { + icon: check, + text: t('core.walletAnalyticsInfo.allowOptout') + }, + { + icon: check, + text: t('core.walletAnalyticsInfo.collectPrivateKeys') + }, + { + icon: check, + text: t('core.walletAnalyticsInfo.collectIp') + }, + { + icon: check, + text: t('core.walletAnalyticsInfo.personalData') + } + ]; + + return ( +
+
{t('core.walletAnalyticsInfo.description')}
+
+
+ {infoTexts.map((info, index) => ( +
+
{info.icon}
+
{info.text}
+
+ ))} +
+
+
+ ); +}; diff --git a/packages/core/src/ui/components/WalletSetup/WalletSetupAnalyticsStep.module.scss b/packages/core/src/ui/components/WalletSetup/WalletSetupAnalyticsStep.module.scss deleted file mode 100644 index 1237c6f83..000000000 --- a/packages/core/src/ui/components/WalletSetup/WalletSetupAnalyticsStep.module.scss +++ /dev/null @@ -1,30 +0,0 @@ -@import '../../styles/theme.scss'; - -.options { - display: flex; - flex-direction: column; - gap: size_unit(2); - .flex { - display: flex; - gap: size_unit(1); - } - p { - font-weight: 400; - font-size: var(--body); - line-height: size_unit(3); - color: var(--text-color-primary); - } -} - -.link { - color: var(--data-blue); - cursor: pointer; -} - -.description { - font-size: var(--body) !important; - line-height: size_unit(3) !important; - color: var(--text-color-primary, #3d3b39); - margin-bottom: size_unit(4) !important; - margin-top: size_unit(0.25) !important; -} diff --git a/packages/core/src/ui/components/WalletSetup/WalletSetupAnalyticsStep.tsx b/packages/core/src/ui/components/WalletSetup/WalletSetupAnalyticsStep.tsx deleted file mode 100644 index d63d55695..000000000 --- a/packages/core/src/ui/components/WalletSetup/WalletSetupAnalyticsStep.tsx +++ /dev/null @@ -1,81 +0,0 @@ -import React from 'react'; -import { WalletSetupStepLayout, WalletTimelineSteps } from './WalletSetupStepLayout'; -import Check from '../../assets/icons/check.svg'; -import NotAllowed from '../../assets/icons/x.svg'; -import styles from './WalletSetupAnalyticsStep.module.scss'; -import { TranslationsFor } from '@ui/utils/types'; - -export interface WalletSetupAnalyticsStepProps { - onDeny: () => void; - onAccept: () => void; - onBack: () => void; - translations: TranslationsFor< - | 'back' - | 'agree' - | 'title' - | 'description' - | 'optionsTitle' - | 'privacyPolicy' - | 'allowOptout' - | 'collectPrivateKeys' - | 'collectIp' - | 'personalData' - >; - isHardwareWallet?: boolean; -} - -const PRIVACY_POLICY_URL = process.env.PRIVACY_POLICY_URL; - -export const WalletSetupAnalyticsStep = ({ - onDeny, - onAccept, - onBack, - translations, - isHardwareWallet = false -}: WalletSetupAnalyticsStepProps): React.ReactElement => ( - - <> -

- {translations.description}{' '} - - {`${translations.privacyPolicy}`} - -

-
-

{translations.optionsTitle}

-
- check -

{translations.allowOptout}

-
-
- check -

- {translations.collectPrivateKeys} -

-
-
- check -

{translations.collectIp}

-
-
- check -

{translations.personalData}

-
-
- - -); diff --git a/packages/core/src/ui/components/WalletSetup/WalletSetupLegalStep.module.scss b/packages/core/src/ui/components/WalletSetup/WalletSetupLegalStep.module.scss deleted file mode 100644 index 3856e61ea..000000000 --- a/packages/core/src/ui/components/WalletSetup/WalletSetupLegalStep.module.scss +++ /dev/null @@ -1,47 +0,0 @@ -@import '../../styles/theme.scss'; - -.walletSetupLegalStep { - display: flex; - flex-direction: column; - gap: 20px; - - .acceptTerms { - display: flex; - align-items: center; - gap: size_unit(1); - p { - font-size: var(--bodySmall); - line-height: size_unit(3); - font-weight: 400; - } - } - :global { - .ant-checkbox-checked .ant-checkbox-inner { - background-color: var(--primary-default, #7f5af0) !important; - border-color: var(--primary-default, #7f5af0) !important; - } - } - :global(.ant-checkbox-inner) { - border-radius: 4px; - background: var(--color-white, var(--bg-color-body)); - border: 1.5px solid var(--light-mode-dark-grey, #c0c0c0); - } - :global { - .ant-checkbox-wrapper:hover .ant-checkbox-inner, - .ant-checkbox:hover .ant-checkbox-inner, - .ant-checkbox-input:focus + .ant-checkbox-inner { - border-color: var(--light-mode-dark-grey, #c0c0c0); - } - .ant-checkbox-checked .ant-checkbox-inner::after { - border: 2px solid var(--color-white, var(--bg-color-body)); - border-top: 0; - border-left: 0; - } - } - p { - font-size: var(--body); - line-height: size_unit(3); - color: var(--text-color-primary); - font-weight: 300; - } -} diff --git a/packages/core/src/ui/components/WalletSetup/WalletSetupLegalStep.tsx b/packages/core/src/ui/components/WalletSetup/WalletSetupLegalStep.tsx deleted file mode 100644 index 832a0b051..000000000 --- a/packages/core/src/ui/components/WalletSetup/WalletSetupLegalStep.tsx +++ /dev/null @@ -1,88 +0,0 @@ -/* eslint-disable react/no-multi-comp */ -import React, { useState } from 'react'; -import { WalletSetupStepLayout, WalletTimelineSteps } from './WalletSetupStepLayout'; -import styles from './WalletSetupLegalStep.module.scss'; -import { Checkbox } from 'antd'; -import { TranslationsFor } from '@ui/utils/types'; -import { useTranslate } from '@src/ui/hooks'; - -export interface WalletSetupLegalStepProps { - onBack: () => void; - onNext: () => void; - translations: TranslationsFor<'title' | 'toolTipText'>; - isHardwareWallet?: boolean; -} - -export const LegalTranslations = (): React.ReactElement => { - const { Trans } = useTranslate(); - return ( - , - strong: , - i: , - b: , - div:
, - u: , - uunderline: , - a: , - privacyPolicy: ( - - ), - iogdmcapolicy: ( - - ), - rulesstreamlinedarbitration: , - rulescomprehensivearbitration: ( - - ), - jamsadr: , - contactform: - }} - /> - ); -}; - -export const WalletSetupLegalStep = ({ - onBack, - onNext, - translations, - isHardwareWallet = false -}: WalletSetupLegalStepProps): React.ReactElement => { - const [areTermsAccepted, setAreTermsAccepted] = useState(false); - - return ( - -
- -
- setAreTermsAccepted(!areTermsAccepted)} - data-testid="wallet-setup-legal-terms-checkbox" - > -

I accept the Terms of Use

-
-
-
-
- ); -}; diff --git a/packages/core/src/ui/components/WalletSetup/index.ts b/packages/core/src/ui/components/WalletSetup/index.ts index ed4f4f54e..a67bcfde6 100644 --- a/packages/core/src/ui/components/WalletSetup/index.ts +++ b/packages/core/src/ui/components/WalletSetup/index.ts @@ -1,8 +1,6 @@ export * from './WalletSetupOptionsStep'; export * from './WalletSetupStepLayout'; -export * from './WalletSetupLegalStep'; export * from './WalletSetupRegisterStep'; -export * from './WalletSetupAnalyticsStep'; export * from './WalletSetupMnemonicIntroStep'; export * from './WalletSetupMnemonicStep'; export * from './WalletSetupCreationStep'; @@ -20,3 +18,6 @@ export * from './MnemonicWordsWritedown'; export * from './WalletSetupNamePasswordStep'; export * from './WalletSetupFlowProvider'; export * from './WalletSetupConfirmationDialogProvider'; +export * from './WalletAnalyticsInfo'; +export * from './LegalTranslations'; +export * from './AnalyticsConfirmationBanner'; diff --git a/packages/core/src/ui/components/WalletSetup/wallet-steps.common.ts b/packages/core/src/ui/components/WalletSetup/wallet-steps.common.ts index b41208b11..af9c76a3c 100644 --- a/packages/core/src/ui/components/WalletSetup/wallet-steps.common.ts +++ b/packages/core/src/ui/components/WalletSetup/wallet-steps.common.ts @@ -1,6 +1,4 @@ export enum WalletSetupSteps { - Legal = 'legal', - Analytics = 'analytics', Mode = 'mode', PreMnemonic = 'pre-mnemonic', Mnemonic = 'mnemonic', diff --git a/packages/core/src/ui/components/WalletSetup/wallet-steps.ts b/packages/core/src/ui/components/WalletSetup/wallet-steps.ts index 6e1e14cd1..c0052b10c 100644 --- a/packages/core/src/ui/components/WalletSetup/wallet-steps.ts +++ b/packages/core/src/ui/components/WalletSetup/wallet-steps.ts @@ -1,15 +1,7 @@ import { WalletSetupSteps, WalletSetupWizard } from './wallet-steps.common'; export const walletSetupWizard: WalletSetupWizard = { - [WalletSetupSteps.Legal]: { - next: WalletSetupSteps.Analytics - }, - [WalletSetupSteps.Analytics]: { - prev: WalletSetupSteps.Legal, - next: WalletSetupSteps.Register - }, [WalletSetupSteps.Register]: { - prev: WalletSetupSteps.Analytics, next: WalletSetupSteps.Password }, [WalletSetupSteps.Password]: { diff --git a/packages/core/src/ui/components/WalletSetupRevamp/WalletSetupOptionsStepRevamp.module.scss b/packages/core/src/ui/components/WalletSetupRevamp/WalletSetupOptionsStepRevamp.module.scss new file mode 100644 index 000000000..e20a97550 --- /dev/null +++ b/packages/core/src/ui/components/WalletSetupRevamp/WalletSetupOptionsStepRevamp.module.scss @@ -0,0 +1,56 @@ +@import '../../styles/theme.scss'; +@import '../../../../../common/src/ui/styles/abstracts/typography'; + +.walletSetupOptionsStep { + padding: size_unit(8) size_unit(9); + height: 100%; + .content { + display: flex; + flex-direction: column; + align-items: center; + height: 100%; + justify-content: space-between; + .image { + width: size_unit(10); + } + } + + .header { + display: flex; + flex-direction: column; + margin-bottom: size_unit(6); + align-items: center; + .title { + @include text-heading; + letter-spacing: -0.015em; + color: var(--text-color-primary); + margin: size_unit(3) 0 0; + text-align: center; + } + .subtitle { + @include text-body-medium; + color: var(--text-color-secondary); + margin: 0; + } + } + + .options { + display: flex; + gap: size_unit(2); + } + .separator { + width: 1px; + height: 100%; + background: var(--light-mode-light-grey-plus, var(--dark-mode-mid-grey)); + } +} + +.link { + color: var(--data-blue); + cursor: pointer; +} + +.legal { + margin-top: size_unit(2); + text-align: center; +} diff --git a/packages/core/src/ui/components/WalletSetupRevamp/WalletSetupOptionsStepRevamp.tsx b/packages/core/src/ui/components/WalletSetupRevamp/WalletSetupOptionsStepRevamp.tsx new file mode 100644 index 000000000..06b6caa68 --- /dev/null +++ b/packages/core/src/ui/components/WalletSetupRevamp/WalletSetupOptionsStepRevamp.tsx @@ -0,0 +1,79 @@ +import React from 'react'; +import styles from './WalletSetupOptionsStepRevamp.module.scss'; +import WalletLogo from '../../assets/icons/onboarding/logo/lace/isologo.png'; +import { ReactComponent as NewWalletIcon } from '../../assets/icons/onboarding/new-wallet.component.svg'; +import { ReactComponent as HardwareWalletIcon } from '../../assets/icons/onboarding/hardware-wallet.component.svg'; +import { ReactComponent as RestoreWalletIcon } from '../../assets/icons/onboarding/restore-wallet.component.svg'; +import { WalletSetupOption } from '../WalletSetup/WalletSetupOption'; +import { TranslationsFor } from '@ui/utils/types'; + +type SetupOptionTranslations = TranslationsFor<'title' | 'description' | 'button'>; + +export interface WalletSetupOptionsStepRevampProps { + onNewWalletRequest: () => void; + onHardwareWalletRequest: () => void; + onRestoreWalletRequest: () => void; + translations: { + title: string; + subTitle: string; + newWallet: SetupOptionTranslations; + hardwareWallet: SetupOptionTranslations; + restoreWallet: SetupOptionTranslations; + }; +} + +const PRIVACY_POLICY_URL = process.env.PRIVACY_POLICY_URL; +const TERMS_OF_USE_URL = process.env.TERMS_OF_USE_URL; + +export const WalletSetupOptionsStepRevamp = ({ + onNewWalletRequest, + onHardwareWalletRequest, + onRestoreWalletRequest, + translations +}: WalletSetupOptionsStepRevampProps): React.ReactElement => ( +
+
+
+ +
+ {translations.title} +
+

+ {translations.subTitle} +

+
+
+); diff --git a/packages/core/src/ui/components/WalletSetupRevamp/index.ts b/packages/core/src/ui/components/WalletSetupRevamp/index.ts index 8d68aa345..bd9eeeeac 100644 --- a/packages/core/src/ui/components/WalletSetupRevamp/index.ts +++ b/packages/core/src/ui/components/WalletSetupRevamp/index.ts @@ -1,2 +1,3 @@ export * from './WalletSetupSelectAccountsStepRevamp'; export * from './WalletSetupStepLayoutRevamp'; +export * from './WalletSetupOptionsStepRevamp'; diff --git a/packages/core/src/ui/lib/translations/en.json b/packages/core/src/ui/lib/translations/en.json index 7336752ff..ee3a1064b 100644 --- a/packages/core/src/ui/lib/translations/en.json +++ b/packages/core/src/ui/lib/translations/en.json @@ -44,7 +44,8 @@ "recoveryPhrase": "Recovery phrase", "connectWallet": "Connect wallet", "nameWallet": "Name wallet", - "allDone": "All done" + "allDone": "All done", + "enterWallet": "Enter wallet" }, "assetSelectorOverlay": { "youDonthaveAnyTokens": "You don't have any tokens.", @@ -112,6 +113,10 @@ "send": "Send", "sending": "Sending", "transaction": "Transaction" + }, + "confirmationBanner": { + "agree": "Agree", + "reject": "Reject" } } } diff --git a/packages/core/src/ui/utils/types.ts b/packages/core/src/ui/utils/types.ts index cf26f3eb0..b462efaff 100644 --- a/packages/core/src/ui/utils/types.ts +++ b/packages/core/src/ui/utils/types.ts @@ -1,14 +1 @@ export type TranslationsFor = Record; - -export type AssetActivityTranslationType = TranslationsFor< - | 'asset' - | 'token' - | 'delegation' - | 'delegationDeregistration' - | 'delegationRegistration' - | 'rewards' - | 'incoming' - | 'outgoing' - | 'sending' - | 'self' ->; From 9b7038c0cb750c7da36a300bd6016a0f9e22b4ff Mon Sep 17 00:00:00 2001 From: John Oshalusi Date: Fri, 1 Mar 2024 13:23:32 +0100 Subject: [PATCH 09/10] feat: [lw-9742] use new register screen for create wallet flow --- apps/browser-extension-wallet/.env.defaults | 1 - .../.env.developerpreview | 1 - apps/browser-extension-wallet/.env.example | 2 +- .../providers/ExperimentsProvider/context.tsx | 8 +- .../wallet-setup/components/WalletSetup.tsx | 8 +- .../components/WalletSetupWizard.tsx | 132 ++---------------- .../components/__tests__/WalletSetup.test.tsx | 0 .../features/wallet-setup/constants.ts | 17 --- .../WalletSetupNamePasswordStep.tsx | 4 +- .../styles.module.scss | 11 ++ .../WalletSetup/WalletSetupStepLayout.tsx | 1 - .../WalletSetup/wallet-steps.common.ts | 1 - .../ui/components/WalletSetup/wallet-steps.ts | 8 +- 13 files changed, 39 insertions(+), 155 deletions(-) create mode 100644 apps/browser-extension-wallet/src/views/browser-view/features/wallet-setup/components/__tests__/WalletSetup.test.tsx delete mode 100644 apps/browser-extension-wallet/src/views/browser-view/features/wallet-setup/constants.ts diff --git a/apps/browser-extension-wallet/.env.defaults b/apps/browser-extension-wallet/.env.defaults index f31c60662..0296fc349 100644 --- a/apps/browser-extension-wallet/.env.defaults +++ b/apps/browser-extension-wallet/.env.defaults @@ -22,7 +22,6 @@ USE_HIDE_MY_BALANCE=true USE_ADA_HANDLE=true USE_DATA_CHECK=false USE_POSTHOG_ANALYTICS=true -USE_COMBINED_PASSWORD_NAME_STEP_COMPONENT=false # TODO Remove redundant feature flags when Trezor and Ledger are supported (https://input-output.atlassian.net/browse/LW-9480) USE_MULTI_DELEGATION_STAKING_LEDGER=false USE_MULTI_DELEGATION_STAKING_TREZOR=false diff --git a/apps/browser-extension-wallet/.env.developerpreview b/apps/browser-extension-wallet/.env.developerpreview index 80566178a..402fe136f 100644 --- a/apps/browser-extension-wallet/.env.developerpreview +++ b/apps/browser-extension-wallet/.env.developerpreview @@ -23,7 +23,6 @@ USE_MULTI_DELEGATION_STAKING=true USE_ADA_HANDLE=false USE_DATA_CHECK=false USE_POSTHOG_ANALYTICS=true -USE_COMBINED_PASSWORD_NAME_STEP_COMPONENT=false USE_MULTI_DELEGATION_STAKING_ACTIVITY=false USE_POSTHOG_ANALYTICS_FOR_OPTED_OUT=false diff --git a/apps/browser-extension-wallet/.env.example b/apps/browser-extension-wallet/.env.example index 740202ad9..3fbdeb7c6 100644 --- a/apps/browser-extension-wallet/.env.example +++ b/apps/browser-extension-wallet/.env.example @@ -25,7 +25,7 @@ USE_HANDLE_AB=false USE_DATA_CHECK=false USE_POSTHOG_ANALYTICS=true USE_POSTHOG_ANALYTICS_FOR_OPTED_OUT=false -USE_COMBINED_PASSWORD_NAME_STEP_COMPONENT=false +USE_MATOMO_ANALYTICS_FOR_OPTED_OUT=false USE_MULTI_DELEGATION_STAKING_ACTIVITY=true USE_MULTI_DELEGATION_STAKING_GRID_VIEW=false USE_ROS_STAKING_COLUMN=false diff --git a/apps/browser-extension-wallet/src/providers/ExperimentsProvider/context.tsx b/apps/browser-extension-wallet/src/providers/ExperimentsProvider/context.tsx index 4819b6423..492330c5f 100644 --- a/apps/browser-extension-wallet/src/providers/ExperimentsProvider/context.tsx +++ b/apps/browser-extension-wallet/src/providers/ExperimentsProvider/context.tsx @@ -1,4 +1,4 @@ -import React, { createContext, useCallback, useContext, useEffect, useMemo, useState } from 'react'; +import React, { createContext, useCallback, useEffect, useMemo, useState } from 'react'; import { usePostHogClientContext } from '@providers/PostHogClientProvider'; import { ExperimentName, ExperimentsConfigStatus } from './types'; @@ -11,12 +11,6 @@ type ExperimentsContext = { // eslint-disable-next-line unicorn/no-null const ExperimentsContext = createContext(null); -export const useExperimentsContext = (): ExperimentsContext => { - const postHogClientContext = useContext(ExperimentsContext); - if (postHogClientContext === null) throw new Error('ExperimentsContext not defined'); - return postHogClientContext; -}; - interface ExperimentsProviderProps { children: React.ReactNode; } diff --git a/apps/browser-extension-wallet/src/views/browser-view/features/wallet-setup/components/WalletSetup.tsx b/apps/browser-extension-wallet/src/views/browser-view/features/wallet-setup/components/WalletSetup.tsx index f447b4850..c974d428f 100644 --- a/apps/browser-extension-wallet/src/views/browser-view/features/wallet-setup/components/WalletSetup.tsx +++ b/apps/browser-extension-wallet/src/views/browser-view/features/wallet-setup/components/WalletSetup.tsx @@ -1,4 +1,10 @@ -import { WalletSetupSteps, WalletSetupFlowProvider, WalletSetupFlow } from '@lace/core'; +import { + WalletSetupSteps, + WalletSetupFlowProvider, + WalletSetupFlow, + useTranslate, + WalletSetupOptionsStep +} from '@lace/core'; import { useAnalyticsContext } from '@providers/AnalyticsProvider'; import { walletRoutePaths } from '@routes/wallet-paths'; import { ILocalStorage } from '@src/types'; diff --git a/apps/browser-extension-wallet/src/views/browser-view/features/wallet-setup/components/WalletSetupWizard.tsx b/apps/browser-extension-wallet/src/views/browser-view/features/wallet-setup/components/WalletSetupWizard.tsx index bdb3c6136..e531c714f 100644 --- a/apps/browser-extension-wallet/src/views/browser-view/features/wallet-setup/components/WalletSetupWizard.tsx +++ b/apps/browser-extension-wallet/src/views/browser-view/features/wallet-setup/components/WalletSetupWizard.tsx @@ -9,9 +9,7 @@ import { WalletSetupFinalStep, WalletSetupMnemonicIntroStep, WalletSetupNamePasswordStep, - WalletSetupPasswordStep, WalletSetupRecoveryPhraseLengthStep, - WalletSetupRegisterStep, WalletSetupSteps, walletSetupWizard } from '@lace/core'; @@ -27,31 +25,17 @@ import { config } from '@src/config'; import { Fallback } from './Fallback'; -import { passwordTranslationMap } from '../constants'; import { deleteFromLocalStorage, getValueFromLocalStorage } from '@src/utils/local-storage'; import { ILocalStorage } from '@src/types'; import { useAnalyticsContext } from '@providers'; import { ENHANCED_ANALYTICS_OPT_IN_STATUS_LS_KEY } from '@providers/AnalyticsProvider/config'; import * as process from 'process'; import { SendOnboardingAnalyticsEvent, SetupType } from '../types'; -import { useExperimentsContext } from '@providers/ExperimentsProvider'; -import { CombinedSetupNamePasswordVariants, ExperimentName } from '@providers/ExperimentsProvider/types'; import { isScriptAddress } from '@cardano-sdk/wallet'; import { filter, firstValueFrom } from 'rxjs'; import { useWalletStore } from '@src/stores'; // import { walletSetupWizardRevamp } from '@lace/core/dist/ui/components/WalletSetupRevamp/wallet-steps-revamp'; -const isCombinedPasswordNameStepEnabled = process.env.USE_COMBINED_PASSWORD_NAME_STEP_COMPONENT === 'true'; -const walletSetupWizardForABTest = { - ...walletSetupWizard, - [WalletSetupSteps.PreMnemonic]: { ...walletSetupWizard['pre-mnemonic'], prev: WalletSetupSteps.Register }, - [WalletSetupSteps.RecoveryPhraseLength]: { - ...walletSetupWizard['recovery-phrase-length'], - prev: WalletSetupSteps.Register - }, - [WalletSetupSteps.Mnemonic]: { ...walletSetupWizard.mnemonic, prev: WalletSetupSteps.Register } -}; - const WalletSetupModeStep = React.lazy(() => import('@lace/core').then((module) => ({ default: module.WalletSetupModeStep })) ); @@ -87,20 +71,19 @@ export const WalletSetupWizard = ({ sendAnalytics, initialStep = WalletSetupSteps.Register }: WalletSetupWizardProps): React.ReactElement => { - const [currentStep, setCurrentStep] = useState( - setupType === SetupType.FORGOT_PASSWORD ? WalletSetupSteps.Password : initialStep - ); + const [currentStep, setCurrentStep] = useState(initialStep); const [walletName, setWalletName] = useState(getValueFromLocalStorage('wallet')?.name); const [password, setPassword] = useState(''); const [walletInstance, setWalletInstance] = useState(); - const [mnemonicLength, setMnemonicLength] = useState(DEFAULT_MNEMONIC_LENGTH); const [mnemonic, setMnemonic] = useState([]); const [walletIsCreating, setWalletIsCreating] = useState(false); const [resetMnemonicStage, setResetMnemonicStage] = useState(''); const [isResetMnemonicModalOpen, setIsResetMnemonicModalOpen] = useState(false); - const { getExperimentVariant } = useExperimentsContext(); - const [shouldDisplayTestVariantForExperiment, setShouldDisplayTestVariantForExperiment] = useState(); + const [enhancedAnalyticsStatus] = useLocalStorage( + ENHANCED_ANALYTICS_OPT_IN_STATUS_LS_KEY, + EnhancedAnalyticsOptInStatus.OptedOut + ); const { createWallet } = useWalletManager(); const { setStayOnAllDonePage } = useWalletStore(); @@ -163,47 +146,12 @@ export const WalletSetupWizard = ({ followDiscord: t('core.walletSetupFinalStep.followDiscord') }; - const walletSetupMnemonicIntroStepTranslations = { - title: t('core.walletSetupMnemonicIntroStep.title'), - description: t('core.walletSetupMnemonicIntroStep.description'), - linkText: t('core.walletSetupMnemonicIntroStep.link') - }; - - const walletSetupRegisterStepTranslations = { - title: t('core.walletSetupRegisterStep.title'), - description: t('core.walletSetupRegisterStep.description'), - walletName: t('core.walletSetupRegisterStep.walletName'), - nameRequired: t('core.walletSetupRegisterStep.nameRequired'), - nameMaxLength: t('core.walletSetupRegisterStep.nameMaxLength') - }; - - const walletSetupPasswordStepTranslations = { - title: t('core.walletSetupRegisterStep.titlePassword'), - description: t('core.walletSetupRegisterStep.passwordDescription'), - password: t('core.walletSetupRegisterStep.password'), - confirmPassword: t('core.walletSetupRegisterStep.confirmPassword'), - noMatchPassword: t('core.walletSetupRegisterStep.noMatchPassword'), - validationMessage: t('core.walletSetupRegisterStep.validationMessage') - }; - const walletSetupRecoveryPhraseLengthStepTranslations = { title: t('core.walletSetupRecoveryPhraseLengthStep.title'), description: t('core.walletSetupRecoveryPhraseLengthStep.description'), wordPassphrase: t('core.walletSetupRecoveryPhraseLengthStep.wordPassphrase') }; - const passwordFeedbackTranslation = (translationKeys: string[]) => { - const translations = []; - - for (const key of translationKeys) { - if (passwordTranslationMap[key]) { - translations.push(t(passwordTranslationMap[key])); - } - } - - return translations; - }; - const moveForward = useCallback(() => { const nextStep = walletSetupWizard[currentStep].next; if (nextStep) { @@ -212,9 +160,7 @@ export const WalletSetupWizard = ({ }, [currentStep, setCurrentStep]); const moveBack = () => { - const prevStep = isCombinedPasswordNameStepEnabled - ? walletSetupWizardForABTest[currentStep].prev - : walletSetupWizard[currentStep].prev; + const prevStep = walletSetupWizard[currentStep].prev; if (prevStep) { setCurrentStep(prevStep); @@ -230,7 +176,7 @@ export const WalletSetupWizard = ({ const goToMyWallet = useCallback( async (cardanoWallet: Wallet.CardanoWallet = walletInstance) => { setStayOnAllDonePage(false); - if (isAnalyticsAccepted) { + if (enhancedAnalyticsStatus === EnhancedAnalyticsOptInStatus.OptedIn) { analytics.sendAliasEvent(); const addresses = await firstValueFrom(cardanoWallet.wallet.addresses$.pipe(filter((a) => a.length > 0))); const hdWalletDiscovered = addresses.some((addr) => !isScriptAddress(addr) && addr.index > 0); @@ -239,12 +185,13 @@ export const WalletSetupWizard = ({ } } }, - [analytics, isAnalyticsAccepted, setStayOnAllDonePage, walletInstance] + [analytics, enhancedAnalyticsStatus, setStayOnAllDonePage, walletInstance] ); const handleCompleteCreation = useCallback(async () => { try { setStayOnAllDonePage(true); + const wallet = await createWallet({ name: walletName, mnemonic, @@ -285,7 +232,7 @@ export const WalletSetupWizard = ({ const createFlowPasswordNextStep = () => { setupType === SetupType.CREATE - ? skipTo(WalletSetupSteps.PreMnemonic) + ? skipTo(WalletSetupSteps.Mnemonic) : useDifferentMnemonicLengths ? skipTo(WalletSetupSteps.RecoveryPhraseLength) : skipTo(WalletSetupSteps.Mnemonic); @@ -298,18 +245,6 @@ export const WalletSetupWizard = ({ createFlowPasswordNextStep(); }; - const handlePasswordStepNextButtonClick = (result: { password: string }) => { - sendAnalytics(postHogOnboardingActions[setupType]?.WALLET_PASSWORD_NEXT_CLICK); - setPassword(result.password); - createFlowPasswordNextStep(); - }; - - const handleRegisterStepNextButtonClick = (result: { walletName: string }) => { - sendAnalytics(postHogOnboardingActions[setupType]?.WALLET_NAME_NEXT_CLICK); - setWalletName(result.walletName); - moveForward(); - }; - useEffect(() => { if (password && currentStep === WalletSetupSteps.Create && !walletIsCreating) { setWalletIsCreating(true); @@ -329,7 +264,7 @@ export const WalletSetupWizard = ({ onCancel={() => useDifferentMnemonicLengths ? skipTo(WalletSetupSteps.RecoveryPhraseLength) - : skipTo(WalletSetupSteps.Password) + : skipTo(WalletSetupSteps.Register) } onSubmit={moveForward} onStepNext={(step: number) => { @@ -357,7 +292,7 @@ export const WalletSetupWizard = ({ mnemonic={mnemonic} onReset={(resetStage) => { setResetMnemonicStage(resetStage); - setIsResetMnemonicModalOpen(true); + resetStage === 'input' ? setIsResetMnemonicModalOpen(true) : skipTo(WalletSetupSteps.Register); }} onNext={moveForward} onStepNext={(stage: MnemonicStage, step: number) => { @@ -386,20 +321,6 @@ export const WalletSetupWizard = ({ ); }; - const shouldDisplayExperiment = useCallback(async () => { - const experimentValue = isAnalyticsAccepted - ? (await getExperimentVariant( - ExperimentName.COMBINED_NAME_PASSWORD_ONBOARDING_SCREEN - )) === 'test' - : false; - - setShouldDisplayTestVariantForExperiment(experimentValue); - }, [getExperimentVariant, isAnalyticsAccepted]); - - useEffect(() => { - shouldDisplayExperiment(); - }, [shouldDisplayExperiment]); - return ( {currentStep === WalletSetupSteps.PreMnemonic && ( @@ -424,34 +345,9 @@ export const WalletSetupWizard = ({ )} - - {shouldDisplayTestVariantForExperiment ? ( - <> - {currentStep === WalletSetupSteps.Register && ( - - )} - - ) : ( - <> - {currentStep === WalletSetupSteps.Register && ( - - )} - {currentStep === WalletSetupSteps.Password && ( - - )} - + {currentStep === WalletSetupSteps.Register && ( + )} - {currentStep === WalletSetupSteps.RecoveryPhraseLength && ( = { - 'feedback.1': 'core.password.feedback.1', - 'feedback.2': 'core.password.feedback.2', - 'feedback.3': 'core.password.feedback.3', - 'feedback.4': 'core.password.feedback.4', - 'feedback.5': 'core.password.feedback.5', - 'feedback.6': 'core.password.feedback.6', - 'feedback.7': 'core.password.feedback.7', - 'feedback.8': 'core.password.feedback.8', - 'feedback.9': 'core.password.feedback.9', - 'feedback.10': 'core.password.feedback.10', - 'feedback.11': 'core.password.feedback.11', - 'feedback.12': 'core.password.feedback.12', - 'feedback.13': 'core.password.feedback.13', - 'feedback.14': 'core.password.feedback.14', - 'feedback.15': 'core.password.feedback.15' -}; diff --git a/packages/core/src/ui/components/WalletSetup/WalletSetupNamePasswordStep/WalletSetupNamePasswordStep.tsx b/packages/core/src/ui/components/WalletSetup/WalletSetupNamePasswordStep/WalletSetupNamePasswordStep.tsx index 723cd27bb..44af980c0 100644 --- a/packages/core/src/ui/components/WalletSetup/WalletSetupNamePasswordStep/WalletSetupNamePasswordStep.tsx +++ b/packages/core/src/ui/components/WalletSetup/WalletSetupNamePasswordStep/WalletSetupNamePasswordStep.tsx @@ -23,10 +23,12 @@ export interface WalletSetupNamePasswordStepProps { onChange?: (state: { name: string; password: string }) => void; } +const INITIAL_WALLET_NAME = 'Wallet 1'; + export const WalletSetupNamePasswordStep = ({ onBack, onNext, - initialWalletName = '', + initialWalletName = INITIAL_WALLET_NAME, onChange }: WalletSetupNamePasswordStepProps): React.ReactElement => { const { t } = useTranslate(); diff --git a/packages/core/src/ui/components/WalletSetup/WalletSetupNamePasswordStep/styles.module.scss b/packages/core/src/ui/components/WalletSetup/WalletSetupNamePasswordStep/styles.module.scss index c046b3071..adddf63a1 100644 --- a/packages/core/src/ui/components/WalletSetup/WalletSetupNamePasswordStep/styles.module.scss +++ b/packages/core/src/ui/components/WalletSetup/WalletSetupNamePasswordStep/styles.module.scss @@ -1,3 +1,5 @@ +@import '../../../styles/theme.scss'; + .walletPasswordAndNameContainer { display: flex; flex-direction: column; @@ -35,3 +37,12 @@ .paddingLeft { padding-left: 24px !important; } + +.input { + width: 100% !important; + max-width: none !important; + + :global(.ant-input-suffix) { + margin-left: size_unit(2); + } +} diff --git a/packages/core/src/ui/components/WalletSetup/WalletSetupStepLayout.tsx b/packages/core/src/ui/components/WalletSetup/WalletSetupStepLayout.tsx index 199322469..067237619 100644 --- a/packages/core/src/ui/components/WalletSetup/WalletSetupStepLayout.tsx +++ b/packages/core/src/ui/components/WalletSetup/WalletSetupStepLayout.tsx @@ -47,7 +47,6 @@ const removeLegalAndAnalyticsStep = ( const getTimelineSteps = (currentStep: WalletTimelineSteps, isHardwareWallet: boolean, flow: WalletSetupFlow) => { const inMemoryWalletSteps = [ - { key: WalletTimelineSteps.LEGAL_AND_ANALYTICS, name: i18n.t('package.core.walletSetupStep.legalAndAnalytics') }, { key: WalletTimelineSteps.WALLET_SETUP, name: i18n.t('package.core.walletSetupStep.walletSetup') }, { key: WalletTimelineSteps.RECOVERY_PHRASE, name: i18n.t('package.core.walletSetupStep.recoveryPhrase') }, { key: WalletTimelineSteps.ALL_DONE, name: i18n.t('package.core.walletSetupStep.allDone') } diff --git a/packages/core/src/ui/components/WalletSetup/wallet-steps.common.ts b/packages/core/src/ui/components/WalletSetup/wallet-steps.common.ts index af9c76a3c..81ec787e6 100644 --- a/packages/core/src/ui/components/WalletSetup/wallet-steps.common.ts +++ b/packages/core/src/ui/components/WalletSetup/wallet-steps.common.ts @@ -3,7 +3,6 @@ export enum WalletSetupSteps { PreMnemonic = 'pre-mnemonic', Mnemonic = 'mnemonic', Register = 'register', - Password = 'password', RecoveryPhraseLength = 'recovery-phrase-length', Create = 'create', Finish = 'finish' diff --git a/packages/core/src/ui/components/WalletSetup/wallet-steps.ts b/packages/core/src/ui/components/WalletSetup/wallet-steps.ts index c0052b10c..124f5dbf2 100644 --- a/packages/core/src/ui/components/WalletSetup/wallet-steps.ts +++ b/packages/core/src/ui/components/WalletSetup/wallet-steps.ts @@ -2,18 +2,14 @@ import { WalletSetupSteps, WalletSetupWizard } from './wallet-steps.common'; export const walletSetupWizard: WalletSetupWizard = { [WalletSetupSteps.Register]: { - next: WalletSetupSteps.Password - }, - [WalletSetupSteps.Password]: { - prev: WalletSetupSteps.Register, next: WalletSetupSteps.RecoveryPhraseLength }, [WalletSetupSteps.RecoveryPhraseLength]: { - prev: WalletSetupSteps.Password, + prev: WalletSetupSteps.Register, next: WalletSetupSteps.Mnemonic }, [WalletSetupSteps.PreMnemonic]: { - prev: WalletSetupSteps.Password, + prev: WalletSetupSteps.Register, next: WalletSetupSteps.Mnemonic }, [WalletSetupSteps.Mnemonic]: { From 1f3ba6f03452d054c9001d87898022ee28579c0a Mon Sep 17 00:00:00 2001 From: John Oshalusi Date: Fri, 1 Mar 2024 16:34:42 +0100 Subject: [PATCH 10/10] feat: [lw-9745]: revamp mnemonic verification --- apps/browser-extension-wallet/.env.defaults | 1 - .../.env.developerpreview | 1 - apps/browser-extension-wallet/.env.example | 2 - .../src/lib/translations/en.json | 22 ++- .../components/WalletSetup.module.scss | 1 - .../wallet-setup/components/WalletSetup.tsx | 8 +- .../components/WalletSetupWizard.tsx | 182 +++++++----------- .../components/Timeline/Timeline.module.scss | 3 +- .../MnemonicWordsAutoComplete.tsx | 10 +- .../WalletSetupNamePasswordStep.tsx | 1 - .../WalletSetup/WalletSetupStepLayout.tsx | 1 + .../WalletSetup/wallet-steps.common.ts | 1 - .../ui/components/WalletSetup/wallet-steps.ts | 12 +- .../MnemonicVideoPopupContent.module.scss | 52 +++++ .../MnemonicVideoPopupContent.tsx | 55 ++++++ .../MnemonicWordContainerRevamp.module.scss | 54 ++++++ .../MnemonicWordContainerRevamp.tsx | 37 ++++ ...nemonicWordsConfirmInputRevamp.module.scss | 27 +++ .../MnemonicWordsConfirmInputRevamp.tsx | 40 ++++ .../MnemonicWordsWritedownRevamp.module.scss | 24 +++ .../MnemonicWordsWritedownRevamp.tsx | 36 ++++ .../WalletSetupMnemonicStepRevamp.tsx | 153 +++++++++++++++ ...MnemonicVerificationStepRevamp.module.scss | 52 +++++ ...letSetupMnemonicVerificationStepRevamp.tsx | 101 ++++++++++ .../WalletSetupMnemonicStepRevamp/index.ts | 3 + .../wallet-utils.ts | 10 + .../WalletSetupStepLayoutRevamp.module.scss | 80 ++++++++ .../WalletSetupStepLayoutRevamp.tsx | 21 +- .../ui/components/WalletSetupRevamp/index.ts | 6 +- 29 files changed, 841 insertions(+), 155 deletions(-) create mode 100644 packages/core/src/ui/components/WalletSetupRevamp/MnemonicVideoPopupContent.module.scss create mode 100644 packages/core/src/ui/components/WalletSetupRevamp/MnemonicVideoPopupContent.tsx create mode 100644 packages/core/src/ui/components/WalletSetupRevamp/WalletSetupMnemonicStepRevamp/MnemonicWordContainerRevamp.module.scss create mode 100644 packages/core/src/ui/components/WalletSetupRevamp/WalletSetupMnemonicStepRevamp/MnemonicWordContainerRevamp.tsx create mode 100644 packages/core/src/ui/components/WalletSetupRevamp/WalletSetupMnemonicStepRevamp/MnemonicWordsConfirmInputRevamp.module.scss create mode 100644 packages/core/src/ui/components/WalletSetupRevamp/WalletSetupMnemonicStepRevamp/MnemonicWordsConfirmInputRevamp.tsx create mode 100644 packages/core/src/ui/components/WalletSetupRevamp/WalletSetupMnemonicStepRevamp/MnemonicWordsWritedownRevamp.module.scss create mode 100644 packages/core/src/ui/components/WalletSetupRevamp/WalletSetupMnemonicStepRevamp/MnemonicWordsWritedownRevamp.tsx create mode 100644 packages/core/src/ui/components/WalletSetupRevamp/WalletSetupMnemonicStepRevamp/WalletSetupMnemonicStepRevamp.tsx create mode 100644 packages/core/src/ui/components/WalletSetupRevamp/WalletSetupMnemonicStepRevamp/WalletSetupMnemonicVerificationStepRevamp.module.scss create mode 100644 packages/core/src/ui/components/WalletSetupRevamp/WalletSetupMnemonicStepRevamp/WalletSetupMnemonicVerificationStepRevamp.tsx create mode 100644 packages/core/src/ui/components/WalletSetupRevamp/WalletSetupMnemonicStepRevamp/index.ts create mode 100644 packages/core/src/ui/components/WalletSetupRevamp/WalletSetupMnemonicStepRevamp/wallet-utils.ts create mode 100644 packages/core/src/ui/components/WalletSetupRevamp/WalletSetupStepLayoutRevamp.module.scss diff --git a/apps/browser-extension-wallet/.env.defaults b/apps/browser-extension-wallet/.env.defaults index 0296fc349..2961cdb94 100644 --- a/apps/browser-extension-wallet/.env.defaults +++ b/apps/browser-extension-wallet/.env.defaults @@ -15,7 +15,6 @@ USE_PASSWORD_VERIFICATION=false USE_DAPP_CONNECTOR=true USE_TREZOR_HW=false USE_TOKEN_PRICING=true -USE_DIFFERENT_MNEMONIC_LENGTHS=true USE_NFT_FOLDERS=true USE_MULTI_CURRENCY=true USE_HIDE_MY_BALANCE=true diff --git a/apps/browser-extension-wallet/.env.developerpreview b/apps/browser-extension-wallet/.env.developerpreview index 402fe136f..1363442ee 100644 --- a/apps/browser-extension-wallet/.env.developerpreview +++ b/apps/browser-extension-wallet/.env.developerpreview @@ -15,7 +15,6 @@ USE_PASSWORD_VERIFICATION=false USE_DAPP_CONNECTOR=true USE_TREZOR_HW=false USE_TOKEN_PRICING=true -USE_DIFFERENT_MNEMONIC_LENGTHS=true USE_NFT_FOLDERS=true USE_MULTI_CURRENCY=true USE_HIDE_MY_BALANCE=true diff --git a/apps/browser-extension-wallet/.env.example b/apps/browser-extension-wallet/.env.example index 3fbdeb7c6..37876861b 100644 --- a/apps/browser-extension-wallet/.env.example +++ b/apps/browser-extension-wallet/.env.example @@ -14,7 +14,6 @@ USE_PASSWORD_VERIFICATION=false USE_DAPP_CONNECTOR=true USE_TREZOR_HW=false USE_TOKEN_PRICING=true -USE_DIFFERENT_MNEMONIC_LENGTHS=true USE_NFT_FOLDERS=true USE_MULTI_CURRENCY=true USE_HIDE_MY_BALANCE=true @@ -25,7 +24,6 @@ USE_HANDLE_AB=false USE_DATA_CHECK=false USE_POSTHOG_ANALYTICS=true USE_POSTHOG_ANALYTICS_FOR_OPTED_OUT=false -USE_MATOMO_ANALYTICS_FOR_OPTED_OUT=false USE_MULTI_DELEGATION_STAKING_ACTIVITY=true USE_MULTI_DELEGATION_STAKING_GRID_VIEW=false USE_ROS_STAKING_COLUMN=false diff --git a/apps/browser-extension-wallet/src/lib/translations/en.json b/apps/browser-extension-wallet/src/lib/translations/en.json index f344b758e..178e7263b 100644 --- a/apps/browser-extension-wallet/src/lib/translations/en.json +++ b/apps/browser-extension-wallet/src/lib/translations/en.json @@ -1273,14 +1273,30 @@ "passphraseInfo3": "Find out more.", "passphraseError": "Make sure the words of your recovery phrase are in the right order and spelled correctly." }, - "walletSetupMnemonicIntroStep": { + "walletSetupMnemonicStepRevamp": { + "writePassphraseTitle": "Save your recovery phrase", + "enterPassphrase": "Enter your recovery passphrase", + "enterPassphraseLength": "Choose recovery phrase length", + "enterPassphraseDescription": "Let's check you've got the correct recovery phrase. Type each word in the right order or paste from clipboard to verify it.", + "writePassphraseSubtitle1": "Consider your recovery phrase as the master key to your wallet.", + "writePassphraseSubtitle2": "Watch video.", + "passphraseError": "Make sure the words of your recovery phrase are in the right order and spelled correctly.", + "enterWallet": "Enter wallet", + "copyToClipboard": "Copy to clipboard", + "pasteFromClipboard": "Paste from clipboard" + }, + "mnemonicVideoPopupContent": { "title": "Keeping your wallet secure", - "description": "Consider your recovery phrase as the master key to your wallet, and the only way to access your funds.", - "link": "Read More." + "description": "Learn about what is a recovery phrase, and how to keep it safe from the video below.", + "link": "Read More.", + "closeButton": "Got it" }, "walletSetupMnemonicVerificationStep": { "enterPassphrase": "Enter your secret passphrase" }, + "walletSetupMnemonicVerificationStepRevamp": { + "enterPassphrase": "Enter your recovery phrase" + }, "walletSetupOptionsStep": { "title": "Let's explore Web3 together", "subTitle": "Choose an option to get started", diff --git a/apps/browser-extension-wallet/src/views/browser-view/features/wallet-setup/components/WalletSetup.module.scss b/apps/browser-extension-wallet/src/views/browser-view/features/wallet-setup/components/WalletSetup.module.scss index 98fe65a72..d9fe76b8d 100644 --- a/apps/browser-extension-wallet/src/views/browser-view/features/wallet-setup/components/WalletSetup.module.scss +++ b/apps/browser-extension-wallet/src/views/browser-view/features/wallet-setup/components/WalletSetup.module.scss @@ -26,7 +26,6 @@ :global { .ant-input-password > input[type='password'], .ant-input-password > input[type='text'] { - width: 380px; transition: none !important; } diff --git a/apps/browser-extension-wallet/src/views/browser-view/features/wallet-setup/components/WalletSetup.tsx b/apps/browser-extension-wallet/src/views/browser-view/features/wallet-setup/components/WalletSetup.tsx index c974d428f..f447b4850 100644 --- a/apps/browser-extension-wallet/src/views/browser-view/features/wallet-setup/components/WalletSetup.tsx +++ b/apps/browser-extension-wallet/src/views/browser-view/features/wallet-setup/components/WalletSetup.tsx @@ -1,10 +1,4 @@ -import { - WalletSetupSteps, - WalletSetupFlowProvider, - WalletSetupFlow, - useTranslate, - WalletSetupOptionsStep -} from '@lace/core'; +import { WalletSetupSteps, WalletSetupFlowProvider, WalletSetupFlow } from '@lace/core'; import { useAnalyticsContext } from '@providers/AnalyticsProvider'; import { walletRoutePaths } from '@routes/wallet-paths'; import { ILocalStorage } from '@src/types'; diff --git a/apps/browser-extension-wallet/src/views/browser-view/features/wallet-setup/components/WalletSetupWizard.tsx b/apps/browser-extension-wallet/src/views/browser-view/features/wallet-setup/components/WalletSetupWizard.tsx index e531c714f..f1f87300c 100644 --- a/apps/browser-extension-wallet/src/views/browser-view/features/wallet-setup/components/WalletSetupWizard.tsx +++ b/apps/browser-extension-wallet/src/views/browser-view/features/wallet-setup/components/WalletSetupWizard.tsx @@ -6,8 +6,7 @@ import { useLocalStorage, useTimeSpentOnPage, useWalletManager } from '@hooks'; import { MnemonicStage, WalletSetupCreationStep, - WalletSetupFinalStep, - WalletSetupMnemonicIntroStep, + MnemonicVideoPopupContent, WalletSetupNamePasswordStep, WalletSetupRecoveryPhraseLengthStep, WalletSetupSteps, @@ -33,19 +32,17 @@ import * as process from 'process'; import { SendOnboardingAnalyticsEvent, SetupType } from '../types'; import { isScriptAddress } from '@cardano-sdk/wallet'; import { filter, firstValueFrom } from 'rxjs'; -import { useWalletStore } from '@src/stores'; -// import { walletSetupWizardRevamp } from '@lace/core/dist/ui/components/WalletSetupRevamp/wallet-steps-revamp'; const WalletSetupModeStep = React.lazy(() => import('@lace/core').then((module) => ({ default: module.WalletSetupModeStep })) ); -const WalletSetupMnemonicStep = React.lazy(() => - import('@lace/core').then((module) => ({ default: module.WalletSetupMnemonicStep })) +const WalletSetupMnemonicStepRevamp = React.lazy(() => + import('@lace/core').then((module) => ({ default: module.WalletSetupMnemonicStepRevamp })) ); -const WalletSetupMnemonicVerificationStep = React.lazy(() => - import('@lace/core').then((module) => ({ default: module.WalletSetupMnemonicVerificationStep })) +const WalletSetupMnemonicVerificationStepRevamp = React.lazy(() => + import('@lace/core').then((module) => ({ default: module.WalletSetupMnemonicVerificationStepRevamp })) ); const wordList = wordlists.english; @@ -80,13 +77,8 @@ export const WalletSetupWizard = ({ const [walletIsCreating, setWalletIsCreating] = useState(false); const [resetMnemonicStage, setResetMnemonicStage] = useState(''); const [isResetMnemonicModalOpen, setIsResetMnemonicModalOpen] = useState(false); - const [enhancedAnalyticsStatus] = useLocalStorage( - ENHANCED_ANALYTICS_OPT_IN_STATUS_LS_KEY, - EnhancedAnalyticsOptInStatus.OptedOut - ); const { createWallet } = useWalletManager(); - const { setStayOnAllDonePage } = useWalletStore(); const analytics = useAnalyticsContext(); const { t } = useTranslation(); const [enhancedAnalyticsStatus] = useLocalStorage( @@ -96,9 +88,6 @@ export const WalletSetupWizard = ({ const { updateEnteredAtTime } = useTimeSpentOnPage(); - const useDifferentMnemonicLengths = process.env.USE_DIFFERENT_MNEMONIC_LENGTHS === 'true'; - const isAnalyticsAccepted = enhancedAnalyticsStatus === EnhancedAnalyticsOptInStatus.OptedIn; - useEffect(() => { updateEnteredAtTime(); }, [currentStep, updateEnteredAtTime]); @@ -112,14 +101,17 @@ export const WalletSetupWizard = ({ }, [mnemonicLength, setupType]); const walletSetupMnemonicStepTranslations = { - writePassphrase: t('core.walletSetupMnemonicStep.writePassphrase'), - body: t('core.walletSetupMnemonicStep.body'), - enterPassphrase: t('core.walletSetupMnemonicStep.enterPassphrase'), - enterPassphraseDescription: t('core.walletSetupMnemonicStep.enterPassphraseDescription'), - passphraseInfo1: t('core.walletSetupMnemonicStep.passphraseInfo1'), - passphraseInfo2: t('core.walletSetupMnemonicStep.passphraseInfo2'), - passphraseInfo3: t('core.walletSetupMnemonicStep.passphraseInfo3'), - passphraseError: t('core.walletSetupMnemonicStep.passphraseError') + writePassphraseTitle: t('core.walletSetupMnemonicStepRevamp.writePassphraseTitle'), + body: t('core.walletSetupMnemonicStepRevamp.body'), + enterPassphrase: t('core.walletSetupMnemonicStepRevamp.enterPassphrase'), + enterPassphraseDescription: t('core.walletSetupMnemonicStepRevamp.enterPassphraseDescription'), + writePassphraseSubtitle1: t('core.walletSetupMnemonicStepRevamp.writePassphraseSubtitle1'), + writePassphraseSubtitle2: t('core.walletSetupMnemonicStepRevamp.writePassphraseSubtitle2'), + passphraseError: t('core.walletSetupMnemonicStepRevamp.passphraseError'), + enterWallet: t('core.walletSetupMnemonicStepRevamp.enterWallet'), + enterPassphraseLength: t('core.walletSetupMnemonicStepRevamp.enterPassphraseLength'), + copyToClipboard: t('core.walletSetupMnemonicStepRevamp.copyToClipboard'), + pasteFromClipboard: t('core.walletSetupMnemonicStepRevamp.pasteFromClipboard') }; const walletSetupModeStepTranslations = { @@ -137,27 +129,18 @@ export const WalletSetupWizard = ({ description: t('core.walletSetupCreateStep.description') }; - const walletSetupFinalStepTranslations = { - title: t('core.walletSetupFinalStep.title'), - description: t('core.walletSetupFinalStep.description'), - close: t('core.walletSetupFinalStep.close'), - followTwitter: t('core.walletSetupFinalStep.followTwitter'), - followYoutube: t('core.walletSetupFinalStep.followYoutube'), - followDiscord: t('core.walletSetupFinalStep.followDiscord') - }; - const walletSetupRecoveryPhraseLengthStepTranslations = { title: t('core.walletSetupRecoveryPhraseLengthStep.title'), description: t('core.walletSetupRecoveryPhraseLengthStep.description'), wordPassphrase: t('core.walletSetupRecoveryPhraseLengthStep.wordPassphrase') }; - const moveForward = useCallback(() => { - const nextStep = walletSetupWizard[currentStep].next; - if (nextStep) { - setCurrentStep(nextStep); - } - }, [currentStep, setCurrentStep]); + const mnemonicVideoPopupContentTranslations = { + title: t('core.mnemonicVideoPopupContent.title'), + description: t('core.mnemonicVideoPopupContent.description'), + linkText: t('core.mnemonicVideoPopupContent.link'), + closeButton: t('core.mnemonicVideoPopupContent.closeButton') + }; const moveBack = () => { const prevStep = walletSetupWizard[currentStep].prev; @@ -173,9 +156,26 @@ export const WalletSetupWizard = ({ setCurrentStep(walletStep); }; + /* const handleAnalyticsChoice = async (isAccepted: boolean) => { + setIsAnalyticsAccepted(isAccepted); + await analytics.setOptedInForEnhancedAnalytics( + isAccepted ? EnhancedAnalyticsOptInStatus.OptedIn : EnhancedAnalyticsOptInStatus.OptedOut + ); + + const postHogAnalyticsAgreeAction = postHogOnboardingActions[setupType]?.ANALYTICS_AGREE_CLICK; + const postHogAnalyticcSkipAction = postHogOnboardingActions[setupType]?.ANALYTICS_SKIP_CLICK; + + const postHogAction = isAccepted ? postHogAnalyticsAgreeAction : postHogAnalyticcSkipAction; + const postHogProperties = { + // eslint-disable-next-line camelcase + $set: { user_tracking_type: isAccepted ? UserTrackingType.Enhanced : UserTrackingType.Basic } + }; + await sendAnalytics(postHogAction, postHogProperties); + moveForward(); + };*/ + const goToMyWallet = useCallback( async (cardanoWallet: Wallet.CardanoWallet = walletInstance) => { - setStayOnAllDonePage(false); if (enhancedAnalyticsStatus === EnhancedAnalyticsOptInStatus.OptedIn) { analytics.sendAliasEvent(); const addresses = await firstValueFrom(cardanoWallet.wallet.addresses$.pipe(filter((a) => a.length > 0))); @@ -185,13 +185,20 @@ export const WalletSetupWizard = ({ } } }, - [analytics, enhancedAnalyticsStatus, setStayOnAllDonePage, walletInstance] + [analytics, enhancedAnalyticsStatus, walletInstance] ); + const moveForward = useCallback(() => { + const nextStep = walletSetupWizard[currentStep].next; + if (nextStep) { + setCurrentStep(nextStep); + } else if (currentStep === WalletSetupSteps.Create) { + goToMyWallet(); + } + }, [currentStep, setCurrentStep, goToMyWallet]); + const handleCompleteCreation = useCallback(async () => { try { - setStayOnAllDonePage(true); - const wallet = await createWallet({ name: walletName, mnemonic, @@ -218,31 +225,13 @@ export const WalletSetupWizard = ({ console.error('Error completing wallet creation', error); throw new Error(error); } - }, [ - createWallet, - setStayOnAllDonePage, - walletName, - mnemonic, - password, - analytics, - setupType, - goToMyWallet, - moveForward - ]); - - const createFlowPasswordNextStep = () => { - setupType === SetupType.CREATE - ? skipTo(WalletSetupSteps.Mnemonic) - : useDifferentMnemonicLengths - ? skipTo(WalletSetupSteps.RecoveryPhraseLength) - : skipTo(WalletSetupSteps.Mnemonic); - }; + }, [createWallet, walletName, mnemonic, password, analytics, setupType, goToMyWallet, moveForward]); const handleNamePasswordStepNextButtonClick = (result: { password: string; walletName: string }) => { - setPassword(result.password); setWalletName(result.walletName); + setPassword(result.password); sendAnalytics(postHogOnboardingActions[setupType]?.WALLET_NAME_PASSWORD_NEXT_CLICK); - createFlowPasswordNextStep(); + skipTo(WalletSetupSteps.Mnemonic); }; useEffect(() => { @@ -256,16 +245,16 @@ export const WalletSetupWizard = ({ const renderedMnemonicStep = () => { if ([SetupType.RESTORE, SetupType.FORGOT_PASSWORD].includes(setupType)) { const isMnemonicSubmitEnabled = util.validateMnemonic(util.joinMnemonicWords(mnemonic)); - return ( - + /* onCancel={() => useDifferentMnemonicLengths ? skipTo(WalletSetupSteps.RecoveryPhraseLength) : skipTo(WalletSetupSteps.Register) - } + }*/ + onCancel={moveBack} onSubmit={moveForward} onStepNext={(step: number) => { /* eslint-disable no-magic-numbers */ @@ -283,36 +272,32 @@ export const WalletSetupWizard = ({ isSubmitEnabled={isMnemonicSubmitEnabled} translations={walletSetupMnemonicStepTranslations} suggestionList={wordList} + defaultMnemonicLength={DEFAULT_MNEMONIC_LENGTH} + onSetMnemonicLength={(value: number) => setMnemonicLength(value)} /> ); } return ( - { setResetMnemonicStage(resetStage); resetStage === 'input' ? setIsResetMnemonicModalOpen(true) : skipTo(WalletSetupSteps.Register); }} + renderVideoPopupContent={({ onClose }) => ( + { + // TODO: https://input-output.atlassian.net/browse/LW-9761 handle analytics here based on the stage argument + }} + videoSrc={process.env.YOUTUBE_RECOVERY_PHRASE_VIDEO_URL} + onClose={onClose} + /> + )} onNext={moveForward} - onStepNext={(stage: MnemonicStage, step: number) => { - /* eslint-disable no-magic-numbers */ - switch (step) { - case 0: - stage === 'input' - ? sendAnalytics(postHogOnboardingActions[setupType]?.ENTER_PASSPHRASE_01_NEXT_CLICK) - : sendAnalytics(postHogOnboardingActions[setupType]?.WRITE_PASSPHRASE_01_NEXT_CLICK); - break; - case 1: - stage === 'input' - ? sendAnalytics(postHogOnboardingActions[setupType]?.ENTER_PASSPHRASE_09_NEXT_CLICK) - : sendAnalytics(postHogOnboardingActions[setupType]?.WRITE_PASSPHRASE_09_NEXT_CLICK); - break; - case 2: - stage === 'input' - ? sendAnalytics(postHogOnboardingActions[setupType]?.ENTER_PASSPHRASE_17_NEXT_CLICK) - : sendAnalytics(postHogOnboardingActions[setupType]?.WRITE_PASSPHRASE_17_NEXT_CLICK); - } + onStepNext={() => { + // TODO: https://input-output.atlassian.net/browse/LW-9761 handle analytics here based on the stage argument }} translations={walletSetupMnemonicStepTranslations} suggestionList={wordList} @@ -323,20 +308,6 @@ export const WalletSetupWizard = ({ return ( - {currentStep === WalletSetupSteps.PreMnemonic && ( - { - analytics.sendEventToPostHog(postHogOnboardingActions[setupType]?.PASSPHRASE_INTRO_NEXT_CLICK); - moveForward(); - }} - translations={walletSetupMnemonicIntroStepTranslations} - onClickVideo={() => - analytics.sendEventToPostHog(postHogOnboardingActions[setupType]?.PASSPHRASE_INTRO_PLAY_VIDEO_CLICK) - } - videoSrc={process.env.YOUTUBE_RECOVERY_PHRASE_VIDEO_URL} - /> - )} {currentStep === WalletSetupSteps.Mnemonic && ( }>{renderedMnemonicStep()} )} @@ -362,15 +333,6 @@ export const WalletSetupWizard = ({ {currentStep === WalletSetupSteps.Create && ( )} - {currentStep === WalletSetupSteps.Finish && ( - { - sendAnalytics(postHogOnboardingActions[setupType]?.DONE_GO_TO_WALLET); - goToMyWallet(); - }} - translations={walletSetupFinalStepTranslations} - /> - )} {setupType === SetupType.CREATE && isResetMnemonicModalOpen && ( ; max?: number; focus?: boolean; + className?: string; } export const MnemonicWordsAutoComplete = ({ @@ -27,7 +28,8 @@ export const MnemonicWordsAutoComplete = ({ onChange, onDropdownVisibleChange, max = DEFAULT_INPUT_MAX_LENGTH, - focus = false + focus = false, + className }: MnemonicWordsAutoCompleteProps): React.ReactElement => { const containerRef = useRef(null); const inputRef = useRef(null); @@ -96,7 +98,7 @@ export const MnemonicWordsAutoComplete = ({ }, [options, value, max]); return ( - + - + ); }; diff --git a/packages/core/src/ui/components/WalletSetup/WalletSetupNamePasswordStep/WalletSetupNamePasswordStep.tsx b/packages/core/src/ui/components/WalletSetup/WalletSetupNamePasswordStep/WalletSetupNamePasswordStep.tsx index 44af980c0..302ae9745 100644 --- a/packages/core/src/ui/components/WalletSetup/WalletSetupNamePasswordStep/WalletSetupNamePasswordStep.tsx +++ b/packages/core/src/ui/components/WalletSetup/WalletSetupNamePasswordStep/WalletSetupNamePasswordStep.tsx @@ -3,7 +3,6 @@ import { WalletSetupStepLayout, WalletTimelineSteps } from '../WalletSetupStepLa import { PasswordVerification } from '@lace/common'; import { passwordComplexity } from '@src/ui/utils/password-complexity'; import { useTranslate } from '@src/ui/hooks'; - import { BarStates, WalletSetupNamePasswordSubmitParams } from './types'; import styles from './styles.module.scss'; import { diff --git a/packages/core/src/ui/components/WalletSetup/WalletSetupStepLayout.tsx b/packages/core/src/ui/components/WalletSetup/WalletSetupStepLayout.tsx index 067237619..8550084b8 100644 --- a/packages/core/src/ui/components/WalletSetup/WalletSetupStepLayout.tsx +++ b/packages/core/src/ui/components/WalletSetup/WalletSetupStepLayout.tsx @@ -16,6 +16,7 @@ export enum WalletTimelineSteps { CONNECT_WALLET, NAME_WALLET } + export interface WalletSetupStepLayoutProps { title: React.ReactNode; children?: React.ReactNode; diff --git a/packages/core/src/ui/components/WalletSetup/wallet-steps.common.ts b/packages/core/src/ui/components/WalletSetup/wallet-steps.common.ts index 81ec787e6..95a9538cf 100644 --- a/packages/core/src/ui/components/WalletSetup/wallet-steps.common.ts +++ b/packages/core/src/ui/components/WalletSetup/wallet-steps.common.ts @@ -1,6 +1,5 @@ export enum WalletSetupSteps { Mode = 'mode', - PreMnemonic = 'pre-mnemonic', Mnemonic = 'mnemonic', Register = 'register', RecoveryPhraseLength = 'recovery-phrase-length', diff --git a/packages/core/src/ui/components/WalletSetup/wallet-steps.ts b/packages/core/src/ui/components/WalletSetup/wallet-steps.ts index 124f5dbf2..a2c6041b2 100644 --- a/packages/core/src/ui/components/WalletSetup/wallet-steps.ts +++ b/packages/core/src/ui/components/WalletSetup/wallet-steps.ts @@ -8,19 +8,11 @@ export const walletSetupWizard: WalletSetupWizard = { prev: WalletSetupSteps.Register, next: WalletSetupSteps.Mnemonic }, - [WalletSetupSteps.PreMnemonic]: { - prev: WalletSetupSteps.Register, - next: WalletSetupSteps.Mnemonic - }, [WalletSetupSteps.Mnemonic]: { - prev: WalletSetupSteps.PreMnemonic, + prev: WalletSetupSteps.RecoveryPhraseLength, next: WalletSetupSteps.Create }, [WalletSetupSteps.Create]: { - prev: WalletSetupSteps.Mnemonic, - next: WalletSetupSteps.Finish - }, - [WalletSetupSteps.Finish]: { - prev: WalletSetupSteps.Create + prev: WalletSetupSteps.Mnemonic } }; diff --git a/packages/core/src/ui/components/WalletSetupRevamp/MnemonicVideoPopupContent.module.scss b/packages/core/src/ui/components/WalletSetupRevamp/MnemonicVideoPopupContent.module.scss new file mode 100644 index 000000000..4883ac80d --- /dev/null +++ b/packages/core/src/ui/components/WalletSetupRevamp/MnemonicVideoPopupContent.module.scss @@ -0,0 +1,52 @@ +@import '../../../../../common/src/ui/styles/abstracts/typography'; + +.container { + height: 100%; + display: flex; + flex-direction: column; + gap: size_unit(6); + + .content { + display: flex; + flex-direction: column; + gap: size_unit(2); + + .title { + @include text-heading; + color: var(--text-color-primary, #3d3b39); + margin: 0; + } + + .description { + font-size: var(--body) !important; + line-height: size_unit(3) !important; + color: var(--text-color-primary, #3d3b39); + margin: 0; + } + + .videoContainer { + position: relative; + height: 272px; + border-radius: 16px; + border: 1px solid #efefef; + + .overlay { + z-index: 1; + position: absolute; + width: 100%; + height: 100%; + border-radius: 16px; + top: 0; + left: 0; + opacity: 0; + } + + .video { + width: 100%; + height: 100%; + border-radius: 16px; + border: none; + } + } + } +} diff --git a/packages/core/src/ui/components/WalletSetupRevamp/MnemonicVideoPopupContent.tsx b/packages/core/src/ui/components/WalletSetupRevamp/MnemonicVideoPopupContent.tsx new file mode 100644 index 000000000..b3c003ebd --- /dev/null +++ b/packages/core/src/ui/components/WalletSetupRevamp/MnemonicVideoPopupContent.tsx @@ -0,0 +1,55 @@ +import { Button } from '@lace/ui'; +import { TranslationsFor } from '@ui/utils/types'; +import { urls } from '@ui/utils/constants'; +import React, { ReactElement, useRef, useState } from 'react'; +import styles from './MnemonicVideoPopupContent.module.scss'; + +type MnemonicVideoPopupContentProps = { + onClickVideo: () => void; + onClose: () => void; + translations: TranslationsFor<'title' | 'description' | 'linkText' | 'closeButton'>; + videoSrc: string; +}; + +export const MnemonicVideoPopupContent = ({ + onClickVideo, + onClose, + translations, + videoSrc +}: MnemonicVideoPopupContentProps): ReactElement => { + const [overlayVisible, setOverlayVisible] = useState(true); + const videoRef = useRef(); + + return ( +
+
+

{translations.title}

+

+ {translations.description}{' '} + + {translations.linkText} + +

+
{ + setOverlayVisible(false); + videoRef.current.src += '&autoplay=1'; + onClickVideo(); + }} + > + {overlayVisible &&
} +