From a1babada699617e58d13cd86873caea00c287848 Mon Sep 17 00:00:00 2001 From: flexsurfer Date: Tue, 5 Sep 2023 13:19:15 +0200 Subject: [PATCH] Onboarding screens (#17165) * Broken back navigation on "Create profile" screen #17155 Onboarding screens layout is broken #17152 Onboarding Flow - Layout issues in enable biometrics screen #17151 Onboarding navigation issues #17129 --- .../components/text_combinations/style.cljs | 8 +--- src/status_im2/common/parallax/view.cljs | 3 +- .../onboarding/common/overlay/events.cljs | 18 ++++++++ .../onboarding/common/overlay/view.cljs | 13 +++--- .../onboarding/create_profile/view.cljs | 2 +- .../onboarding/enable_biometrics/style.cljs | 2 +- .../onboarding/enable_biometrics/view.cljs | 24 ++++------ .../onboarding/enable_notifications/view.cljs | 2 +- .../contexts/onboarding/intro/view.cljs | 4 +- .../onboarding/new_to_status/view.cljs | 17 +++---- .../contexts/onboarding/sign_in/view.cljs | 5 --- .../contexts/profile/profiles/view.cljs | 12 +++-- .../contexts/syncing/scan_sync_code/view.cljs | 32 ++++++------- src/status_im2/events.cljs | 1 + src/status_im2/navigation/core.cljs | 15 +++---- src/status_im2/navigation/screens.cljs | 45 ++++++++----------- src/status_im2/navigation/util.cljs | 42 ----------------- 17 files changed, 95 insertions(+), 150 deletions(-) create mode 100644 src/status_im2/contexts/onboarding/common/overlay/events.cljs delete mode 100644 src/status_im2/navigation/util.cljs diff --git a/src/quo2/components/text_combinations/style.cljs b/src/quo2/components/text_combinations/style.cljs index dd96e349f2..911364f23f 100644 --- a/src/quo2/components/text_combinations/style.cljs +++ b/src/quo2/components/text_combinations/style.cljs @@ -2,14 +2,10 @@ (defn container [container-style] - (merge - {:flex 1 - :margin-horizontal 20} - container-style)) + (assoc container-style :margin-horizontal 20)) (def title-container - {:flex 1 - :flex-direction :row + {:flex-direction :row :align-items :center}) (def avatar-container diff --git a/src/status_im2/common/parallax/view.cljs b/src/status_im2/common/parallax/view.cljs index 402144450a..9cffc0579d 100644 --- a/src/status_im2/common/parallax/view.cljs +++ b/src/status_im2/common/parallax/view.cljs @@ -34,8 +34,7 @@ (defn f-video [{:keys [layers disable-parallax? offset stretch container-style enable-looping?] - :or {offset 50 - stretch 0}}] + :or {offset 50 stretch 0}}] [rn/view {:style (style/outer-container container-style)} (map-indexed (fn [idx layer] diff --git a/src/status_im2/contexts/onboarding/common/overlay/events.cljs b/src/status_im2/contexts/onboarding/common/overlay/events.cljs new file mode 100644 index 0000000000..95bc8c6362 --- /dev/null +++ b/src/status_im2/contexts/onboarding/common/overlay/events.cljs @@ -0,0 +1,18 @@ +(ns status-im2.contexts.onboarding.common.overlay.events + (:require [utils.re-frame :as rf] + [status-im2.contexts.onboarding.common.overlay.view :as overlay] + [status-im2.contexts.profile.profiles.view :as profiles] + [re-frame.core :as re-frame])) + +(re-frame/reg-fx + :onboarding/overlay-dismiss-fx + (fn [] + (when-let [blur-dismiss-fn @overlay/blur-dismiss-fn-atom] + (blur-dismiss-fn)) + (when-let [pop-animation-fn @profiles/pop-animation-fn-atom] + (pop-animation-fn)))) + +(rf/defn overlay-dismiss + {:events [:onboarding/overlay-dismiss]} + [_] + {:onboarding/overlay-dismiss-fx nil}) diff --git a/src/status_im2/contexts/onboarding/common/overlay/view.cljs b/src/status_im2/contexts/onboarding/common/overlay/view.cljs index 60284869c5..605efa211a 100644 --- a/src/status_im2/contexts/onboarding/common/overlay/view.cljs +++ b/src/status_im2/contexts/onboarding/common/overlay/view.cljs @@ -35,19 +35,23 @@ 0 (/ constants/onboarding-modal-animation-duration 2) (/ constants/onboarding-modal-animation-duration 2)) + (js/clearInterval @timer-interval) (reset! timer-interval (js/setInterval (fn [] (if (> @blur-amount 0) - (swap! blur-amount - 1) + (swap! blur-amount dec) (js/clearInterval @timer-interval))) (/ constants/onboarding-modal-animation-duration max-blur-amount 2)))) +;; we had to register it here, because of hotreload, overwise on hotreload it will be reseted +(defonce blur-amount (reagent/atom 0)) + (defn f-view - [blur-amount] - (let [opacity (reanimated/use-shared-value 0) + [] + (let [opacity (reanimated/use-shared-value (if (zero? @blur-amount) 0 1)) blur-show-fn #(blur-show opacity blur-amount) blur-dismiss-fn #(blur-dismiss opacity blur-amount)] (rn/use-effect @@ -69,5 +73,4 @@ (defn view [] - (let [blur-amount (reagent/atom 0)] - [:f> f-view blur-amount])) + [:f> f-view]) diff --git a/src/status_im2/contexts/onboarding/create_profile/view.cljs b/src/status_im2/contexts/onboarding/create_profile/view.cljs index 4b65ee1418..830b725bf7 100644 --- a/src/status_im2/contexts/onboarding/create_profile/view.cljs +++ b/src/status_im2/contexts/onboarding/create_profile/view.cljs @@ -136,7 +136,7 @@ {:margin-top navigation-bar-top :background :blur :icon-name :i/arrow-left - :on-press #(rf/dispatch [:navigate-back])}] + :on-press #(rf/dispatch [:navigate-back-within-stack :new-to-status])}] [rn/scroll-view {:on-layout (fn [event] (let [height (oops/oget event "nativeEvent.layout.height")] diff --git a/src/status_im2/contexts/onboarding/enable_biometrics/style.cljs b/src/status_im2/contexts/onboarding/enable_biometrics/style.cljs index 5a5c73fc94..0dc3874d10 100644 --- a/src/status_im2/contexts/onboarding/enable_biometrics/style.cljs +++ b/src/status_im2/contexts/onboarding/enable_biometrics/style.cljs @@ -6,7 +6,7 @@ [insets] {:flex 1 :justify-content :space-between - :padding-top (:top insets)}) + :padding-top (+ (:top insets) 56)}) (defn page-illustration [width] diff --git a/src/status_im2/contexts/onboarding/enable_biometrics/view.cljs b/src/status_im2/contexts/onboarding/enable_biometrics/view.cljs index 560f0c095f..9d2d3bee0e 100644 --- a/src/status_im2/contexts/onboarding/enable_biometrics/view.cljs +++ b/src/status_im2/contexts/onboarding/enable_biometrics/view.cljs @@ -43,31 +43,23 @@ (defn enable-biometrics-parallax [] (let [stretch (if rn/small-screen? 25 40)] - [:<> - [parallax/video - {:layers (:biometrics resources/parallax-video) - :stretch stretch}] - [rn/view - [quo/page-nav {:background :blur}] - [page-title]]])) + [parallax/video + {:layers (:biometrics resources/parallax-video) + :stretch stretch}])) (defn enable-biometrics-simple [] (let [width (:width (rn/get-window))] - [:<> - [rn/view {:flex 1} - [quo/page-nav {:background :blur}] - [page-title] - [rn/view {:style {:flex 1}} - [rn/image - {:resize-mode :contain - :style (style/page-illustration width) - :source (resources/get-image :biometrics)}]]]])) + [rn/image + {:resize-mode :contain + :style (style/page-illustration width) + :source (resources/get-image :biometrics)}])) (defn enable-biometrics [] (let [insets (safe-area/get-insets)] [rn/view {:style (style/page-container insets)} + [page-title] (if whitelist/whitelisted? [enable-biometrics-parallax] [enable-biometrics-simple]) diff --git a/src/status_im2/contexts/onboarding/enable_notifications/view.cljs b/src/status_im2/contexts/onboarding/enable_notifications/view.cljs index 02adb097b7..5f3ed30c20 100644 --- a/src/status_im2/contexts/onboarding/enable_notifications/view.cljs +++ b/src/status_im2/contexts/onboarding/enable_notifications/view.cljs @@ -52,7 +52,7 @@ [quo/page-nav {:background :blur :icon-name :i/arrow-left - :on-press #(rf/dispatch [:navigate-back-within-stack :identifiers])}] + :on-press #(rf/dispatch [:navigate-back-within-stack :new-to-status])}] [page-title] [rn/view {:style style/page-illustration} [quo/text diff --git a/src/status_im2/contexts/onboarding/intro/view.cljs b/src/status_im2/contexts/onboarding/intro/view.cljs index 54112e515d..7b75d25c16 100644 --- a/src/status_im2/contexts/onboarding/intro/view.cljs +++ b/src/status_im2/contexts/onboarding/intro/view.cljs @@ -26,8 +26,8 @@ :animated-heading (i18n/label :t/sign-in-by-syncing) :accessibility-label :already-use-status-button} :bottom-card {:on-press (fn [] - (when @overlay/blur-show-fn-atom - (@overlay/blur-show-fn-atom)) + (when-let [blur-show-fn @overlay/blur-show-fn-atom] + (blur-show-fn)) (rf/dispatch [:open-modal :new-to-status])) :heading (i18n/label :t/new-to-status) :accessibility-label :new-to-status-button}} diff --git a/src/status_im2/contexts/onboarding/new_to_status/view.cljs b/src/status_im2/contexts/onboarding/new_to_status/view.cljs index 6cd39a88be..85009be560 100644 --- a/src/status_im2/contexts/onboarding/new_to_status/view.cljs +++ b/src/status_im2/contexts/onboarding/new_to_status/view.cljs @@ -8,17 +8,8 @@ [status-im2.contexts.onboarding.new-to-status.style :as style] [utils.i18n :as i18n] [utils.re-frame :as rf] - [status-im2.contexts.onboarding.common.overlay.view :as overlay] - [status-im2.contexts.profile.profiles.view :as profiles] - [status-im2.config :as config])) - -(defn navigate-back - [] - (when @overlay/blur-dismiss-fn-atom - (@overlay/blur-dismiss-fn-atom)) - (when @profiles/pop-animation-fn-atom - (@profiles/pop-animation-fn-atom)) - (rf/dispatch [:dismiss-modal :new-to-status])) + [status-im2.config :as config] + re-frame.db)) (defn sign-in-options [] @@ -107,7 +98,9 @@ :type :no-title :background :blur :icon-name :i/arrow-left - :on-press navigate-back + :on-press #(do + (rf/dispatch [:onboarding/overlay-dismiss]) + (rf/dispatch [:navigate-back])) :right-side [{:icon-name :i/info :on-press #(rf/dispatch [:show-bottom-sheet {:content getting-started-doc diff --git a/src/status_im2/contexts/onboarding/sign_in/view.cljs b/src/status_im2/contexts/onboarding/sign_in/view.cljs index 4d52f29b8f..935b6f4efd 100644 --- a/src/status_im2/contexts/onboarding/sign_in/view.cljs +++ b/src/status_im2/contexts/onboarding/sign_in/view.cljs @@ -3,11 +3,6 @@ [status-im2.contexts.onboarding.common.background.view :as background] [status-im2.contexts.syncing.scan-sync-code.view :as scan-sync-code])) -(defn navigate-back - [] - (when @scan-sync-code/navigate-back-fn - (@scan-sync-code/navigate-back-fn))) - (defn view [] [scan-sync-code/view diff --git a/src/status_im2/contexts/profile/profiles/view.cljs b/src/status_im2/contexts/profile/profiles/view.cljs index 7cfd64b6a1..ca062fcfea 100644 --- a/src/status_im2/contexts/profile/profiles/view.cljs +++ b/src/status_im2/contexts/profile/profiles/view.cljs @@ -20,10 +20,13 @@ (defonce push-animation-fn-atom (atom nil)) (defonce pop-animation-fn-atom (atom nil)) +;; we need this for hotreload, overwise on hotreload translate-x will be reseted +(defonce translate-x-atom (atom 0)) (defn push-animation [translate-x] (let [window-width (:width (rn/get-window))] + (reset! translate-x-atom (- window-width)) (reanimated/animate-shared-value-with-delay translate-x (- window-width) constants/onboarding-modal-animation-duration @@ -32,6 +35,7 @@ (defn pop-animation [translate-x] + (reset! translate-x-atom 0) (reanimated/animate-shared-value-with-delay translate-x 0 constants/onboarding-modal-animation-duration @@ -126,7 +130,7 @@ (defn- f-profiles-section [{:keys [set-hide-profiles]}] (let [profiles (vals (rf/sub [:profile/profiles-overview])) - translate-x (reanimated/use-shared-value 0)] + translate-x (reanimated/use-shared-value @translate-x-atom)] (rn/use-effect (fn [] (reset! push-animation-fn-atom #(push-animation translate-x)) (reset! pop-animation-fn-atom #(pop-animation translate-x)) @@ -305,10 +309,12 @@ :container-style {:margin-bottom (+ (safe-area/get-bottom) 12)}} (i18n/label :t/log-in)]])) +;; we had to register it here, because of hotreload, overwise on hotreload it will be reseted +(defonce show-profiles? (reagent/atom false)) + (defn view [] - (let [show-profiles? (reagent/atom false) - set-show-profiles #(reset! show-profiles? true) + (let [set-show-profiles #(reset! show-profiles? true) set-hide-profiles #(reset! show-profiles? false)] (fn [] [:<> diff --git a/src/status_im2/contexts/syncing/scan_sync_code/view.cljs b/src/status_im2/contexts/syncing/scan_sync_code/view.cljs index 8de42e5f77..fb3c9cd0cb 100644 --- a/src/status_im2/contexts/syncing/scan_sync_code/view.cljs +++ b/src/status_im2/contexts/syncing/scan_sync_code/view.cljs @@ -17,7 +17,6 @@ [status-im2.contexts.syncing.scan-sync-code.animation :as animation] [status-im2.contexts.syncing.scan-sync-code.style :as style] [status-im2.contexts.syncing.utils :as sync-utils] - [status-im2.navigation.util :as navigation.util] [utils.debounce :as debounce] [utils.i18n :as i18n] [utils.re-frame :as rf] @@ -28,7 +27,6 @@ (defonce camera-permission-granted? (reagent/atom false)) (defonce dismiss-animations (atom nil)) -(defonce navigate-back-fn (atom nil)) (defn perform-preflight-check "Performing the check for the first time @@ -290,6 +288,7 @@ (defn f-view [_] (let [insets (safe-area/get-insets) + qr-code-succeed? (reagent/atom false) active-tab (reagent/atom 1) qr-view-finder (reagent/atom {}) render-camera? (reagent/atom false) @@ -298,8 +297,7 @@ set-rescan-timeout (fn [] (reset! scan-code? false) (js/setTimeout #(reset! scan-code? true) 3000))] - (fn [{:keys [title show-bottom-view? background animated? qr-code-succeed? - set-qr-code-succeeded]}] + (fn [{:keys [title show-bottom-view? background animated?]}] (let [torch-mode (if @torch? :on :off) flashlight-icon (if @torch? :i/flashlight-on :i/flashlight-off) scan-qr-code-tab? (= @active-tab 1) @@ -309,7 +307,7 @@ (boolean (not-empty @qr-view-finder))) camera-ready-to-scan? (and (or (not animated?) @render-camera?) show-camera? - (not qr-code-succeed?)) + (not @qr-code-succeed?)) title-opacity (reanimated/use-shared-value (if animated? 0 1)) subtitle-opacity (reanimated/use-shared-value (if animated? 0 1)) content-opacity (reanimated/use-shared-value (if animated? 0 1)) @@ -322,10 +320,16 @@ :content-opacity content-opacity :subtitle-opacity subtitle-opacity :title-opacity title-opacity})] + (rn/use-effect #(set-listener-torch-off-on-app-inactive torch?)) (when animated? + (rn/use-effect + (fn [] + (rn/hw-back-add-listener reset-animations-fn) + #(rn/hw-back-remove-listener reset-animations-fn)) + []) (animation/animate-subtitle subtitle-opacity) (animation/animate-title title-opacity) (animation/animate-bottom bottom-view-translate-y)) @@ -337,8 +341,7 @@ (js/setTimeout #(reset! render-camera? true) (+ constants/onboarding-modal-animation-duration constants/onboarding-modal-animation-delay - 300)) - (reset! navigate-back-fn reset-animations-fn)) + 300))) (when-not @camera-permission-granted? (permissions/permission-granted? :camera #(reset! camera-permission-granted? %) @@ -350,7 +353,7 @@ {:torch-mode torch-mode :qr-view-finder @qr-view-finder :scan-code? @scan-code? - :set-qr-code-succeeded set-qr-code-succeeded + :set-qr-code-succeeded #(reset! qr-code-succeed? true) :set-rescan-timeout set-rescan-timeout}]) [rn/view {:style (style/root-container (:top insets))} [:f> header @@ -389,14 +392,5 @@ flashlight-icon])]])))) (defn view - [{:keys [screen-name] :as _props}] - (let [qr-code-succeed? (reagent/atom false)] - (navigation.util/create-class-and-bind - screen-name - {:component-did-appear (fn set-qr-code-failed [_this] - (reset! qr-code-succeed? false))} - (fn [props] - (let [new-pops (assoc props - :qr-code-succeed? @qr-code-succeed? - :set-qr-code-succeeded #(reset! qr-code-succeed? true))] - [:f> f-view new-pops]))))) + [props] + [:f> f-view props]) diff --git a/src/status_im2/events.cljs b/src/status_im2/events.cljs index c061358c59..c430b318e8 100644 --- a/src/status_im2/events.cljs +++ b/src/status_im2/events.cljs @@ -14,6 +14,7 @@ status-im2.contexts.profile.events status-im2.contexts.shell.share.events status-im2.contexts.syncing.events + status-im2.contexts.onboarding.common.overlay.events [status-im2.db :as db] [utils.re-frame :as rf])) diff --git a/src/status_im2/navigation/core.cljs b/src/status_im2/navigation/core.cljs index e9810ac30e..e950a1bba1 100644 --- a/src/status_im2/navigation/core.cljs +++ b/src/status_im2/navigation/core.cljs @@ -48,8 +48,12 @@ (navigation/reg-component-did-appear-listener (fn [view-id] (when (get views/screens view-id) - (set-view-id view-id) + ;;NOTE when back from the background on Android, this event happens for all screens, but we need + ;;only for active one + (when (and @state/curr-modal (= @state/curr-modal view-id)) + (set-view-id view-id)) (when-not @state/curr-modal + (set-view-id view-id) (reset! state/pushed-screen-id view-id))))) (defn dissmissModal @@ -167,18 +171,11 @@ (navigation/reg-button-pressed-listener (fn [id] - (cond - (= "dismiss-modal" id) + (if (= "dismiss-modal" id) (do (when-let [event (get-in views/screens [(last @state/modals) :on-dissmiss])] (re-frame/dispatch event)) (dissmissModal)) - (= "RNN.hardwareBackButton" id) - (when-let [handler (get-in views/screens - [(or (last @state/modals) @state/pushed-screen-id) - :hardware-back-button-handler])] - (handler)) - :else (when-let [handler (get-in views/screens [(keyword id) :right-handler])] (handler))))) diff --git a/src/status_im2/navigation/screens.cljs b/src/status_im2/navigation/screens.cljs index ecc0875be3..2924a14456 100644 --- a/src/status_im2/navigation/screens.cljs +++ b/src/status_im2/navigation/screens.cljs @@ -118,25 +118,24 @@ ;; Onboarding {:name :intro :options {:theme :dark} + :on-focus [:onboarding/overlay-dismiss] :component intro/view} {:name :profiles :options {:theme :dark :layout options/onboarding-layout} + :on-focus [:onboarding/overlay-dismiss] :component profiles/view} - {:name :new-to-status - :options {:theme :dark - :layout options/onboarding-transparent-layout - :animations (merge - transitions/new-to-status-modal-animations - transitions/push-animations-for-transparent-background) - :popGesture false - :modalPresentationStyle :overCurrentContext - :hardwareBackButton {:dismissModalOnPress false - :popStackOnPress false}} - :hardware-back-button-handler new-to-status/navigate-back - :component new-to-status/new-to-status} + {:name :new-to-status + :options {:theme :dark + :layout options/onboarding-transparent-layout + :animations (merge + transitions/new-to-status-modal-animations + transitions/push-animations-for-transparent-background) + :popGesture false + :modalPresentationStyle :overCurrentContext} + :component new-to-status/new-to-status} {:name :create-profile :options {:theme :dark @@ -181,10 +180,7 @@ :layout options/onboarding-transparent-layout :animations (merge transitions/new-to-status-modal-animations transitions/push-animations-for-transparent-background) - :modalPresentationStyle :overCurrentContext - :popGesture false - :hardwareBackButton {:dismissModalOnPress false - :popStackOnPress false}} + :modalPresentationStyle :overCurrentContext} :component enable-notifications/enable-notifications} {:name :identifiers @@ -200,16 +196,13 @@ :options options/dark-screen :component scan-sync-code-page/view} - {:name :sign-in-intro - :options {:layout options/onboarding-transparent-layout - :animations (merge - transitions/sign-in-modal-animations - transitions/push-animations-for-transparent-background) - :modalPresentationStyle :overCurrentContext - :hardwareBackButton {:dismissModalOnPress false - :popStackOnPress false}} - :hardware-back-button-handler sign-in/navigate-back - :component sign-in/animated-view} + {:name :sign-in-intro + :options {:layout options/onboarding-transparent-layout + :animations (merge + transitions/sign-in-modal-animations + transitions/push-animations-for-transparent-background) + :modalPresentationStyle :overCurrentContext} + :component sign-in/animated-view} {:name :sign-in :options {:theme :dark diff --git a/src/status_im2/navigation/util.cljs b/src/status_im2/navigation/util.cljs deleted file mode 100644 index 6fd2867b15..0000000000 --- a/src/status_im2/navigation/util.cljs +++ /dev/null @@ -1,42 +0,0 @@ -(ns status-im2.navigation.util - (:require [react-native.navigation :as navigation] - [reagent.core :as reagent])) - -(defn create-class-and-bind - "Creates a React class that allows the use of life-cycle methods added by - react-native-navigation: - - componentWillAppear - - componentDidAppear - - componentDidDisappear - Receives: - - `component-id` - The component-id to subscribe registered in navigation - - `react-methods` - A map of React methods (kebab-case) -> function handler - - `reagent-render` - A regular reagent function that returns hiccup. - Example: - (defn view - [props & children] - ;; Bindings executed when component is created - (let [qr-code-succeed? (reagent/atom false)] - (create-class-and-bind - \"sign-in-intro\" ; navigation component-id of the screen to subscribe - {:component-did-appear (fn [this] - ;; Executed when component appeared to the screen - ) - :component-will-appear (fn [this] - ;; Executed when component will be shown to the screen - ) - :component-did-disappear (fn [this] - ;; Executed when component disappeared from the screen - )} - (fn [props & children] ; Must be the same signature as this `view` function - ;; Regular component call, e.g.: - [rn/view {:style {:padding-top 10}} - [:f> my-f-component-call (assoc props :on-press identity)] - children])))) - " - [component-id react-methods reagent-render] - (reagent/create-class - (assoc react-methods - :display-name (str component-id "-view") - :component-did-mount #(navigation/bind-component % component-id) - :reagent-render reagent-render)))