From 8aefbe25b30b7639d08d882f3ef75b9ac746c76a Mon Sep 17 00:00:00 2001 From: Ivan Socolsky Date: Thu, 18 Aug 2016 10:37:08 -0300 Subject: [PATCH] wallet details refactor --- public/views/tab-home.html | 4 +- public/views/walletDetails.html | 64 +- src/js/controllers/preferences.js | 2 +- src/js/controllers/preferencesUnit.js | 29 +- src/js/controllers/tab-home.js | 9 +- src/js/controllers/walletDetails.js | 136 ++-- src/js/routes.js | 1072 ++++++++++++------------- src/js/services/txFormatService.js | 17 +- src/js/services/walletService.js | 82 +- 9 files changed, 706 insertions(+), 709 deletions(-) diff --git a/public/views/tab-home.html b/public/views/tab-home.html index 28cd452b1..f2c41021e 100644 --- a/public/views/tab-home.html +++ b/public/views/tab-home.html @@ -3,7 +3,7 @@ Home - +

Payment Proposals

@@ -64,7 +64,7 @@ Incomplete - {{item.availableBalanceStr}} + {{item.status.availableBalanceStr}} diff --git a/public/views/walletDetails.html b/public/views/walletDetails.html index cb43b4795..aa5ab94c6 100644 --- a/public/views/walletDetails.html +++ b/public/views/walletDetails.html @@ -1,6 +1,6 @@ - + {{wallet.name}} @@ -14,7 +14,7 @@ - +
No Wallet @@ -33,35 +33,35 @@
-
+
-
- {{wallet.updateError|translate}} +
+ {{updateStatusError|translate}}
-
+
Scan status finished with error
Tap to retry
-
+
{{status.totalBalanceStr}} -
{{status.totalBalanceAlternative}} {{status.alternativeIsoCode}}
-
+
{{status.totalBalanceAlternative}} {{status.alternativeIsoCode}}
+
Pending Confirmation: {{status.pendingAmountStr}}
-
+
[Balance Hidden]
Tap and hold to show
-
+
...
@@ -82,7 +82,7 @@
-
+
@@ -94,7 +94,7 @@
+ ng-click="recreate()"> Recreate
@@ -105,48 +105,46 @@
-

Payment Proposals

-

Unsent transactions

+

Payment Proposals

+

Unsent transactions

+ ng-show="status.lockedBalanceSat"> Total Locked Balance: - {{wallet.lockedBalanceStr}} - {{wallet.lockedBalanceAlternative}} - {{wallet.alternativeIsoCode}} + {{status.lockedBalanceStr}} + {{status.lockedBalanceAlternative}} + {{status.alternativeIsoCode}}
- - -

+ +

Activity

