wallet UX error fixes and more frequent refreshes

fix wallet errors that were sticking when refresh occured
add separate errors for transaction history fetching with visual feedback
update wallet when going on wallet tab
update transaction list when opening transaction modal
This commit is contained in:
Eric Dvorsak 2017-09-07 19:29:45 +02:00 committed by Roman Volosovskyi
parent 97789feb6b
commit c1cac1eb7c
12 changed files with 219 additions and 166 deletions

View File

@ -20,6 +20,7 @@
(def color-gray6 "#212121") (def color-gray6 "#212121")
(def color-gray7 "#9fa3b4") (def color-gray7 "#9fa3b4")
(def color-gray8 "#6E777E") (def color-gray8 "#6E777E")
(def color-gray9 "#E9EBEC")
(def color-dark "#49545d") (def color-dark "#49545d")
(def color-steel "#838b91") (def color-steel "#838b91")
(def color-white "white") (def color-white "white")

View File

@ -165,8 +165,8 @@
[:start-requesting-discoveries] [:start-requesting-discoveries]
[:remove-old-discoveries!] [:remove-old-discoveries!]
[:set :accounts/creating-account? false] [:set :accounts/creating-account? false]
[:refresh-wallet] [:update-wallet]
[:refresh-transactions] [:update-transactions]
[:get-fcm-token]]})) [:get-fcm-token]]}))
(register-handler-fx (register-handler-fx
@ -270,7 +270,7 @@
;; TODO(oskarth): Put this token in DB ;; TODO(oskarth): Put this token in DB
(register-handler-fx (register-handler-fx
:get-fcm-token :get-fcm-token
(fn [_ _] (fn [_ _]
(notifications/get-fcm-token) (notifications/get-fcm-token)
{})) {}))

View File

@ -5,6 +5,7 @@
[status-im.utils.transactions :as transactions] [status-im.utils.transactions :as transactions]
[status-im.ui.screens.wallet.db :as wallet.db] [status-im.ui.screens.wallet.db :as wallet.db]
[status-im.components.status :as status] [status-im.components.status :as status]
[status-im.ui.screens.wallet.navigation]
[taoensso.timbre :as log])) [taoensso.timbre :as log]))
(defn get-balance [{:keys [web3 account-id on-success on-error]}] (defn get-balance [{:keys [web3 account-id on-success on-error]}]
@ -18,73 +19,72 @@
(on-error err)))) (on-error err))))
(on-error "web3 or account-id not available"))) (on-error "web3 or account-id not available")))
(defn assoc-error-message [db error-type err]
(assoc-in db [:wallet :errors error-type] (or (when err (str err))
:unknown-error)))
(defn clear-error-message [db error-type]
(update-in db [:wallet :errors] dissoc error-type))
;; FX ;; FX
(reg-fx (reg-fx
:get-balance :get-balance
(fn [{:keys [web3 account-id success-event error-event]}] (fn [{:keys [web3 account-id success-event error-event]}]
(get-balance (get-balance {:web3 web3
{:web3 web3 :account-id account-id
:account-id account-id :on-success #(dispatch [success-event %])
:on-success #(dispatch [success-event %]) :on-error #(dispatch [error-event %])})))
:on-error #(dispatch [error-event %])})))
(reg-fx (reg-fx
:get-transactions :get-transactions
(fn [{:keys [network account-id]}] (fn [{:keys [network account-id success-event error-event]}]
(transactions/get-transactions network (transactions/get-transactions network
account-id account-id
#(dispatch [:update-transactions-succes %]) #(dispatch [success-event %])
#(dispatch [:update-transactions-fail %])))) #(dispatch [error-event %]))))
;; TODO(oskarth): At some point we want to get list of relevant assets to get prices for
(reg-fx (reg-fx
:get-prices :get-prices
(fn [{:keys [from to success-event error-event]}] (fn [{:keys [from to success-event error-event]}]
(prices/get-prices (prices/get-prices from
from to
to #(dispatch [success-event %])
#(dispatch [success-event %]) #(dispatch [error-event %]))))
#(dispatch [error-event %]))))
;; Handlers ;; Handlers
;; TODO(oskarth): At some point we want to get list of relevant assets to get prices for
(handlers/register-handler-fx (handlers/register-handler-fx
:load-prices :update-wallet
(fn [{{:keys [wallet] :as db} :db} [_ a]]
{:get-prices {:from "ETH"
:to "USD"
:success-event :update-prices
:error-event :update-prices-fail}
:db (assoc db :prices-loading? true)}))
(handlers/register-handler-fx
:refresh-wallet
(fn [{{:keys [web3 accounts/current-account-id network] :as db} :db} [_ a]] (fn [{{:keys [web3 accounts/current-account-id network] :as db} :db} [_ a]]
{:get-balance {:web3 web3 {:get-balance {:web3 web3
:account-id current-account-id :account-id current-account-id
:success-event :update-balance :success-event :update-balance-success
:error-event :update-balance-fail} :error-event :update-balance-fail}
:dispatch [:load-prices] :get-prices {:from "ETH"
:db (assoc-in db [:wallet :balance-loading?] true)})) :to "USD"
:success-event :update-prices-success
(defn assoc-error-message [db err] :error-event :update-prices-fail}
(assoc-in db [:wallet :wallet/error] err)) :db (-> db
(clear-error-message :price-update)
(handlers/register-handler-db (clear-error-message :balance-update)
:wallet/clear-error-message (assoc-in [:wallet :balance-loading?] true)
(fn [db [_]] (assoc :prices-loading? true))}))
(update db :wallet dissoc :wallet/error)))
(handlers/register-handler-fx (handlers/register-handler-fx
:refresh-transactions :update-transactions
(fn [{{:keys [accounts/current-account-id network] :as db} :db} _] (fn [{{:keys [accounts/current-account-id network] :as db} :db} _]
{:get-transactions {:account-id current-account-id {:get-transactions {:account-id current-account-id
:network network} :network network
:db (assoc-in db [:wallet :transactions-loading?] true)})) :success-event :update-transactions-success
:error-event :update-transactions-fail}
:db (-> db
(clear-error-message :transaction-update)
(assoc-in [:wallet :transactions-loading?] true))}))
(handlers/register-handler-db (handlers/register-handler-db
:update-transactions-succes :update-transactions-success
(fn [db [_ transactions]] (fn [db [_ transactions]]
(-> db (-> db
(assoc-in [:wallet :transactions] transactions) (assoc-in [:wallet :transactions] transactions)
@ -94,31 +94,36 @@
:update-transactions-fail :update-transactions-fail
(fn [db [_ err]] (fn [db [_ err]]
(log/debug "Unable to get transactions: " err) (log/debug "Unable to get transactions: " err)
(-> (assoc-error-message db :error) (-> db
(assoc-error-message :transactions-update err)
(assoc-in [:wallet :transactions-loading?] false)))) (assoc-in [:wallet :transactions-loading?] false))))
(handlers/register-handler-db (handlers/register-handler-db
:update-balance :update-balance-success
(fn [db [_ balance]] (fn [db [_ balance]]
(-> db (-> db
(assoc-in [:wallet :balance] balance) (assoc-in [:wallet :balance] balance)
(assoc-in [:wallet :balance-loading?] false)))) (assoc-in [:wallet :balance-loading?] false))))
(handlers/register-handler-db
:update-prices
(fn [db [_ prices]]
(assoc db :prices prices :prices-loading? false)))
(handlers/register-handler-db (handlers/register-handler-db
:update-balance-fail :update-balance-fail
(fn [db [_ err]] (fn [db [_ err]]
(log/debug "Unable to get balance: " err) (log/debug "Unable to get balance: " err)
(-> (assoc-error-message db :error) (-> db
(assoc-error-message :balance-update err)
(assoc-in [:wallet :balance-loading?] false)))) (assoc-in [:wallet :balance-loading?] false))))
(handlers/register-handler-db
:update-prices-success
(fn [db [_ prices]]
(assoc db
:prices prices
:prices-loading? false)))
(handlers/register-handler-db (handlers/register-handler-db
:update-prices-fail :update-prices-fail
(fn [db [_ err]] (fn [db [_ err]]
(log/debug "Unable to get prices: " err) (log/debug "Unable to get prices: " err)
(-> (assoc-error-message db :error) (-> db
(assoc :prices-loading? false)))) (assoc-error-message :prices-update err)
(assoc :prices-loading? false))))

View File

@ -1,14 +1,29 @@
(ns status-im.ui.screens.wallet.history.styles (ns status-im.ui.screens.wallet.history.styles
(:require [status-im.components.styles :as st])) (:require [status-im.components.styles :as styles]))
(def error-container
{:align-self :center
:justify-content :center
:border-radius 4
:padding-vertical 4
:flex-direction :row
:background-color styles/color-gray9})
(def error-message
{:color styles/color-black
:padding-top 3
:padding-right 10
:font-size 13})
(def wallet-transactions-container (def wallet-transactions-container
{:flex 1 {:flex 1
:background-color st/color-white}) :background-color styles/color-white})
(def main-section (def main-section
{:flex 1 {:flex 1
:position :relative :position :relative
:background-color st/color-white}) :background-color styles/color-white})
(def empty-text (def empty-text
{:text-align :center {:text-align :center
@ -24,11 +39,11 @@
{:flex 1 {:flex 1
:flex-direction :column :flex-direction :column
:justify-content :center :justify-content :center
:background-color st/color-gray-transparent}) :background-color styles/color-gray-transparent})
(def sign-all-popup (def sign-all-popup
{:align-self :flex-start {:align-self :flex-start
:background-color st/color-white :background-color styles/color-white
:margin-horizontal 12 :margin-horizontal 12
:border-radius 8}) :border-radius 8})
@ -38,7 +53,7 @@
:margin-horizontal 12 :margin-horizontal 12
:text-align :center :text-align :center
:padding-vertical 9 :padding-vertical 9
:background-color st/color-light-gray}) :background-color styles/color-light-gray})
(def sign-all-popup-text (def sign-all-popup-text
{:margin-top 8 {:margin-top 8
@ -64,4 +79,4 @@
(defn transaction-icon-background [color] (defn transaction-icon-background [color]
{:border-radius 32 {:border-radius 32
:background-color st/color-blue4-transparent}) :background-color styles/color-blue4-transparent})

View File

@ -1,18 +1,18 @@
(ns status-im.ui.screens.wallet.history.views (ns status-im.ui.screens.wallet.history.views
(:require-macros [status-im.utils.views :refer [defview letsubs]]) (:require [re-frame.core :as re-frame]
(:require [reagent.core :as r] [reagent.core :as reagent]
[re-frame.core :as rf] [status-im.components.button.view :as button]
[status-im.components.button.view :as btn] [status-im.components.checkbox.view :as checkbox]
[status-im.components.checkbox.view :as chk]
[status-im.components.react :as rn]
[status-im.components.list.views :as list] [status-im.components.list.views :as list]
[status-im.components.tabs.styles :as tst] [status-im.components.react :as react]
[status-im.components.tabs.styles :as tabs.styles]
[status-im.components.tabs.views :as tabs] [status-im.components.tabs.views :as tabs]
[status-im.components.toolbar-new.actions :as act]
[status-im.components.toolbar-new.view :as toolbar] [status-im.components.toolbar-new.view :as toolbar]
[status-im.ui.screens.wallet.history.styles :as history-styles] [status-im.i18n :as i18n]
[status-im.utils.utils :as utils] [status-im.ui.screens.wallet.history.styles :as history.styles]
[status-im.i18n :as i18n])) [status-im.ui.screens.wallet.views :as wallet.views]
[status-im.utils.utils :as utils])
(:require-macros [status-im.utils.views :refer [defview letsubs]]))
(defn on-sign-transaction (defn on-sign-transaction
[m] [m]
@ -25,13 +25,13 @@
(utils/show-popup "TODO" "Delete Transaction")) (utils/show-popup "TODO" "Delete Transaction"))
(defn unsigned-action [] (defn unsigned-action []
[toolbar/text-action #(rf/dispatch [:navigate-to-modal :wallet-transactions-sign-all]) [toolbar/text-action #(re-frame/dispatch [:navigate-to-modal :wallet-transactions-sign-all])
(i18n/label :t/transactions-sign-all)]) (i18n/label :t/transactions-sign-all)])
(def history-action (def history-action
{:icon :icons/filter {:icon :icons/filter
:icon-opts {} :icon-opts {}
:handler #(utils/show-popup "TODO" "Not implemented") #_(rf/dispatch [:navigate-to-modal :wallet-transactions-sign-all])}) :handler #(utils/show-popup "TODO" "Not implemented") #_(re-frame/dispatch [:navigate-to-modal :wallet-transactions-sign-all])})
(defn toolbar-view [view-id] (defn toolbar-view [view-id]
[toolbar/toolbar2 {} [toolbar/toolbar2 {}
@ -43,14 +43,14 @@
[history-action]])]) [history-action]])])
(defn action-buttons [m] (defn action-buttons [m]
[rn/view {:style history-styles/action-buttons} [react/view {:style history.styles/action-buttons}
[btn/primary-button {:text (i18n/label :t/transactions-sign) :on-press #(on-sign-transaction m)}] [button/primary-button {:text (i18n/label :t/transactions-sign) :on-press #(on-sign-transaction m)}]
[btn/secondary-button {:text (i18n/label :t/delete) :on-press #(on-delete-transaction m)}]]) [button/secondary-button {:text (i18n/label :t/delete) :on-press #(on-delete-transaction m)}]])
(defn- unsigned? [type] (= "unsigned" type)) (defn- unsigned? [type] (= "unsigned" type))
(defn- inbound? [type] (= "inbound" type)) (defn- inbound? [type] (= "inbound" type))
(defn- transaction-icon [k color] {:icon k :style (history-styles/transaction-icon-background color)}) (defn- transaction-icon [k color] {:icon k :style (history.styles/transaction-icon-background color)})
(defn- transaction-type->icon [s] (defn- transaction-type->icon [s]
(case s (case s
@ -74,23 +74,24 @@
[list/item-icon {:icon :icons/forward}]]) [list/item-icon {:icon :icons/forward}]])
;; TODO(yenda) hook with re-frame ;; TODO(yenda) hook with re-frame
(defn empty-text [s] (defn empty-text [s]
[rn/text {:style history-styles/empty-text} s]) [react/text {:style history.styles/empty-text} s])
(defview history-list [] (defview history-list []
(letsubs [transactions-history-list [:wallet/transactions-history-list] (letsubs [transactions-history-list [:wallet/transactions-history-list]
transactions-loading? [:wallet/transactions-loading?]] transactions-loading? [:wallet/transactions-loading?]
[rn/scroll-view error-message [:wallet.transactions/error-message?]]
[react/scroll-view
(when error-message [wallet.views/error-message-view history.styles/error-container history.styles/error-message])
[list/section-list {:sections transactions-history-list [list/section-list {:sections transactions-history-list
:render-fn render-transaction :render-fn render-transaction
:empty-component (empty-text (i18n/label :t/transactions-history-empty)) :empty-component (empty-text (i18n/label :t/transactions-history-empty))
:on-refresh #(rf/dispatch [:refresh-transactions]) :on-refresh #(re-frame/dispatch [:update-transactions])
:refreshing transactions-loading?}]])) :refreshing transactions-loading?}]]))
(defview unsigned-list [transactions] (defview unsigned-list [transactions]
[] []
[rn/scroll-view [react/scroll-view
[list/flat-list {:data transactions [list/flat-list {:data transactions
:render-fn render-transaction :render-fn render-transaction
:empty-component (empty-text (i18n/label :t/transactions-unsigned-empty))}]]) :empty-component (empty-text (i18n/label :t/transactions-unsigned-empty))}]])
@ -117,19 +118,19 @@
(defview sign-all [] (defview sign-all []
[] []
[rn/keyboard-avoiding-view {:style history-styles/sign-all-view} [react/keyboard-avoiding-view {:style history.styles/sign-all-view}
[rn/view {:style history-styles/sign-all-done} [react/view {:style history.styles/sign-all-done}
[btn/primary-button {:style history-styles/sign-all-done-button [button/primary-button {:style history.styles/sign-all-done-button
:text (i18n/label :t/done) :text (i18n/label :t/done)
:on-press #(rf/dispatch [:navigate-back])}]] :on-press #(re-frame/dispatch [:navigate-back])}]]
[rn/view {:style history-styles/sign-all-popup} [react/view {:style history.styles/sign-all-popup}
[rn/text {:style history-styles/sign-all-popup-sign-phrase} "one two three"] ;; TODO hook [react/text {:style history.styles/sign-all-popup-sign-phrase} "one two three"] ;; TODO hook
[rn/text {:style history-styles/sign-all-popup-text} (i18n/label :t/transactions-sign-all-text)] [react/text {:style history.styles/sign-all-popup-text} (i18n/label :t/transactions-sign-all-text)]
[rn/view {:style history-styles/sign-all-actions} [react/view {:style history.styles/sign-all-actions}
[rn/text-input {:style history-styles/sign-all-input [react/text-input {:style history.styles/sign-all-input
:secure-text-entry true :secure-text-entry true
:placeholder (i18n/label :t/transactions-sign-input-placeholder)}] :placeholder (i18n/label :t/transactions-sign-input-placeholder)}]
[btn/primary-button {:text (i18n/label :t/transactions-sign-all) :on-press #(on-sign-transaction %)}]]]]) [button/primary-button {:text (i18n/label :t/transactions-sign-all) :on-press #(on-sign-transaction %)}]]]])
;; Filter history ;; Filter history
@ -137,13 +138,13 @@
[list/item [list/item
[list/item-icon (transaction-type->icon "pending")] ;; TODO add proper token data [list/item-icon (transaction-type->icon "pending")] ;; TODO add proper token data
[list/item-content label symbol] [list/item-content label symbol]
[chk/checkbox {:checked? true #_checked?}]]) [checkbox/checkbox {:checked? true #_checked?}]])
(defn- item-type [{:keys [id label checked?]}] (defn- item-type [{:keys [id label checked?]}]
[list/item [list/item
[list/item-icon (transaction-type->icon id)] [list/item-icon (transaction-type->icon id)]
[list/item-content label] [list/item-content label]
[chk/checkbox checked?]]) [checkbox/checkbox checked?]])
(def filter-data (def filter-data
[{:title (i18n/label :t/transactions-filter-tokens) [{:title (i18n/label :t/transactions-filter-tokens)
@ -163,13 +164,13 @@
(defview filter-history [] (defview filter-history []
[] []
[rn/view [react/view
[toolbar/toolbar2 {} [toolbar/toolbar2 {}
[toolbar/nav-clear-text (i18n/label :t/done)] [toolbar/nav-clear-text (i18n/label :t/done)]
[toolbar/content-title (i18n/label :t/transactions-filter-title)] [toolbar/content-title (i18n/label :t/transactions-filter-title)]
[toolbar/text-action #(utils/show-popup "TODO" "Select All") [toolbar/text-action #(utils/show-popup "TODO" "Select All")
(i18n/label :t/transactions-filter-select-all)]] (i18n/label :t/transactions-filter-select-all)]]
[rn/scroll-view [react/scroll-view
[list/section-list {:sections filter-data}]]]) [list/section-list {:sections filter-data}]]])
;; TODO(jeluard) whole swipe logic ;; TODO(jeluard) whole swipe logic
@ -177,10 +178,10 @@
(defn- main-section [view-id unsigned-transactions] (defn- main-section [view-id unsigned-transactions]
(let [tabs (tab-list unsigned-transactions)] (let [tabs (tab-list unsigned-transactions)]
[rn/view {:style history-styles/main-section} [react/view {:style history.styles/main-section}
[tabs/tabs {:selected-view-id @view-id [tabs/tabs {:selected-view-id @view-id
:tab-list tabs}] :tab-list tabs}]
[rn/swiper (merge tst/swiper [react/swiper (merge tabs.styles/swiper
{:index (get-tab-index tabs @view-id) {:index (get-tab-index tabs @view-id)
:loop false}) :loop false})
;:ref #(reset! swiper %) ;:ref #(reset! swiper %)
@ -193,8 +194,8 @@
;; TODO(yenda) must reflect selected wallet ;; TODO(yenda) must reflect selected wallet
(defview transactions [] (defview transactions []
[unsigned-transactions [:wallet/unsigned-transactions]] (letsubs [unsigned-transactions [:wallet/unsigned-transactions]]
(let [view-id (r/atom :wallet-transactions-history)] (let [view-id (reagent/atom :wallet-transactions-history)]
[rn/view {:style history-styles/wallet-transactions-container} [react/view {:style history.styles/wallet-transactions-container}
[toolbar-view view-id] [toolbar-view view-id]
[main-section view-id unsigned-transactions]])) [main-section view-id unsigned-transactions]])))

View File

@ -1,39 +1,26 @@
(ns status-im.ui.screens.wallet.main.styles (ns status-im.ui.screens.wallet.main.styles
(:require [status-im.components.styles :as st] (:require [status-im.components.styles :as styles]
[status-im.utils.platform :as platform])) [status-im.utils.platform :as platform]))
(def wallet-container (def wallet-container
{:flex 1 {:flex 1
:background-color st/color-white}) :background-color styles/color-white})
(def wallet-error-container (def error-container
{:align-self :center {:align-self :center
:justify-content :center :justify-content :center
:border-radius 20 :border-radius 20
:flex-direction :row :flex-direction :row
:background-color st/color-blue5}) :background-color styles/color-blue5})
(def wallet-exclamation-container (def error-message
{:background-color st/color-red-2 {:color styles/color-white
:justify-content :center
:margin-top 5
:margin-left 10
:margin-right 7
:margin-bottom 5
:border-radius 100})
(def wallet-error-exclamation
{:width 16
:height 16})
(def wallet-error-message
{:color st/color-white
:padding-top 3 :padding-top 3
:padding-right 10 :padding-right 10
:font-size 13}) :font-size 13})
(def toolbar (def toolbar
{:background-color st/color-blue5 {:background-color styles/color-blue5
:elevation 0}) :elevation 0})
(def toolbar-title-container (def toolbar-title-container
@ -45,7 +32,7 @@
{:flex-direction :row}) {:flex-direction :row})
(def toolbar-title-text (def toolbar-title-text
{:color st/color-white {:color styles/color-white
:font-size 17 :font-size 17
:margin-right 4}) :margin-right 4})
@ -69,7 +56,7 @@
(def main-section (def main-section
{:padding 16 {:padding 16
:background-color st/color-blue4}) :background-color styles/color-blue4})
(def total-balance-container (def total-balance-container
{:margin-top 18 {:margin-top 18
@ -81,12 +68,12 @@
(def total-balance-value (def total-balance-value
{:font-size 37 {:font-size 37
:color st/color-white}) :color styles/color-white})
(def total-balance-currency (def total-balance-currency
{:font-size 37 {:font-size 37
:margin-left 9 :margin-left 9
:color st/color-white :color styles/color-white
:opacity 0.4}) :opacity 0.4})
(def value-variation (def value-variation
@ -95,7 +82,7 @@
(def value-variation-title (def value-variation-title
{:font-size 14 {:font-size 14
:color st/color-white :color styles/color-white
:opacity 0.6}) :opacity 0.6})
(def today-variation-container (def today-variation-container
@ -106,22 +93,22 @@
(def today-variation-container-positive (def today-variation-container-positive
(merge today-variation-container (merge today-variation-container
{:background-color st/color-green-1})) {:background-color styles/color-green-1}))
(def today-variation-container-negative (def today-variation-container-negative
(merge today-variation-container (merge today-variation-container
{:background-color st/color-red-3})) {:background-color styles/color-red-3}))
(def today-variation (def today-variation
{:font-size 12}) {:font-size 12})
(def today-variation-positive (def today-variation-positive
(merge today-variation (merge today-variation
{:color st/color-green-2})) {:color styles/color-green-2}))
(def today-variation-negative (def today-variation-negative
(merge today-variation (merge today-variation
{:color st/color-red-4})) {:color styles/color-red-4}))
(def buttons (def buttons
{:margin-top 34}) {:margin-top 34})
@ -131,13 +118,13 @@
;;;;;;;;;;;;;;;;;;;; ;;;;;;;;;;;;;;;;;;;;
(def asset-section (def asset-section
{:background-color st/color-white {:background-color styles/color-white
:padding-vertical 16}) :padding-vertical 16})
(def asset-section-title (def asset-section-title
{:font-size 14 {:font-size 14
:margin-left 16 :margin-left 16
:color st/color-gray4}) :color styles/color-gray4})
(def asset-item-value-container (def asset-item-value-container
{:flex 1 {:flex 1
@ -146,20 +133,20 @@
(def asset-item-value (def asset-item-value
{:font-size 16 {:font-size 16
:color st/color-black}) :color styles/color-black})
(def add-asset-icon (def add-asset-icon
{:border-radius 32 {:border-radius 32
:background-color st/color-blue4-transparent}) :background-color styles/color-blue4-transparent})
(def add-asset-text (def add-asset-text
{:font-size 16 {:font-size 16
:color st/color-blue4}) :color styles/color-blue4})
(def asset-item-currency (def asset-item-currency
{:font-size 16 {:font-size 16
:color st/color-gray4 :color styles/color-gray4
:margin-left 6}) :margin-left 6})
(defn asset-border [color] (defn asset-border [color]
{:border-color color :border-width 1 :border-radius 32}) {:border-color color :border-width 1 :border-radius 32})

View File

@ -17,6 +17,7 @@
[status-im.utils.platform :as platform] [status-im.utils.platform :as platform]
[status-im.utils.utils :as utils] [status-im.utils.utils :as utils]
[status-im.ui.screens.wallet.main.styles :as wallet-styles] [status-im.ui.screens.wallet.main.styles :as wallet-styles]
[status-im.ui.screens.wallet.views :as wallet.views]
[status-im.utils.money :as money])) [status-im.utils.money :as money]))
(defn- show-not-implemented! [] (defn- show-not-implemented! []
@ -47,16 +48,9 @@
[(assoc (act/opts [{:text (i18n/label :t/wallet-settings) :value show-not-implemented!}]) :icon-opts {:color :white}) [(assoc (act/opts [{:text (i18n/label :t/wallet-settings) :value show-not-implemented!}]) :icon-opts {:color :white})
transaction-history-action]]]) transaction-history-action]]])
(defn error-message-view [error-message]
[rn/view {:style wallet-styles/wallet-error-container}
[rn/view {:style wallet-styles/wallet-exclamation-container}
[vi/icon :icons/exclamation_mark {:color :white
:container-style wallet-styles/wallet-error-exclamation}]]
[rn/text {:style wallet-styles/wallet-error-message} (i18n/label :t/wallet-error)]])
(defn main-section [usd-value change error-message] (defn main-section [usd-value change error-message]
[rn/view {:style wallet-styles/main-section} [rn/view {:style wallet-styles/main-section}
(when error-message [error-message-view error-message]) (when error-message [wallet.views/error-message-view wallet-styles/error-container wallet-styles/error-message])
[rn/view {:style wallet-styles/total-balance-container} [rn/view {:style wallet-styles/total-balance-container}
[rn/view {:style wallet-styles/total-balance} [rn/view {:style wallet-styles/total-balance}
[rn/text {:style wallet-styles/total-balance-value} usd-value] [rn/text {:style wallet-styles/total-balance-value} usd-value]
@ -125,7 +119,7 @@
:data [{}] :data [{}]
:renderItem (list/wrap-render-fn render-add-asset-fn)}] :renderItem (list/wrap-render-fn render-add-asset-fn)}]
:render-section-header-fn #() :render-section-header-fn #()
:on-refresh #(rf/dispatch [:refresh-wallet]) :on-refresh #(rf/dispatch [:update-wallet])
:refreshing (or prices-loading? balance-loading?)}]])) :refreshing (or prices-loading? balance-loading?)}]]))
(defview wallet [] (defview wallet []
@ -134,7 +128,7 @@
portfolio-change [:portfolio-change] portfolio-change [:portfolio-change]
prices-loading? [:prices-loading?] prices-loading? [:prices-loading?]
balance-loading? [:wallet/balance-loading?] balance-loading? [:wallet/balance-loading?]
error-message [:wallet/error-message]] error-message [:wallet/error-message?]]
[rn/view {:style wallet-styles/wallet-container} [rn/view {:style wallet-styles/wallet-container}
[toolbar-view] [toolbar-view]
[rn/scroll-view [rn/scroll-view

View File

@ -0,0 +1,13 @@
(ns status-im.ui.screens.wallet.navigation
(:require [re-frame.core :as re-frame]
[status-im.ui.screens.navigation :as navigation]))
(defmethod navigation/preload-data! :wallet
[db _]
(re-frame/dispatch [:update-wallet])
db)
(defmethod navigation/preload-data! :wallet-transactions
[db _]
(re-frame/dispatch [:update-transactions])
db)

View File

@ -0,0 +1,15 @@
(ns status-im.ui.screens.wallet.styles
(:require [status-im.components.styles :as st]))
(def wallet-exclamation-container
{:background-color st/color-red-2
:justify-content :center
:margin-top 5
:margin-left 10
:margin-right 7
:margin-bottom 5
:border-radius 100})
(def wallet-error-exclamation
{:width 16
:height 16})

View File

@ -16,9 +16,14 @@
(fn [db] (fn [db]
(get-in db [:prices :last-day]))) (get-in db [:prices :last-day])))
(reg-sub :wallet/error-message (reg-sub :wallet/error-message?
(fn [db] (fn [db]
(get-in db [:wallet :wallet/error]))) (or (get-in db [:wallet :errors :balance-update])
(get-in db [:wallet :errors :prices-update]))))
(reg-sub :wallet.transactions/error-message?
(fn [db]
(get-in db [:wallet :errors :transactions-update])))
(reg-sub :eth-balance (reg-sub :eth-balance
:<- [:balance] :<- [:balance]

View File

@ -0,0 +1,12 @@
(ns status-im.ui.screens.wallet.views
(:require [status-im.components.react :as react]
[status-im.ui.screens.wallet.styles :as styles]
[status-im.components.icons.vector-icons :as vector-icons]
[status-im.i18n :as i18n]))
(defn error-message-view [error-container-style error-message-style]
[react/view {:style error-container-style}
[react/view {:style styles/wallet-exclamation-container}
[vector-icons/icon :icons/exclamation_mark {:color :white
:container-style styles/wallet-error-exclamation}]]
[react/text {:style error-message-style} (i18n/label :t/wallet-error)]])

View File

@ -14,15 +14,20 @@
clear-error" clear-error"
(run-test-sync (run-test-sync
(re-frame/reg-fx ::events/init-store #()) (re-frame/reg-fx ::events/init-store #())
(re-frame/reg-fx :get-prices #())
(re-frame/reg-fx :get-balance #())
(re-frame/dispatch [:initialize-db]) (re-frame/dispatch [:initialize-db])
(let [error (re-frame/subscribe [:wallet/error-message]) (let [error (re-frame/subscribe [:wallet/error-message?])
message :error] message "failed balance update"]
(re-frame/dispatch [:update-balance-fail message]) (re-frame/dispatch [:update-balance-fail message])
(is (= message @error))) (is (= message @error)))
(let [error (re-frame/subscribe [:wallet/error-message]) (let [error (re-frame/subscribe [:wallet/error-message?])]
message :error] (re-frame/dispatch [:update-wallet])
(is (nil? @error)))
(let [error (re-frame/subscribe [:wallet/error-message?])
message "failed price update"]
(re-frame/dispatch [:update-prices-fail message]) (re-frame/dispatch [:update-prices-fail message])
(is (= message @error))) (is (= message @error))))
(let [error (re-frame/subscribe [:wallet/error-message])] (let [error (re-frame/subscribe [:wallet/error-message?])]
(re-frame/dispatch [:wallet/clear-error-message]) (re-frame/dispatch [:update-wallet])
(is (nil? @error))))) (is (nil? @error))))