aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorDan J Miller <danjm.com@gmail.com>2019-01-30 20:16:12 +0800
committerWhymarrh Whitby <whymarrh.whitby@gmail.com>2019-01-30 20:16:12 +0800
commit02bdbbbc3e2d349ddde5657069ec6dda15fc6668 (patch)
tree09c2f2dad8263695dee5f49b0ae30c6b59503205
parentdf3169d1c7250d13bb8bc123dc91f7913ad75a81 (diff)
downloadtangerine-wallet-browser-02bdbbbc3e2d349ddde5657069ec6dda15fc6668.tar
tangerine-wallet-browser-02bdbbbc3e2d349ddde5657069ec6dda15fc6668.tar.gz
tangerine-wallet-browser-02bdbbbc3e2d349ddde5657069ec6dda15fc6668.tar.bz2
tangerine-wallet-browser-02bdbbbc3e2d349ddde5657069ec6dda15fc6668.tar.lz
tangerine-wallet-browser-02bdbbbc3e2d349ddde5657069ec6dda15fc6668.tar.xz
tangerine-wallet-browser-02bdbbbc3e2d349ddde5657069ec6dda15fc6668.tar.zst
tangerine-wallet-browser-02bdbbbc3e2d349ddde5657069ec6dda15fc6668.zip
Add visual indicator when displaying a cached balance (#5854)
-rw-r--r--app/_locales/en/messages.json3
-rw-r--r--development/states/confirm-sig-requests.json1
-rw-r--r--development/states/currency-localization.json1
-rw-r--r--development/states/send-edit.json1
-rw-r--r--development/states/send-new-ui.json1
-rw-r--r--development/states/tx-list-items.json1
-rw-r--r--test/data/mock-state.json1
-rw-r--r--test/unit/ui/app/selectors.spec.js1
-rw-r--r--ui/app/components/currency-display/currency-display.component.js7
-rw-r--r--ui/app/components/send/account-list-item/account-list-item.component.js42
-rw-r--r--ui/app/components/send/account-list-item/account-list-item.container.js4
-rw-r--r--ui/app/components/send/account-list-item/tests/account-list-item-component.test.js1
-rw-r--r--ui/app/components/send/account-list-item/tests/account-list-item-container.test.js4
-rw-r--r--ui/app/components/send/tests/send-selectors-test-data.js1
-rw-r--r--ui/app/components/tooltip-v2.js6
-rw-r--r--ui/app/components/transaction-view-balance/index.scss18
-rw-r--r--ui/app/components/transaction-view-balance/transaction-view-balance.component.js47
-rw-r--r--ui/app/components/transaction-view-balance/transaction-view-balance.container.js2
-rw-r--r--ui/app/components/user-preferenced-currency-display/user-preferenced-currency-display.component.js1
-rw-r--r--ui/app/css/itcss/components/account-dropdown.scss29
-rw-r--r--ui/app/css/itcss/settings/variables.scss1
-rw-r--r--ui/app/selectors.js19
22 files changed, 161 insertions, 31 deletions
diff --git a/app/_locales/en/messages.json b/app/_locales/en/messages.json
index 7810c6eb4..33e72cd83 100644
--- a/app/_locales/en/messages.json
+++ b/app/_locales/en/messages.json
@@ -139,6 +139,9 @@
"balance": {
"message": "Balance"
},
+ "balanceOutdated": {
+ "message": "Balance may be outdated"
+ },
"balances": {
"message": "Token balance(s)"
},
diff --git a/development/states/confirm-sig-requests.json b/development/states/confirm-sig-requests.json
index 613112ec9..aa3e8dfdf 100644
--- a/development/states/confirm-sig-requests.json
+++ b/development/states/confirm-sig-requests.json
@@ -23,6 +23,7 @@
"name": "Send Account 4"
}
},
+ "cachedBalances": {},
"unapprovedTxs": {},
"currentCurrency": "USD",
"conversionRate": 1200.88200327,
diff --git a/development/states/currency-localization.json b/development/states/currency-localization.json
index a4ca19eb6..7dd1a135d 100644
--- a/development/states/currency-localization.json
+++ b/development/states/currency-localization.json
@@ -23,6 +23,7 @@
"name": "Send Account 4"
}
},
+ "cachedBalances": {},
"unapprovedTxs": {},
"currentCurrency": "USD",
"conversionRate": 19855,
diff --git a/development/states/send-edit.json b/development/states/send-edit.json
index 0157dece4..f617910f1 100644
--- a/development/states/send-edit.json
+++ b/development/states/send-edit.json
@@ -23,6 +23,7 @@
"name": "Send Account 4"
}
},
+ "cachedBalances": {},
"assetImages": {},
"unapprovedTxs": {},
"currentCurrency": "USD",
diff --git a/development/states/send-new-ui.json b/development/states/send-new-ui.json
index 88bffbd48..bb4d80c5c 100644
--- a/development/states/send-new-ui.json
+++ b/development/states/send-new-ui.json
@@ -23,6 +23,7 @@
"name": "Send Account 4"
}
},
+ "cachedBalances": {},
"unapprovedTxs": {},
"currentCurrency": "USD",
"conversionRate": 1200.88200327,
diff --git a/development/states/tx-list-items.json b/development/states/tx-list-items.json
index 24daf3254..7939e3d94 100644
--- a/development/states/tx-list-items.json
+++ b/development/states/tx-list-items.json
@@ -23,6 +23,7 @@
"name": "Send Account 4"
}
},
+ "cachedBalances": {},
"currentCurrency": "USD",
"conversionRate": 1200.88200327,
"conversionDate": 1489013762,
diff --git a/test/data/mock-state.json b/test/data/mock-state.json
index 8deff5531..671697182 100644
--- a/test/data/mock-state.json
+++ b/test/data/mock-state.json
@@ -11,6 +11,7 @@
"name": "Test Account 2"
}
},
+ "cachedBalances": {},
"unapprovedTxs": {
"8393540981007587": {
"id": 8393540981007587,
diff --git a/test/unit/ui/app/selectors.spec.js b/test/unit/ui/app/selectors.spec.js
index e2b198abf..070de0bcd 100644
--- a/test/unit/ui/app/selectors.spec.js
+++ b/test/unit/ui/app/selectors.spec.js
@@ -19,6 +19,7 @@ describe('Selectors', function () {
'address': '0x0dcd5d886577d5081b0c52e242ef29e70be3e7bc',
},
},
+ cachedBalances: {},
},
}
})
diff --git a/ui/app/components/currency-display/currency-display.component.js b/ui/app/components/currency-display/currency-display.component.js
index 2d7413b57..6a743cc4e 100644
--- a/ui/app/components/currency-display/currency-display.component.js
+++ b/ui/app/components/currency-display/currency-display.component.js
@@ -17,10 +17,11 @@ export default class CurrencyDisplay extends PureComponent {
value: PropTypes.string,
numberOfDecimals: PropTypes.oneOfType([PropTypes.string, PropTypes.number]),
hideLabel: PropTypes.bool,
+ hideTitle: PropTypes.bool,
}
render () {
- const { className, displayValue, prefix, prefixComponent, style, suffix } = this.props
+ const { className, displayValue, prefix, prefixComponent, style, suffix, hideTitle } = this.props
const text = `${prefix || ''}${displayValue}`
const title = `${text} ${suffix}`
@@ -28,9 +29,9 @@ export default class CurrencyDisplay extends PureComponent {
<div
className={classnames('currency-display-component', className)}
style={style}
- title={title}
+ title={!hideTitle && title || null}
>
- { prefixComponent}
+ { prefixComponent }
<span className="currency-display-component__text">{ text }</span>
{
suffix && (
diff --git a/ui/app/components/send/account-list-item/account-list-item.component.js b/ui/app/components/send/account-list-item/account-list-item.component.js
index a61467bb3..665383e58 100644
--- a/ui/app/components/send/account-list-item/account-list-item.component.js
+++ b/ui/app/components/send/account-list-item/account-list-item.component.js
@@ -1,9 +1,11 @@
import React, { Component } from 'react'
import PropTypes from 'prop-types'
+import classnames from 'classnames'
import { checksumAddress } from '../../../util'
import Identicon from '../../identicon'
import UserPreferencedCurrencyDisplay from '../../user-preferenced-currency-display'
import { PRIMARY, SECONDARY } from '../../../constants/common'
+import Tooltip from '../../tooltip-v2'
export default class AccountListItem extends Component {
@@ -16,6 +18,7 @@ export default class AccountListItem extends Component {
displayBalance: PropTypes.bool,
handleClick: PropTypes.func,
icon: PropTypes.node,
+ balanceIsCached: PropTypes.bool,
};
static contextTypes = {
@@ -30,6 +33,7 @@ export default class AccountListItem extends Component {
displayBalance = true,
handleClick,
icon = null,
+ balanceIsCached,
} = this.props
const { name, address, balance } = account || {}
@@ -58,16 +62,34 @@ export default class AccountListItem extends Component {
{
displayBalance && (
- <div className="account-list-item__account-balances">
- <UserPreferencedCurrencyDisplay
- type={PRIMARY}
- value={balance}
- />
- <UserPreferencedCurrencyDisplay
- type={SECONDARY}
- value={balance}
- />
- </div>
+ <Tooltip
+ position="left"
+ title={this.context.t('balanceOutdated')}
+ disabled={!balanceIsCached}
+ style={{
+ left: '-20px !important',
+ }}
+ >
+ <div className={classnames('account-list-item__account-balances', {
+ 'account-list-item__cached-balances': balanceIsCached,
+ })}>
+ <div className="account-list-item__primary-cached-container">
+ <UserPreferencedCurrencyDisplay
+ type={PRIMARY}
+ value={balance}
+ hideTitle={true}
+ />
+ {
+ balanceIsCached ? <span className="account-list-item__cached-star">*</span> : null
+ }
+ </div>
+ <UserPreferencedCurrencyDisplay
+ type={SECONDARY}
+ value={balance}
+ hideTitle={true}
+ />
+ </div>
+ </Tooltip>
)
}
diff --git a/ui/app/components/send/account-list-item/account-list-item.container.js b/ui/app/components/send/account-list-item/account-list-item.container.js
index f8e73d923..03a60be67 100644
--- a/ui/app/components/send/account-list-item/account-list-item.container.js
+++ b/ui/app/components/send/account-list-item/account-list-item.container.js
@@ -4,6 +4,9 @@ import {
getCurrentCurrency,
getNativeCurrency,
} from '../send.selectors.js'
+import {
+ isBalanceCached,
+} from '../../../selectors'
import AccountListItem from './account-list-item.component'
export default connect(mapStateToProps)(AccountListItem)
@@ -13,5 +16,6 @@ function mapStateToProps (state) {
conversionRate: getConversionRate(state),
currentCurrency: getCurrentCurrency(state),
nativeCurrency: getNativeCurrency(state),
+ balanceIsCached: isBalanceCached(state),
}
}
diff --git a/ui/app/components/send/account-list-item/tests/account-list-item-component.test.js b/ui/app/components/send/account-list-item/tests/account-list-item-component.test.js
index 6ffc0b1c6..f2ddb73c0 100644
--- a/ui/app/components/send/account-list-item/tests/account-list-item-component.test.js
+++ b/ui/app/components/send/account-list-item/tests/account-list-item-component.test.js
@@ -121,6 +121,7 @@ describe('AccountListItem Component', function () {
{
type: 'PRIMARY',
value: 'mockBalance',
+ hideTitle: true,
}
)
})
diff --git a/ui/app/components/send/account-list-item/tests/account-list-item-container.test.js b/ui/app/components/send/account-list-item/tests/account-list-item-container.test.js
index 7c2f5fcb2..8c22bc8f8 100644
--- a/ui/app/components/send/account-list-item/tests/account-list-item-container.test.js
+++ b/ui/app/components/send/account-list-item/tests/account-list-item-container.test.js
@@ -15,6 +15,9 @@ proxyquire('../account-list-item.container.js', {
getCurrentCurrency: (s) => `mockCurrentCurrency:${s}`,
getNativeCurrency: (s) => `mockNativeCurrency:${s}`,
},
+ '../../../selectors.js': {
+ isBalanceCached: (s) => `mockBalanceIsCached:${s}`,
+ },
})
describe('account-list-item container', () => {
@@ -26,6 +29,7 @@ describe('account-list-item container', () => {
conversionRate: 'mockConversionRate:mockState',
currentCurrency: 'mockCurrentCurrency:mockState',
nativeCurrency: 'mockNativeCurrency:mockState',
+ balanceIsCached: 'mockBalanceIsCached:mockState',
})
})
diff --git a/ui/app/components/send/tests/send-selectors-test-data.js b/ui/app/components/send/tests/send-selectors-test-data.js
index 30a2666cf..66c0da229 100644
--- a/ui/app/components/send/tests/send-selectors-test-data.js
+++ b/ui/app/components/send/tests/send-selectors-test-data.js
@@ -22,6 +22,7 @@ module.exports = {
'name': 'Send Account 4',
},
},
+ 'cachedBalances': {},
'currentBlockGasLimit': '0x4c1878',
'currentCurrency': 'USD',
'conversionRate': 1200.88200327,
diff --git a/ui/app/components/tooltip-v2.js b/ui/app/components/tooltip-v2.js
index 054782203..b54026794 100644
--- a/ui/app/components/tooltip-v2.js
+++ b/ui/app/components/tooltip-v2.js
@@ -20,6 +20,7 @@ export default class Tooltip extends PureComponent {
arrow: PropTypes.bool,
children: PropTypes.node,
containerClassName: PropTypes.string,
+ disabled: PropTypes.bool,
onHidden: PropTypes.func,
position: PropTypes.oneOf([
'top',
@@ -33,10 +34,11 @@ export default class Tooltip extends PureComponent {
title: PropTypes.string,
trigger: PropTypes.any,
wrapperClassName: PropTypes.string,
+ style: PropTypes.object,
}
render () {
- const {arrow, children, containerClassName, position, size, title, trigger, onHidden, wrapperClassName } = this.props
+ const {arrow, children, containerClassName, disabled, position, size, title, trigger, onHidden, wrapperClassName, style } = this.props
if (!title) {
return (
@@ -50,6 +52,7 @@ export default class Tooltip extends PureComponent {
<div className={wrapperClassName}>
<ReactTippy
className={containerClassName}
+ disabled={disabled}
title={title}
position={position}
trigger={trigger}
@@ -57,6 +60,7 @@ export default class Tooltip extends PureComponent {
size={size}
arrow={arrow}
onHidden={onHidden}
+ style={style}
>
{children}
</ReactTippy>
diff --git a/ui/app/components/transaction-view-balance/index.scss b/ui/app/components/transaction-view-balance/index.scss
index f3fd580d7..bdcd536b0 100644
--- a/ui/app/components/transaction-view-balance/index.scss
+++ b/ui/app/components/transaction-view-balance/index.scss
@@ -17,6 +17,7 @@
display: flex;
flex-direction: column;
min-width: 0;
+ position: relative;
@media screen and (max-width: $break-small) {
align-items: center;
@@ -26,6 +27,10 @@
}
}
+ &__primary-container {
+ display: flex;
+ }
+
&__primary-balance {
font-size: 1.5rem;
@@ -36,6 +41,19 @@
}
}
+ &__cached-star {
+ margin-left: 4px;
+ }
+
+ &__cached-balance, &__cached-star {
+ color: $web-orange;
+ }
+
+ &__cached-secondary-balance {
+ color: rgba(220, 153, 18, 0.6901960784313725);
+ font-size: 1.15rem;
+ }
+
&__secondary-balance {
font-size: 1.15rem;
color: #a0a0a0;
diff --git a/ui/app/components/transaction-view-balance/transaction-view-balance.component.js b/ui/app/components/transaction-view-balance/transaction-view-balance.component.js
index a24b97478..bd6b4bdb6 100644
--- a/ui/app/components/transaction-view-balance/transaction-view-balance.component.js
+++ b/ui/app/components/transaction-view-balance/transaction-view-balance.component.js
@@ -1,11 +1,13 @@
import React, { PureComponent } from 'react'
import PropTypes from 'prop-types'
+import classnames from 'classnames'
import Button from '../button'
import Identicon from '../identicon'
import TokenBalance from '../token-balance'
import UserPreferencedCurrencyDisplay from '../user-preferenced-currency-display'
import { SEND_ROUTE } from '../../routes'
import { PRIMARY, SECONDARY } from '../../constants/common'
+import Tooltip from '../tooltip-v2'
export default class TransactionViewBalance extends PureComponent {
static contextTypes = {
@@ -19,10 +21,11 @@ export default class TransactionViewBalance extends PureComponent {
network: PropTypes.string,
balance: PropTypes.string,
assetImage: PropTypes.string,
+ balanceIsCached: PropTypes.bool,
}
renderBalance () {
- const { selectedToken, balance } = this.props
+ const { selectedToken, balance, balanceIsCached } = this.props
return selectedToken
? (
@@ -34,20 +37,34 @@ export default class TransactionViewBalance extends PureComponent {
/>
</div>
) : (
- <div className="transaction-view-balance__balance">
- <UserPreferencedCurrencyDisplay
- className="transaction-view-balance__primary-balance"
- value={balance}
- type={PRIMARY}
- ethNumberOfDecimals={4}
- />
- <UserPreferencedCurrencyDisplay
- className="transaction-view-balance__secondary-balance"
- value={balance}
- type={SECONDARY}
- ethNumberOfDecimals={4}
- />
- </div>
+ <Tooltip position="top" title={this.context.t('balanceOutdated')} disabled={!balanceIsCached}>
+ <div className="transaction-view-balance__balance">
+ <div className="transaction-view-balance__primary-container">
+ <UserPreferencedCurrencyDisplay
+ className={classnames('transaction-view-balance__primary-balance', {
+ 'transaction-view-balance__cached-balance': balanceIsCached,
+ })}
+ value={balance}
+ type={PRIMARY}
+ ethNumberOfDecimals={4}
+ hideTitle={true}
+ />
+ {
+ balanceIsCached ? <span className="transaction-view-balance__cached-star">*</span> : null
+ }
+ </div>
+ <UserPreferencedCurrencyDisplay
+ className={classnames({
+ 'transaction-view-balance__cached-secondary-balance': balanceIsCached,
+ 'transaction-view-balance__secondary-balance': !balanceIsCached,
+ })}
+ value={balance}
+ type={SECONDARY}
+ ethNumberOfDecimals={4}
+ hideTitle={true}
+ />
+ </div>
+ </Tooltip>
)
}
diff --git a/ui/app/components/transaction-view-balance/transaction-view-balance.container.js b/ui/app/components/transaction-view-balance/transaction-view-balance.container.js
index f9f05b0ae..354db5ae1 100644
--- a/ui/app/components/transaction-view-balance/transaction-view-balance.container.js
+++ b/ui/app/components/transaction-view-balance/transaction-view-balance.container.js
@@ -8,6 +8,7 @@ import {
getNativeCurrency,
getSelectedTokenAssetImage,
getMetaMaskAccounts,
+ isBalanceCached,
} from '../../selectors'
import { showModal } from '../../actions'
@@ -24,6 +25,7 @@ const mapStateToProps = state => {
balance,
nativeCurrency: getNativeCurrency(state),
assetImage: getSelectedTokenAssetImage(state),
+ balanceIsCached: isBalanceCached(state),
}
}
diff --git a/ui/app/components/user-preferenced-currency-display/user-preferenced-currency-display.component.js b/ui/app/components/user-preferenced-currency-display/user-preferenced-currency-display.component.js
index f2a834ea7..d9f29327d 100644
--- a/ui/app/components/user-preferenced-currency-display/user-preferenced-currency-display.component.js
+++ b/ui/app/components/user-preferenced-currency-display/user-preferenced-currency-display.component.js
@@ -10,6 +10,7 @@ export default class UserPreferencedCurrencyDisplay extends PureComponent {
value: PropTypes.string,
numberOfDecimals: PropTypes.oneOfType([PropTypes.string, PropTypes.number]),
hideLabel: PropTypes.bool,
+ hideTitle: PropTypes.bool,
style: PropTypes.object,
showEthLogo: PropTypes.bool,
ethLogoHeight: PropTypes.oneOfType([PropTypes.string, PropTypes.number]),
diff --git a/ui/app/css/itcss/components/account-dropdown.scss b/ui/app/css/itcss/components/account-dropdown.scss
index b29afdc8c..716404cc3 100644
--- a/ui/app/css/itcss/components/account-dropdown.scss
+++ b/ui/app/css/itcss/components/account-dropdown.scss
@@ -24,6 +24,10 @@
position: relative;
}
+ &__tooltip-wrapper {
+ left: -10px;
+ }
+
&__account-balances {
height: auto;
border: none;
@@ -34,6 +38,24 @@
position: relative;
}
+ &__primary-cached-container {
+ display: flex;
+ }
+
+ &__cached-star {
+ margin-left: 4px;
+ }
+
+ &__cached-balances {
+ div:first-of-type {
+ color: $web-orange;
+ }
+
+ div:last-of-type {
+ color: rgba(220, 153, 18, 0.6901960784313725)
+ }
+ }
+
&__account-name {
font-size: 16px;
margin-left: 8px;
@@ -52,6 +74,13 @@
font-size: 12px;
}
+ &__balance-flag {
+ position: absolute;
+ top: 3px;
+ left: -8px;
+ color: $curious-blue;
+ }
+
&__account-primary-balance {
color: $scorpion;
border: none;
diff --git a/ui/app/css/itcss/settings/variables.scss b/ui/app/css/itcss/settings/variables.scss
index 42a8655df..89bd8b96a 100644
--- a/ui/app/css/itcss/settings/variables.scss
+++ b/ui/app/css/itcss/settings/variables.scss
@@ -59,6 +59,7 @@ $oslo-gray: #8C8E94;
$polar: #fafcfe;
$blizzard-blue: #bfdef3;
$mischka: #dddee9;
+$web-orange: #f2a202;
/*
Z-Indicies
diff --git a/ui/app/selectors.js b/ui/app/selectors.js
index f1ef41f28..c60b27ab4 100644
--- a/ui/app/selectors.js
+++ b/ui/app/selectors.js
@@ -37,6 +37,7 @@ const selectors = {
getMetaMaskAccounts,
getCurrentEthBalance,
getNetworkIdentifier,
+ isBalanceCached,
}
module.exports = selectors
@@ -62,7 +63,7 @@ function getSelectedIdentity (state) {
function getMetaMaskAccounts (state) {
const currentAccounts = state.metamask.accounts
- const cachedBalances = state.metamask.cachedBalances
+ const cachedBalances = state.metamask.cachedBalances[state.metamask.network]
const selectedAccounts = {}
Object.keys(currentAccounts).forEach(accountID => {
@@ -70,7 +71,7 @@ function getMetaMaskAccounts (state) {
if (account && account.balance === null || account.balance === undefined) {
selectedAccounts[accountID] = {
...account,
- balance: cachedBalances[accountID],
+ balance: cachedBalances && cachedBalances[accountID],
}
} else {
selectedAccounts[accountID] = account
@@ -79,6 +80,20 @@ function getMetaMaskAccounts (state) {
return selectedAccounts
}
+function isBalanceCached (state) {
+ const selectedAccountBalance = state.metamask.accounts[getSelectedAddress(state)].balance
+ const cachedBalance = getSelectedAccountCachedBalance(state)
+
+ return Boolean(!selectedAccountBalance && cachedBalance)
+}
+
+function getSelectedAccountCachedBalance (state) {
+ const cachedBalances = state.metamask.cachedBalances[state.metamask.network]
+ const selectedAddress = getSelectedAddress(state)
+
+ return cachedBalances && cachedBalances[selectedAddress]
+}
+
function getSelectedAccount (state) {
const accounts = getMetaMaskAccounts(state)
const selectedAddress = getSelectedAddress(state)