No transactions yet ZZZZ {{wallet.totalBalanceStr}} + ng-show="!txHistory[0] && !updatingTxHistory && !txHistoryError && !updateStatusError && !notAuthorized" + translate>No transactions yet {{status.totalBalanceStr}}
+
-
- -
+
-
{{wallet.txProgress}} transactions downloaded
+
{{updatingTxHistoryProgress}} transactions downloaded
Updating transaction history. Please stand by.
-
+
@@ -219,14 +217,12 @@
-
-
- -
+
+
diff --git a/src/js/controllers/preferences.js b/src/js/controllers/preferences.js index a23706cdc..5137bd1ac 100644 --- a/src/js/controllers/preferences.js +++ b/src/js/controllers/preferences.js @@ -11,7 +11,7 @@ angular.module('copayApp.controllers').controller('preferencesController', $scope.externalSource = null; if (wallet) { - walletService.updateStatus(wallet, {}, function(err, status) {}); + walletService.getStatus(wallet, {}, function(err, status) {}); var config = configService.getSync(); config.aliasFor = config.aliasFor || {}; $scope.alias = config.aliasFor[walletId] || wallet.credentials.walletName; diff --git a/src/js/controllers/preferencesUnit.js b/src/js/controllers/preferencesUnit.js index c74efc0de..abdee5625 100644 --- a/src/js/controllers/preferencesUnit.js +++ b/src/js/controllers/preferencesUnit.js @@ -7,22 +7,19 @@ angular.module('copayApp.controllers').controller('preferencesUnitController', f $scope.currentUnit = config.wallet.settings.unitCode; } - $scope.unitList = [ - { - name: 'bits (1,000,000 bits = 1BTC)', - shortName: 'bits', - value: 100, - decimals: 2, - code: 'bit', - }, - { - name: 'BTC', - shortName: 'BTC', - value: 100000000, - decimals: 8, - code: 'btc', - } - ]; + $scope.unitList = [{ + name: 'bits (1,000,000 bits = 1BTC)', + shortName: 'bits', + value: 100, + decimals: 2, + code: 'bit', + }, { + name: 'BTC', + shortName: 'BTC', + value: 100000000, + decimals: 8, + code: 'btc', + }]; $scope.save = function(newUnit) { var opts = { diff --git a/src/js/controllers/tab-home.js b/src/js/controllers/tab-home.js index d897faecf..579069381 100644 --- a/src/js/controllers/tab-home.js +++ b/src/js/controllers/tab-home.js @@ -88,11 +88,9 @@ angular.module('copayApp.controllers').controller('tabHomeController', self.updateAllClients = function() { var txps = []; - var wallets = profileService.getWallets(); - var l = wallets.length, - i = 0; + var i = $scope.wallets.length; - lodash.each(wallets, function(wallet) { + lodash.each($scope.wallets, function(wallet) { walletService.getStatus(wallet, {}, function(err, status) { if (err) { console.log('[tab-home.js.35:err:]', $log.error(err)); //TODO @@ -101,9 +99,10 @@ angular.module('copayApp.controllers').controller('tabHomeController', if (status.pendingTxps && status.pendingTxps[0]) { txps = txps.concat(status.pendingTxps); } - if (++i == l) { + if (--i == 0) { setPendingTxps(txps); } + wallet.status = status; }); }); } diff --git a/src/js/controllers/walletDetails.js b/src/js/controllers/walletDetails.js index 09615af35..0e2a6927a 100644 --- a/src/js/controllers/walletDetails.js +++ b/src/js/controllers/walletDetails.js @@ -1,36 +1,16 @@ 'use strict'; -angular.module('copayApp.controllers').controller('walletDetailsController', function($scope, $rootScope, $interval, $timeout, $filter, $log, $ionicModal, $ionicPopover, $state, $stateParams, profileService, lodash, configService, gettext, gettextCatalog, platformInfo, go, walletService) { - +angular.module('copayApp.controllers').controller('walletDetailsController', function($scope, $rootScope, $interval, $timeout, $filter, $log, $ionicModal, $ionicPopover, $state, $stateParams, bwcError, profileService, lodash, configService, gettext, gettextCatalog, platformInfo, go, walletService) { var isCordova = platformInfo.isCordova; var isWP = platformInfo.isWP; var isAndroid = platformInfo.isAndroid; var isChromeApp = platformInfo.isChromeApp; - var self = this; - $rootScope.shouldHideMenuBar = false; - $rootScope.wpInputFocused = false; - var config = configService.getSync(); - var configWallet = config.wallet; - var walletSettings = configWallet.settings; - var ret = {}; + var errorPopup; + + var HISTORY_SHOW_LIMIT = 10; - // INIT. Global value - ret.unitToSatoshi = walletSettings.unitToSatoshi; - ret.satToUnit = 1 / ret.unitToSatoshi; - ret.unitName = walletSettings.unitName; - ret.alternativeIsoCode = walletSettings.alternativeIsoCode; - ret.alternativeName = walletSettings.alternativeName; - ret.alternativeAmount = 0; - ret.unitDecimals = walletSettings.unitDecimals; - ret.isCordova = isCordova; - ret.addresses = []; - ret.isMobile = platformInfo.isMobile; - ret.isWindowsPhoneApp = platformInfo.isWP; - ret.countDown = null; - ret.sendMaxInfo = {}; - ret.showAlternative = false; $scope.openSearchModal = function() { var fc = profileService.focusedClient; @@ -61,48 +41,100 @@ angular.module('copayApp.controllers').controller('walletDetailsController', fun }); }; - $scope.updateAll = function()  { - $scope.update(); - } + $scope.recreate = function() { + walletService.recreate(); + }; - $scope.update = function() { - $scope.updating = true; + $scope.updateStatus = function(force) { + $scope.updatingStatus = true; + $scope.updateStatusError = false; $timeout(function() { walletService.getStatus(wallet, { - force: true + force: !!force, }, function(err, status) { - if (err) {} // TODO + $scope.updatingStatus = false; + if (err) { + $scope.status = null; + $scope.updateStatusError = true; + return; + } $scope.status = status; - $scope.updating = false; }); }) }; + $scope.updateTxHistory = function() { + + if ($scope.updatingTxHistory) return; + + $scope.updatingTxHistory = true; + $scope.updateTxHistoryError = false; + $scope.updatingTxHistoryProgress = null; + + var progressFn = function(txs) { + $scope.updatingTxHistoryProgress = txs ? txs.length : 0; + completeTxHistory = txs; + $scope.showHistory(); + $scope.$digest(); + }; + + $timeout(function() { + walletService.getTxHistory(wallet, { + progressFn: progressFn, + }, function(err, txHistory) { + $scope.updatingTxHistory = false; + if (err) { + $scope.txHistory = null; + $scope.updateTxHistoryError = true; + return; + } + completeTxHistory = txHistory; + + $scope.showHistory(); + $scope.$apply(); + }); + }); + }; + + $scope.showHistory = function() { + if ($scope.isSearching) { + $scope.txHistorySearchResults = filteredTxHistory ? filteredTxHistory.slice(0, (currentTxHistoryPage + 1) * HISTORY_SHOW_LIMIT) : []; + $scope.txHistoryShowMore = filteredTxHistory.length > $scope.txHistorySearchResults.length; + } else { + $scope.txHistory = completeTxHistory ? completeTxHistory.slice(0, (currentTxHistoryPage + 1) * HISTORY_SHOW_LIMIT) : []; + $scope.txHistoryShowMore = completeTxHistory.length > $scope.txHistory.length; + } + }; + + $scope.showMore = function() { + currentTxHistoryPage++; + $scope.showHistory(); + $scope.$broadcast('scroll.infiniteScrollComplete'); + }; + + $scope.updateAll = function()  { + $scope.updateStatus(false); + $scope.updateTxHistory(); + } + $scope.hideToggle = function() { console.log('[walletDetails.js.70:hideToogle:] TODO'); //TODO }; - if (!$stateParams.walletId) { - $log.debug('No wallet provided... using the first one'); - $stateParams.walletId = profileService.getWallets({ - onlyComplete: true - })[0].id; - } + var currentTxHistoryPage; + var completeTxHistory; + var wallet; + $scope.init = function() { + currentTxHistoryPage = 0; + completeTxHistory = []; - var wallet = profileService.getWallet($stateParams.walletId); - $scope.wallet = wallet; + wallet = profileService.getWallet($stateParams.walletId); + $scope.wallet = wallet; + $scope.requiresMultipleSignatures = wallet.credentials.m > 1; + $scope.newTx = false; + + $scope.updateAll(); + }; - if (wallet) { - walletService.getStatus(wallet, {}, function(err, status) { - console.log('*** [walletDetails.js ln89] status:', status); // TODO - if (err) {} // TODO - $scope.status = status; - }); - walletService.getHistory(wallet, {}, function(err, txHistory) { - console.log('*** [walletDetails.js ln93] txHistory:', txHistory); // TODO - if (err) {} // TODO - $scope.txHistory = txHistory; - }); - } }); diff --git a/src/js/routes.js b/src/js/routes.js index 8f1edee76..632681450 100644 --- a/src/js/routes.js +++ b/src/js/routes.js @@ -14,555 +14,555 @@ if (window && window.navigator) { //Setting up route angular.module('copayApp').config(function(historicLogProvider, $provide, $logProvider, $stateProvider, $urlRouterProvider, $compileProvider) { - $urlRouterProvider.otherwise('/tabs.home'); + $urlRouterProvider.otherwise('/tabs.home'); - $logProvider.debugEnabled(true); - $provide.decorator('$log', ['$delegate', 'platformInfo', - function($delegate, platformInfo) { - var historicLog = historicLogProvider.$get(); + $logProvider.debugEnabled(true); + $provide.decorator('$log', ['$delegate', 'platformInfo', + function($delegate, platformInfo) { + var historicLog = historicLogProvider.$get(); - ['debug', 'info', 'warn', 'error', 'log'].forEach(function(level) { - if (platformInfo.isDevel && level == 'error') return; + ['debug', 'info', 'warn', 'error', 'log'].forEach(function(level) { + if (platformInfo.isDevel && level == 'error') return; - var orig = $delegate[level]; - $delegate[level] = function() { - if (level == 'error') - console.log(arguments); + var orig = $delegate[level]; + $delegate[level] = function() { + if (level == 'error') + console.log(arguments); - var args = Array.prototype.slice.call(arguments); - - args = args.map(function(v) { - try { - if (typeof v == 'undefined') v = 'undefined'; - if (!v) v = 'null'; - if (typeof v == 'object') { - if (v.message) - v = v.message; - else - v = JSON.stringify(v); - } - // Trim output in mobile - if (platformInfo.isCordova) { - v = v.toString(); - if (v.length > 3000) { - v = v.substr(0, 2997) + '...'; - } - } - } catch (e) { - console.log('Error at log decorator:', e); - v = 'undefined'; - } - return v; - }); + var args = Array.prototype.slice.call(arguments); + args = args.map(function(v) { try { - if (platformInfo.isCordova) - console.log(args.join(' ')); - - historicLog.add(level, args.join(' ')); - orig.apply(null, args); + if (typeof v == 'undefined') v = 'undefined'; + if (!v) v = 'null'; + if (typeof v == 'object') { + if (v.message) + v = v.message; + else + v = JSON.stringify(v); + } + // Trim output in mobile + if (platformInfo.isCordova) { + v = v.toString(); + if (v.length > 3000) { + v = v.substr(0, 2997) + '...'; + } + } } catch (e) { - console.log('ERROR (at log decorator):', e, args[0]); + console.log('Error at log decorator:', e); + v = 'undefined'; } - }; - }); - return $delegate; - } - ]); + return v; + }); - // whitelist 'chrome-extension:' for chromeApp to work with image URLs processed by Angular - // link: http://stackoverflow.com/questions/15606751/angular-changes-urls-to-unsafe-in-extension-page?lq=1 - $compileProvider.imgSrcSanitizationWhitelist(/^\s*((https?|ftp|file|blob|chrome-extension):|data:image\/)/); + try { + if (platformInfo.isCordova) + console.log(args.join(' ')); - $stateProvider - .state('translators', { - url: '/translators', - needProfile: true, - views: { - 'main': { - templateUrl: 'views/translators.html' + historicLog.add(level, args.join(' ')); + orig.apply(null, args); + } catch (e) { + console.log('ERROR (at log decorator):', e, args[0]); } - } - }) - .state('disclaimer', { - url: '/disclaimer', - needProfile: false, - views: { - 'main': { - templateUrl: 'views/disclaimer.html', - } - } - }) - .state('wallet', { - url: '/wallet/{walletId}', - abstract: true, - needProfile: true, - views: { - 'main': { - template: '', - }, - }, - }) - .state('wallet.details', { - url: '/details', - templateUrl: 'views/walletDetails.html', - needProfile: true - }) - .state('wallet.preferences', { - url: '/preferences', - templateUrl: 'views/preferences.html', - needProfile: true - }) - .state('wallet.preferencesAlias', { - url: '/preferencesAlias', - templateUrl: 'views/preferencesAlias.html', - needProfile: true - }) - .state('wallet.preferencesColor', { - url: '/preferencesColor', - templateUrl: 'views/preferencesColor.html', - needProfile: true - }) - .state('wallet.preferencesEmail', { - url: '/preferencesEmail', - templateUrl: 'views/preferencesEmail.html', - needProfile: true - }) - .state('wallet.backup', { - url: '/backup', - templateUrl: 'views/backup.html', - needProfile: true - }) - .state('wallet.preferencesAdvanced', { - url: '/preferencesAdvanced', - templateUrl: 'views/preferencesAdvanced.html', - needProfile: true - }) - .state('wallet.information', { - url: '/information', - templateUrl: 'views/preferencesInformation.html', - needProfile: true - }) - .state('wallet.export', { - url: '/export', - templateUrl: 'views/export.html', - needProfile: true - }) - .state('wallet.preferencesBwsUrl', { - url: '/preferencesBwsUrl', - templateUrl: 'views/preferencesBwsUrl.html', - needProfile: true - }) - .state('wallet.preferencesHistory', { - url: '/preferencesHistory', - templateUrl: 'views/preferencesHistory.html', - needProfile: true - }) - .state('wallet.deleteWords', { - url: '/deleteWords', - templateUrl: 'views/preferencesDeleteWords.html', - needProfile: true - }) - .state('wallet.delete', { - url: '/delete', - templateUrl: 'views/preferencesDeleteWallet.html', - needProfile: true - }) - .state('wallet.copayers', { - url: '/copayers', - needProfile: true, - cache: false, - templateUrl: 'views/copayers.html' - }) - -// OLD - // .state('walletHome', { - // url: '/old', - // needProfile: true, - // views: { - // 'main': { - // templateUrl: 'views/walletHome.html', - // }, - // } - // }) - .state('tabs', { - url: '/tabs', - cache: false, - needProfile: true, - abstract: true, - views: { - 'main': { - templateUrl: 'views/tabs.html', - }, - } - }) - .state('tabs.home', { - url: '/home', - cache: false, - needProfile: true, - views: { - 'tab-home': { - templateUrl: 'views/tab-home.html', - }, - } - }) - .state('tabs.receive', { - url: '/receive', - cache: false, - needProfile: true, - views: { - 'tab-receive': { - templateUrl: 'views/tab-receive.html', - }, - } - }) - .state('tabs.scan', { - url: '/scan', - needProfile: true, - views: { - 'tab-scan': { - templateUrl: 'views/tab-scan.html', - }, - } - }) - .state('tabs.send', { - url: '/send', - cache: false, - needProfile: true, - views: { - 'tab-send': { - templateUrl: 'views/tab-send.html', - }, - } - }) - .state('tabs.settings', { - url: '/settings', - needProfile: true, - views: { - 'tab-settings': { - templateUrl: 'views/tab-settings.html', - }, - } - }) - .state('amount', { - cache: false, - url: '/amount:/:toAddress/:toName', - needProfile: true, - views: { - 'main': { - templateUrl: 'views/amount.html', - }, - }, - }) - .state('confirm', { - cache: false, - url: '/confirm/:toAddress/:toName/:toAmount', - needProfile: true, - views: { - 'main': { - templateUrl: 'views/confirm.html', - }, - }, - }) - - .state('unsupported', { - url: '/unsupported', - needProfile: false, - views: { - 'main': { - templateUrl: 'views/unsupported.html' - } - } - }) - .state('uri', { - url: '/uri/:url', - needProfile: true, - views: { - 'main': { - templateUrl: 'views/uri.html' - } - } - }) - .state('uripayment', { - url: '/uri-payment/:url', - templateUrl: 'views/paymentUri.html', - views: { - 'main': { - templateUrl: 'views/paymentUri.html', - }, - }, - needProfile: true - }) - .state('join', { - url: '/join', - needProfile: true, - views: { - 'main': { - templateUrl: 'views/join.html' - }, - } - }) - .state('import', { - url: '/import', - needProfile: true, - views: { - 'main': { - templateUrl: 'views/import.html' - }, - } - }) - .state('create', { - url: '/create', - templateUrl: 'views/create.html', - needProfile: true, - views: { - 'main': { - templateUrl: 'views/create.html' - }, - } - }) - .state('preferencesLanguage', { - url: '/preferencesLanguage', - needProfile: true, - views: { - 'main': { - templateUrl: 'views/preferencesLanguage.html' - }, - } - }) - .state('preferencesUnit', { - url: '/preferencesUnit', - templateUrl: 'views/preferencesUnit.html', - needProfile: true, - views: { - 'main': { - templateUrl: 'views/preferencesUnit.html' - }, - } - }) - .state('preferencesFee', { - url: '/preferencesFee', - templateUrl: 'views/preferencesFee.html', - needProfile: true, - views: { - 'main': { - templateUrl: 'views/preferencesFee.html' - }, - } - }) - .state('uriglidera', { - url: '/uri-glidera/:url', - needProfile: true, - views: { - 'main': { - templateUrl: 'views/glideraUri.html' - }, - } - }) - .state('glidera', { - url: '/glidera', - needProfile: true, - views: { - 'main': { - templateUrl: 'views/glidera.html' - }, - } - }) - .state('buyGlidera', { - url: '/buy', - needProfile: true, - views: { - 'main': { - templateUrl: 'views/buyGlidera.html' - }, - } - }) - .state('sellGlidera', { - url: '/sell', - needProfile: true, - views: { - 'main': { - templateUrl: 'views/sellGlidera.html' - }, - } - }) - .state('preferencesGlidera', { - url: '/preferencesGlidera', - needProfile: true, - views: { - 'main': { - templateUrl: 'views/preferencesGlidera.html' - }, - } - }) - .state('bitpayCard', { - url: '/bitpay-card', - needProfile: true, - views: { - 'main': { - templateUrl: 'views/bitpayCard.html' - }, - } - }) - .state('preferencesBitpayCard', { - url: '/preferences-bitpay-card', - needProfile: true, - views: { - 'main': { - templateUrl: 'views/preferencesBitpayCard.html' - }, - } - }) - .state('coinbase', { - url: '/coinbase', - needProfile: true, - views: { - 'main': { - templateUrl: 'views/coinbase.html' - }, - } - }) - .state('preferencesCoinbase', { - url: '/preferencesCoinbase', - needProfile: true, - views: { - 'main': { - templateUrl: 'views/preferencesCoinbase.html' - }, - } - }) - .state('uricoinbase', { - url: '/uri-coinbase/:url', - needProfile: true, - views: { - 'main': { - templateUrl: 'views/coinbaseUri.html' - }, - } - }) - .state('buyCoinbase', { - url: '/buycoinbase', - needProfile: true, - views: { - 'main': { - templateUrl: 'views/buyCoinbase.html' - }, - } - }) - .state('sellCoinbase', { - url: '/sellcoinbase', - needProfile: true, - views: { - 'main': { - templateUrl: 'views/sellCoinbase.html' - }, - } - }) - .state('buyandsell', { - url: '/buyandsell', - needProfile: true, - views: { - 'main': { - templateUrl: 'views/buyAndSell.html', - controller: function(platformInfo) { - if (platformInfo.isCordova && StatusBar.isVisible) { - StatusBar.backgroundColorByHexString("#4B6178"); - } - } - } - } - }) - .state('amazon', { - url: '/amazon', - needProfile: true, - views: { - 'main': { - templateUrl: 'views/amazon.html' - }, - } - }) - .state('buyAmazon', { - url: '/buyamazon', - needProfile: true, - views: { - 'main': { - templateUrl: 'views/buyAmazon.html' - }, - } - }) - .state('preferencesAltCurrency', { - url: '/preferencesAltCurrency', - templateUrl: 'views/preferencesAltCurrency.html', - needProfile: true, - views: { - 'main': { - templateUrl: 'views/preferencesAltCurrency.html' - }, - } - }) - .state('about', { - url: '/about', - templateUrl: 'views/preferencesAbout.html', - needProfile: true, - views: { - 'main': { - templateUrl: 'views/preferencesAbout.html' - }, - } - }) - .state('logs', { - url: '/logs', - templateUrl: 'views/preferencesLogs.html', - needProfile: true, - views: { - 'main': { - templateUrl: 'views/preferencesLogs.html' - }, - } - }) - .state('paperWallet', { - url: '/paperWallet', - templateUrl: 'views/paperWallet.html', - needProfile: true, - views: { - 'main': { - templateUrl: 'views/paperWallet.html' - }, - } - }) - .state('preferencesGlobal', { - url: '/preferencesGlobal', - needProfile: true, - views: { - 'main': { - templateUrl: 'views/preferencesGlobal.html', - }, - } - }) - .state('termOfUse', { - url: '/termOfUse', - needProfile: true, - views: { - 'main': { - templateUrl: 'views/termOfUse.html', - }, - } - }) - .state('add', { - url: '/add', - needProfile: true, - views: { - 'main': { - templateUrl: 'views/add.html', - controller: function(platformInfo) { - if (platformInfo.isCordova && StatusBar.isVisible) { - StatusBar.backgroundColorByHexString("#4B6178"); - } - } - } - } + }; }); + return $delegate; + } + ]); + + // whitelist 'chrome-extension:' for chromeApp to work with image URLs processed by Angular + // link: http://stackoverflow.com/questions/15606751/angular-changes-urls-to-unsafe-in-extension-page?lq=1 + $compileProvider.imgSrcSanitizationWhitelist(/^\s*((https?|ftp|file|blob|chrome-extension):|data:image\/)/); + + $stateProvider + .state('translators', { + url: '/translators', + needProfile: true, + views: { + 'main': { + templateUrl: 'views/translators.html' + } + } + }) + .state('disclaimer', { + url: '/disclaimer', + needProfile: false, + views: { + 'main': { + templateUrl: 'views/disclaimer.html', + } + } + }) + .state('wallet', { + url: '/wallet/{walletId}', + abstract: true, + needProfile: true, + views: { + 'main': { + template: '', + }, + }, + }) + .state('wallet.details', { + url: '/details', + templateUrl: 'views/walletDetails.html', + needProfile: true + }) + .state('wallet.preferences', { + url: '/preferences', + templateUrl: 'views/preferences.html', + needProfile: true + }) + .state('wallet.preferencesAlias', { + url: '/preferencesAlias', + templateUrl: 'views/preferencesAlias.html', + needProfile: true + }) + .state('wallet.preferencesColor', { + url: '/preferencesColor', + templateUrl: 'views/preferencesColor.html', + needProfile: true + }) + .state('wallet.preferencesEmail', { + url: '/preferencesEmail', + templateUrl: 'views/preferencesEmail.html', + needProfile: true + }) + .state('wallet.backup', { + url: '/backup', + templateUrl: 'views/backup.html', + needProfile: true + }) + .state('wallet.preferencesAdvanced', { + url: '/preferencesAdvanced', + templateUrl: 'views/preferencesAdvanced.html', + needProfile: true + }) + .state('wallet.information', { + url: '/information', + templateUrl: 'views/preferencesInformation.html', + needProfile: true + }) + .state('wallet.export', { + url: '/export', + templateUrl: 'views/export.html', + needProfile: true + }) + .state('wallet.preferencesBwsUrl', { + url: '/preferencesBwsUrl', + templateUrl: 'views/preferencesBwsUrl.html', + needProfile: true + }) + .state('wallet.preferencesHistory', { + url: '/preferencesHistory', + templateUrl: 'views/preferencesHistory.html', + needProfile: true + }) + .state('wallet.deleteWords', { + url: '/deleteWords', + templateUrl: 'views/preferencesDeleteWords.html', + needProfile: true + }) + .state('wallet.delete', { + url: '/delete', + templateUrl: 'views/preferencesDeleteWallet.html', + needProfile: true + }) + .state('wallet.copayers', { + url: '/copayers', + needProfile: true, + cache: false, + templateUrl: 'views/copayers.html' + }) + + // OLD + // .state('walletHome', { + // url: '/old', + // needProfile: true, + // views: { + // 'main': { + // templateUrl: 'views/walletHome.html', + // }, + // } + // }) + .state('tabs', { + url: '/tabs', + cache: false, + needProfile: true, + abstract: true, + views: { + 'main': { + templateUrl: 'views/tabs.html', + }, + } }) + .state('tabs.home', { + url: '/home', + cache: false, + needProfile: true, + views: { + 'tab-home': { + templateUrl: 'views/tab-home.html', + }, + } + }) + .state('tabs.receive', { + url: '/receive', + cache: false, + needProfile: true, + views: { + 'tab-receive': { + templateUrl: 'views/tab-receive.html', + }, + } + }) + .state('tabs.scan', { + url: '/scan', + needProfile: true, + views: { + 'tab-scan': { + templateUrl: 'views/tab-scan.html', + }, + } + }) + .state('tabs.send', { + url: '/send', + cache: false, + needProfile: true, + views: { + 'tab-send': { + templateUrl: 'views/tab-send.html', + }, + } + }) + .state('tabs.settings', { + url: '/settings', + needProfile: true, + views: { + 'tab-settings': { + templateUrl: 'views/tab-settings.html', + }, + } + }) + .state('amount', { + cache: false, + url: '/amount:/:toAddress/:toName', + needProfile: true, + views: { + 'main': { + templateUrl: 'views/amount.html', + }, + }, + }) + .state('confirm', { + cache: false, + url: '/confirm/:toAddress/:toName/:toAmount', + needProfile: true, + views: { + 'main': { + templateUrl: 'views/confirm.html', + }, + }, + }) + + .state('unsupported', { + url: '/unsupported', + needProfile: false, + views: { + 'main': { + templateUrl: 'views/unsupported.html' + } + } + }) + .state('uri', { + url: '/uri/:url', + needProfile: true, + views: { + 'main': { + templateUrl: 'views/uri.html' + } + } + }) + .state('uripayment', { + url: '/uri-payment/:url', + templateUrl: 'views/paymentUri.html', + views: { + 'main': { + templateUrl: 'views/paymentUri.html', + }, + }, + needProfile: true + }) + .state('join', { + url: '/join', + needProfile: true, + views: { + 'main': { + templateUrl: 'views/join.html' + }, + } + }) + .state('import', { + url: '/import', + needProfile: true, + views: { + 'main': { + templateUrl: 'views/import.html' + }, + } + }) + .state('create', { + url: '/create', + templateUrl: 'views/create.html', + needProfile: true, + views: { + 'main': { + templateUrl: 'views/create.html' + }, + } + }) + .state('preferencesLanguage', { + url: '/preferencesLanguage', + needProfile: true, + views: { + 'main': { + templateUrl: 'views/preferencesLanguage.html' + }, + } + }) + .state('preferencesUnit', { + url: '/preferencesUnit', + templateUrl: 'views/preferencesUnit.html', + needProfile: true, + views: { + 'main': { + templateUrl: 'views/preferencesUnit.html' + }, + } + }) + .state('preferencesFee', { + url: '/preferencesFee', + templateUrl: 'views/preferencesFee.html', + needProfile: true, + views: { + 'main': { + templateUrl: 'views/preferencesFee.html' + }, + } + }) + .state('uriglidera', { + url: '/uri-glidera/:url', + needProfile: true, + views: { + 'main': { + templateUrl: 'views/glideraUri.html' + }, + } + }) + .state('glidera', { + url: '/glidera', + needProfile: true, + views: { + 'main': { + templateUrl: 'views/glidera.html' + }, + } + }) + .state('buyGlidera', { + url: '/buy', + needProfile: true, + views: { + 'main': { + templateUrl: 'views/buyGlidera.html' + }, + } + }) + .state('sellGlidera', { + url: '/sell', + needProfile: true, + views: { + 'main': { + templateUrl: 'views/sellGlidera.html' + }, + } + }) + .state('preferencesGlidera', { + url: '/preferencesGlidera', + needProfile: true, + views: { + 'main': { + templateUrl: 'views/preferencesGlidera.html' + }, + } + }) + .state('bitpayCard', { + url: '/bitpay-card', + needProfile: true, + views: { + 'main': { + templateUrl: 'views/bitpayCard.html' + }, + } + }) + .state('preferencesBitpayCard', { + url: '/preferences-bitpay-card', + needProfile: true, + views: { + 'main': { + templateUrl: 'views/preferencesBitpayCard.html' + }, + } + }) + .state('coinbase', { + url: '/coinbase', + needProfile: true, + views: { + 'main': { + templateUrl: 'views/coinbase.html' + }, + } + }) + .state('preferencesCoinbase', { + url: '/preferencesCoinbase', + needProfile: true, + views: { + 'main': { + templateUrl: 'views/preferencesCoinbase.html' + }, + } + }) + .state('uricoinbase', { + url: '/uri-coinbase/:url', + needProfile: true, + views: { + 'main': { + templateUrl: 'views/coinbaseUri.html' + }, + } + }) + .state('buyCoinbase', { + url: '/buycoinbase', + needProfile: true, + views: { + 'main': { + templateUrl: 'views/buyCoinbase.html' + }, + } + }) + .state('sellCoinbase', { + url: '/sellcoinbase', + needProfile: true, + views: { + 'main': { + templateUrl: 'views/sellCoinbase.html' + }, + } + }) + .state('buyandsell', { + url: '/buyandsell', + needProfile: true, + views: { + 'main': { + templateUrl: 'views/buyAndSell.html', + controller: function(platformInfo) { + if (platformInfo.isCordova && StatusBar.isVisible) { + StatusBar.backgroundColorByHexString("#4B6178"); + } + } + } + } + }) + .state('amazon', { + url: '/amazon', + needProfile: true, + views: { + 'main': { + templateUrl: 'views/amazon.html' + }, + } + }) + .state('buyAmazon', { + url: '/buyamazon', + needProfile: true, + views: { + 'main': { + templateUrl: 'views/buyAmazon.html' + }, + } + }) + .state('preferencesAltCurrency', { + url: '/preferencesAltCurrency', + templateUrl: 'views/preferencesAltCurrency.html', + needProfile: true, + views: { + 'main': { + templateUrl: 'views/preferencesAltCurrency.html' + }, + } + }) + .state('about', { + url: '/about', + templateUrl: 'views/preferencesAbout.html', + needProfile: true, + views: { + 'main': { + templateUrl: 'views/preferencesAbout.html' + }, + } + }) + .state('logs', { + url: '/logs', + templateUrl: 'views/preferencesLogs.html', + needProfile: true, + views: { + 'main': { + templateUrl: 'views/preferencesLogs.html' + }, + } + }) + .state('paperWallet', { + url: '/paperWallet', + templateUrl: 'views/paperWallet.html', + needProfile: true, + views: { + 'main': { + templateUrl: 'views/paperWallet.html' + }, + } + }) + .state('preferencesGlobal', { + url: '/preferencesGlobal', + needProfile: true, + views: { + 'main': { + templateUrl: 'views/preferencesGlobal.html', + }, + } + }) + .state('termOfUse', { + url: '/termOfUse', + needProfile: true, + views: { + 'main': { + templateUrl: 'views/termOfUse.html', + }, + } + }) + .state('add', { + url: '/add', + needProfile: true, + views: { + 'main': { + templateUrl: 'views/add.html', + controller: function(platformInfo) { + if (platformInfo.isCordova && StatusBar.isVisible) { + StatusBar.backgroundColorByHexString("#4B6178"); + } + } + } + } + }); +}) .run(function($rootScope, $state, $location, $log, $timeout, $ionicPlatform, lodash, platformInfo, profileService, uxLanguage, go, gettextCatalog) { if (platformInfo.isCordova) { diff --git a/src/js/services/txFormatService.js b/src/js/services/txFormatService.js index d4a75873a..bfcaeb1c8 100644 --- a/src/js/services/txFormatService.js +++ b/src/js/services/txFormatService.js @@ -3,17 +3,6 @@ angular.module('copayApp.services').factory('txFormatService', function(bwcService, rateService, configService, lodash) { var root = {}; - - // // RECEIVE - // // Check address - // root.isUsed(wallet.walletId, balance.byAddress, function(err, used) { - // if (used) { - // $log.debug('Address used. Creating new'); - // $rootScope.$emit('Local/AddressIsUsed'); - // } - // }); - // - root.Utils = bwcService.getUtils(); @@ -57,8 +46,8 @@ angular.module('copayApp.services').factory('txFormatService', function(bwcServi }; root.processTx = function(tx) { - if (!tx || tx.action == 'invalid') - return tx; + if (!tx || tx.action == 'invalid') + return tx; // New transaction output format if (tx.outputs && tx.outputs.length) { @@ -77,7 +66,7 @@ angular.module('copayApp.services').factory('txFormatService', function(bwcServi }, 0); } tx.toAddress = tx.outputs[0].toAddress; - } + } tx.amountStr = root.formatAmountStr(tx.amount); tx.alternativeAmountStr = root.formatAlternativeStr(tx.amount); diff --git a/src/js/services/walletService.js b/src/js/services/walletService.js index 4ab83f1b2..00fd0c854 100644 --- a/src/js/services/walletService.js +++ b/src/js/services/walletService.js @@ -1,7 +1,7 @@ 'use strict'; // DO NOT INCLUDE STORAGE HERE \/ \/ -angular.module('copayApp.services').factory('walletService', function($log, $timeout, lodash, trezor, ledger, storageService, configService, rateService, uxLanguage, bwcService, $filter, gettextCatalog, bwcError, $ionicPopup, fingerprintService, ongoingProcess, gettext, $rootScope, txStatus, txFormatService, $ionicModal) { +angular.module('copayApp.services').factory('walletService', function($log, $timeout, lodash, trezor, ledger, storageService, configService, rateService, uxLanguage, $filter, gettextCatalog, bwcError, $ionicPopup, fingerprintService, ongoingProcess, gettext, $rootScope, txStatus, txFormatService, $ionicModal) { // DO NOT INCLUDE STORAGE HERE ^^ // // @@ -12,7 +12,7 @@ angular.module('copayApp.services').factory('walletService', function($log, $tim root.WALLET_STATUS_MAX_TRIES = 7; root.WALLET_STATUS_DELAY_BETWEEN_TRIES = 1.4 * 1000; root.SOFT_CONFIRMATION_LIMIT = 12; - root.HISTORY_SHOW_LIMIT = 10; + root.SAFE_CONFIRMATIONS = 6; // UI Related root.openStatusModal = function(type, txp, cb) { @@ -31,8 +31,15 @@ angular.module('copayApp.services').factory('walletService', function($log, $tim }); }; - - + // // RECEIVE + // // Check address + // root.isUsed(wallet.walletId, balance.byAddress, function(err, used) { + // if (used) { + // $log.debug('Address used. Creating new'); + // $rootScope.$emit('Local/AddressIsUsed'); + // } + // }); + // var _signWithLedger = function(wallet, txp, cb) { $log.info('Requesting Ledger Chrome app to sign the transaction'); @@ -154,12 +161,12 @@ angular.module('copayApp.services').factory('walletService', function($log, $tim cache.unitName = config.unitName; //STR - cache.totalBalanceStr = root.formatAmount(cache.totalBalanceSat) + ' ' + cache.unitName; - cache.lockedBalanceStr = root.formatAmount(cache.lockedBalanceSat) + ' ' + cache.unitName; - cache.availableBalanceStr = root.formatAmount(cache.availableBalanceSat) + ' ' + cache.unitName; + cache.totalBalanceStr = txFormatService.formatAmount(cache.totalBalanceSat) + ' ' + cache.unitName; + cache.lockedBalanceStr = txFormatService.formatAmount(cache.lockedBalanceSat) + ' ' + cache.unitName; + cache.availableBalanceStr = txFormatService.formatAmount(cache.availableBalanceSat) + ' ' + cache.unitName; if (cache.pendingAmount) { - cache.pendingAmountStr = root.formatAmount(cache.pendingAmount) + ' ' + cache.unitName; + cache.pendingAmountStr = txFormatService.formatAmount(cache.pendingAmount) + ' ' + cache.unitName; } else { cache.pendingAmountStr = null; } @@ -229,13 +236,7 @@ angular.module('copayApp.services').factory('walletService', function($log, $tim }); }; - _getStatus(walletStatusHash(), 0, function(err, status) { - if (err) { - root.handleError(err); - return cb(err); - } - return cb(null, status); - }) + _getStatus(walletStatusHash(), 0, cb); }; var getSavedTxs = function(walletId, cb) { @@ -300,8 +301,8 @@ angular.module('copayApp.services').factory('walletService', function($log, $tim if (tx.time > now) tx.time = now; - if (tx.confirmations >= SAFE_CONFIRMATIONS) { - tx.safeConfirmed = SAFE_CONFIRMATIONS + '+'; + if (tx.confirmations >= root.SAFE_CONFIRMATIONS) { + tx.safeConfirmed = root.SAFE_CONFIRMATIONS + '+'; } else { tx.safeConfirmed = false; wallet.hasUnsafeConfirmed = true; @@ -323,13 +324,15 @@ angular.module('copayApp.services').factory('walletService', function($log, $tim return ret; }; - var updateLocalTxHistory = function(wallet, cb) { + var updateLocalTxHistory = function(wallet, progressFn, cb) { var FIRST_LIMIT = 5; var LIMIT = 50; var requestLimit = FIRST_LIMIT; var walletId = wallet.credentials.walletId; var config = configService.getSync().wallet.settings; + progressFn = progressFn || function() {}; + var fixTxsUnit = function(txs) { if (!txs || !txs[0] || !txs[0].amountStr) return; @@ -359,43 +362,27 @@ angular.module('copayApp.services').factory('walletService', function($log, $tim // First update - if (walletId == wallet.credentials.walletId) { - wallet.completeHistory = txsFromLocal; - } + wallet.completeHistory = txsFromLocal; - if (wallet.historyUpdateInProgress) - return; - - wallet.historyUpdateInProgress = true; - - function getNewTxs(newTxs, skip, i_cb) { + function getNewTxs(newTxs, skip, cb) { getTxsFromServer(wallet, skip, endingTxid, requestLimit, function(err, res, shouldContinue) { - if (err) return i_cb(err); + if (err) return cb(err); + + newTxs = newTxs.concat(processNewTxs(wallet, lodash.compact(res))); + + progressFn(newTxs); - newTxs = newTxs.concat(lodash.compact(res)); skip = skip + requestLimit; $log.debug('Syncing TXs. Got:' + newTxs.length + ' Skip:' + skip, ' EndingTxid:', endingTxid, ' Continue:', shouldContinue); if (!shouldContinue) { - newTxs = processNewTxs(wallet, newTxs); $log.debug('Finished Sync: New / soft confirmed Txs: ' + newTxs.length); - return i_cb(null, newTxs); + return cb(null, newTxs); } requestLimit = LIMIT; - getNewTxs(newTxs, skip, i_cb); - - // Progress update - if (walletId == wallet.credentials.walletId) { - wallet.txProgress = newTxs.length; - if (wallet.completeHistory < FIRST_LIMIT && txsFromLocal.length == 0) { - $log.debug('Showing partial history'); - var newHistory = processNewTxs(wallet, newTxs); - newHistory = lodash.compact(newHistory.concat(confirmedTxs)); - wallet.completeHistory = newHistory; - } - } + getNewTxs(newTxs, skip, cb); }); }; @@ -456,10 +443,8 @@ angular.module('copayApp.services').factory('walletService', function($log, $tim }; - root.getHistory = function(wallet, opts, cb) { + root.getTxHistory = function(wallet, opts, cb) { opts = opts || {}; - opts.skip = opts.skip || 0; - opts.limit = opts.limit || root.HISTORY_SHOW_LIMIT; var walletId = wallet.credentials.walletId; @@ -467,10 +452,9 @@ angular.module('copayApp.services').factory('walletService', function($log, $tim $log.debug('Updating Transaction History'); - updateLocalTxHistory(wallet, function(err) { + updateLocalTxHistory(wallet, opts.progressFn, function(err) { if (err) return cb(err); - var txs = wallet.completeHistory ? wallet.completeHistory.slice(opts.skip, opts.limit) : null; - return cb(err, txs); + return cb(err, wallet.completeHistory); }); };