mirror of
https://github.com/Such-Software/hash-wallet.git
synced 2026-10-18 05:51:34 +02:00
Ywallet zcash (#2810)
* feat(zcash): initial commit - initial work on cw_zcash - use single .db for everything zcash to speed up sync and scanning - implement silent autoshielding of non-orchard funds - use FFI for everything to fetch the data - add support for passphrase by adding extra word to seed phrase - enforce lints on CI for cw_zcash directory - use correct zcash name, and call transparent zcash tZEC - minor cleanups outsite of cw_zcash - gitmodules, gitignore - db debug - fix broken addressPageType in WalletInfo - enable debug options in kDebugMode and kProfileMode * feat: T address rotation (and cache) wip: minor fixes * wip: shield tx list * fix fiat amounts fix derrivation of rotation account addresses screen for zcash block height fix T address shields improvements Amount in disposable T shields UI improvements show pending outgoing tx in tx history * fix null check on passphrase page fix tx showing as pending rename auto shield txs fixed send all to include fee use rotating address in addressForExchange wrap all calls of WarpApi.getLatestHeight in try catch to prevent leaking errors other minor fixes from notion * wallet group debug cache sent tx address wallet T address rotation fixes automatically pick the fee for auto-shield * fix T address cache deserialization fix autoshield icon fix autoshield text getCachedDestinationAddress fix send address cache * address comments from review * wip: iOS fix * fix swap * Allow cakepay payment from zcash wallet * fix: ios (I'm stupid) fix: reorder addresses to make orchard default fix: send all balance * 5.6.6 bump fix: ios apple review add transport error to ignored exceptions * fix: leaving dust behind when sweeping all * Change wallets order * fix: reflect balance of pending out txs fix: restore height support * linux support (disabled) * fix: date picker for zcash on restore screen fix: build script for linux match WarpApi.warpSync args with upstream * fix: linter script * ensure all exchange providers support ZEC (#2802) * ensure all exchange providers support ZEC * remove zaddr and tzec currencies and refactor providers * Update lib/exchange/provider/near_Intents_exchange_provider.dart * add back old zcash currencies for backward compatibility, thanks Czarek * minor fix [skip ci] --------- Co-authored-by: Omar Hatem <omarh.ismail1@gmail.com> * Update android/app/src/main/AndroidManifestBase.xml [skip ci] * Update ios/Runner/InfoBase.plist [skip ci] * fix: remove unused code fix: macos fix: disable on linux and macos * update build numbers [skip ci] * Add zcash to birdpay --------- Co-authored-by: Czarek Nakamoto <cyjan@mrcyjanek.net> Co-authored-by: Serhii <borodenko.sv@gmail.com>
This commit is contained in:
co-authored by
Czarek Nakamoto
Serhii
parent
2a77d359f1
commit
ef9b0fbae6
@@ -35,7 +35,7 @@ class AnonPayApi {
|
||||
clearnetUri: Uri.https(clearNetAuthority, "$anonPayStatus/$id"),
|
||||
onionUri: Uri.https(onionApiAuthority, "$anonPayStatus/$id"),
|
||||
);
|
||||
|
||||
|
||||
final responseJSON = json.decode(response.body) as Map<String, dynamic>;
|
||||
final status = responseJSON['Status'] as String;
|
||||
final fiatAmount = responseJSON['Fiat_Amount'] as double?;
|
||||
|
||||
@@ -122,6 +122,7 @@ class RobinhoodBuyProvider extends BuyProvider {
|
||||
case WalletType.banano:
|
||||
case WalletType.wownero:
|
||||
case WalletType.zano:
|
||||
case WalletType.zcash:
|
||||
case WalletType.decred:
|
||||
throw Exception("Wallet Type ${wallet.type.name} is not available for Robinhood");
|
||||
}
|
||||
|
||||
@@ -1,4 +1,4 @@
|
||||
enum CakePayPaymentMethod { BTC, BTC_LN, XMR, LTC, LTC_MWEB }
|
||||
enum CakePayPaymentMethod { BTC, BTC_LN, XMR, LTC, LTC_MWEB, ZEC }
|
||||
|
||||
extension CakePayPaymentMethodLabel on CakePayPaymentMethod {
|
||||
String get label => switch (this) {
|
||||
@@ -7,6 +7,7 @@ extension CakePayPaymentMethodLabel on CakePayPaymentMethod {
|
||||
CakePayPaymentMethod.XMR => 'Monero',
|
||||
CakePayPaymentMethod.LTC => 'Litecoin',
|
||||
CakePayPaymentMethod.LTC_MWEB => 'MWEB',
|
||||
CakePayPaymentMethod.ZEC => 'Zcash',
|
||||
};
|
||||
}
|
||||
|
||||
@@ -63,7 +64,9 @@ class CakePayOrder {
|
||||
CakePayPaymentMethod.XMR => order.paymentData.xmr,
|
||||
CakePayPaymentMethod.LTC => order.paymentData.ltc,
|
||||
CakePayPaymentMethod.LTC_MWEB => order.paymentData.ltc_mweb,
|
||||
_ => null
|
||||
CakePayPaymentMethod.ZEC => order.paymentData.zec,
|
||||
// TODO: Handle this case.
|
||||
CakePayPaymentMethod.BTC_LN => throw UnimplementedError(),
|
||||
};
|
||||
|
||||
if (data == null) return null;
|
||||
@@ -87,6 +90,7 @@ class CakePayOrder {
|
||||
CakePayPaymentMethod.XMR => 'XMR',
|
||||
CakePayPaymentMethod.LTC => 'LTC',
|
||||
CakePayPaymentMethod.LTC_MWEB => 'LTC',
|
||||
CakePayPaymentMethod.ZEC => 'ZEC',
|
||||
};
|
||||
}
|
||||
}
|
||||
@@ -129,6 +133,7 @@ class PaymentData {
|
||||
final CryptoPaymentData? xmr;
|
||||
final CryptoPaymentData? ltc;
|
||||
final CryptoPaymentData? ltc_mweb;
|
||||
final CryptoPaymentData? zec;
|
||||
final DateTime invoiceTime;
|
||||
final DateTime expirationTime;
|
||||
final int? commission;
|
||||
@@ -139,6 +144,7 @@ class PaymentData {
|
||||
required this.xmr,
|
||||
required this.ltc,
|
||||
required this.ltc_mweb,
|
||||
required this.zec,
|
||||
required this.invoiceTime,
|
||||
required this.expirationTime,
|
||||
required this.commission,
|
||||
@@ -151,6 +157,7 @@ class PaymentData {
|
||||
xmr: map['XMR'] != null ? CryptoPaymentData.fromMap(map['XMR'] as Map<String, dynamic>) : null,
|
||||
ltc: map['LTC'] != null ? CryptoPaymentData.fromMap(map['LTC'] as Map<String, dynamic>) : null,
|
||||
ltc_mweb: map['LTC_MWEB'] != null ? CryptoPaymentData.fromMap(map['LTC_MWEB'] as Map<String, dynamic>) : null,
|
||||
zec: map['ZEC_CHAIN'] != null ? CryptoPaymentData.fromMap(map['ZEC_CHAIN'] as Map<String, dynamic>) : null,
|
||||
invoiceTime: DateTime.fromMillisecondsSinceEpoch(map['invoice_time'] as int),
|
||||
expirationTime: DateTime.fromMillisecondsSinceEpoch(map['expiration_time'] as int),
|
||||
commission: map['commission'] as int?,
|
||||
|
||||
@@ -135,10 +135,15 @@ class AddressValidator extends TextValidator {
|
||||
'|[13][a-km-zA-HJ-NP-Z1-9]{25,34}';
|
||||
case CryptoCurrency.hbar:
|
||||
pattern = '[0-9a-zA-Z.]+';
|
||||
case CryptoCurrency.zaddr:
|
||||
pattern = 'zs[0-9a-zA-Z]{75}';
|
||||
case CryptoCurrency.zec:
|
||||
pattern = 't1[0-9a-zA-Z]{33}|t3[0-9a-zA-Z]{33}';
|
||||
pattern =
|
||||
'(?:'
|
||||
't1[0-9A-Za-z]{33}'
|
||||
'|t3[0-9A-Za-z]{33}'
|
||||
'|zs[a-z0-9]{76}'
|
||||
'|zxviews[a-z0-9]{278}'
|
||||
'|u1[a-z0-9]{1,300}'
|
||||
')';
|
||||
case CryptoCurrency.dcr:
|
||||
pattern = '(D|T|S)[ksecS]([0-9a-zA-Z])+';
|
||||
case CryptoCurrency.rvn:
|
||||
@@ -282,8 +287,6 @@ class AddressValidator extends TextValidator {
|
||||
return [34];
|
||||
case CryptoCurrency.zen:
|
||||
return [35];
|
||||
case CryptoCurrency.zaddr:
|
||||
return null;
|
||||
case CryptoCurrency.zec:
|
||||
return null;
|
||||
case CryptoCurrency.kmd:
|
||||
@@ -352,6 +355,15 @@ class AddressValidator extends TextValidator {
|
||||
pattern = '(T|t)[1-9A-HJ-NP-Za-km-z]{33}';
|
||||
case CryptoCurrency.zano:
|
||||
pattern = '([1-9A-HJ-NP-Za-km-z]{90,200})|(@[\w\d.-]+)';
|
||||
case CryptoCurrency.zec:
|
||||
pattern =
|
||||
'(?:'
|
||||
't1[0-9A-Za-z]{33}'
|
||||
'|t3[0-9A-Za-z]{33}'
|
||||
'|zs[a-z0-9]{76}'
|
||||
'|zxviews[a-z0-9]{278}'
|
||||
'|u1[a-z0-9]{1,300}'
|
||||
')';
|
||||
default:
|
||||
if (type.tag == CryptoCurrency.eth.title) {
|
||||
pattern = '0x[0-9a-zA-Z]+';
|
||||
|
||||
@@ -253,6 +253,21 @@ class DogeURI extends PaymentURI {
|
||||
}
|
||||
}
|
||||
|
||||
class ZcashURI extends PaymentURI {
|
||||
ZcashURI({required super.amount, required super.address});
|
||||
|
||||
@override
|
||||
String toString() {
|
||||
var base = 'zcash:$address';
|
||||
|
||||
if (amount.isNotEmpty) {
|
||||
base += '?amount=${amount.replaceAll(',', '.')}';
|
||||
}
|
||||
|
||||
return base;
|
||||
}
|
||||
}
|
||||
|
||||
class ERC681URI extends PaymentURI {
|
||||
final int chainId;
|
||||
final String? contractAddress;
|
||||
|
||||
@@ -10,6 +10,7 @@ import 'package:cake_wallet/wownero/wownero.dart';
|
||||
import 'package:cake_wallet/zano/zano.dart';
|
||||
import 'package:cake_wallet/decred/decred.dart';
|
||||
import 'package:cake_wallet/utils/language_list.dart';
|
||||
import 'package:cake_wallet/zcash/zcash.dart';
|
||||
import 'package:cw_core/wallet_type.dart';
|
||||
|
||||
class SeedValidator extends Validator<MnemonicItem> {
|
||||
@@ -52,6 +53,8 @@ class SeedValidator extends Validator<MnemonicItem> {
|
||||
return zano!.getWordList(language);
|
||||
case WalletType.decred:
|
||||
return decred!.getDecredWordList();
|
||||
case WalletType.zcash:
|
||||
return zcash!.getZcashWordList(language);
|
||||
case WalletType.none:
|
||||
case WalletType.haven:
|
||||
return [];
|
||||
|
||||
@@ -84,6 +84,7 @@ class WalletCreationService {
|
||||
case WalletType.tron:
|
||||
case WalletType.dogecoin:
|
||||
case WalletType.nano:
|
||||
case WalletType.zcash:
|
||||
return true;
|
||||
case WalletType.monero:
|
||||
case WalletType.wownero:
|
||||
|
||||
+4
-1
@@ -62,6 +62,7 @@ import 'package:cake_wallet/view_model/link_view_model.dart';
|
||||
import 'package:cake_wallet/tron/tron.dart';
|
||||
import 'package:cake_wallet/src/screens/transaction_details/rbf_details_page.dart';
|
||||
import 'package:cake_wallet/view_model/start_tor_view_model.dart';
|
||||
import 'package:cake_wallet/zcash/zcash.dart';
|
||||
import 'package:cw_core/receive_page_option.dart';
|
||||
import 'package:cake_wallet/entities/wallet_edit_page_arguments.dart';
|
||||
import 'package:cake_wallet/entities/wallet_manager.dart';
|
||||
@@ -1109,7 +1110,7 @@ Future<void> setup({
|
||||
getIt.registerFactory<MoonPayProvider>(() => MoonPayProvider(
|
||||
appStore: getIt.get<AppStore>(),
|
||||
wallet: getIt.get<AppStore>().wallet!,
|
||||
isTestEnvironment: kDebugMode,
|
||||
isTestEnvironment: kDebugMode || kProfileMode,
|
||||
));
|
||||
|
||||
getIt.registerFactory<OnRamperBuyProvider>(() => OnRamperBuyProvider(
|
||||
@@ -1224,6 +1225,8 @@ Future<void> setup({
|
||||
return decred!.createDecredWalletService(_unspentCoinsInfoSource);
|
||||
case WalletType.haven:
|
||||
return HavenWalletService();
|
||||
case WalletType.zcash:
|
||||
return zcash!.createZcashWalletService(SettingsStoreBase.walletPasswordDirectInput);
|
||||
case WalletType.none:
|
||||
throw Exception('Unexpected token: ${param1.toString()} for generating of WalletService');
|
||||
}
|
||||
|
||||
@@ -52,6 +52,7 @@ const decredDefaultUri = "default-spv-nodes";
|
||||
const dogecoinDefaultNodeUri = 'dogecoin.stackwallet.com:50022';
|
||||
const baseDefaultNodeUri = 'base.nownodes.io';
|
||||
const arbitrumDefaultNodeUri = 'arbitrum.nownodes.io';
|
||||
const zcashDefaultNodeUri = 'zec-node.cakewallet.com:443';
|
||||
|
||||
Future<void> defaultSettingsMigration(
|
||||
{required int version,
|
||||
@@ -559,7 +560,14 @@ Future<void> defaultSettingsMigration(
|
||||
case 54:
|
||||
await _backupWowneroSeeds(havenSeedStore);
|
||||
break;
|
||||
|
||||
case 55:
|
||||
await addWalletNodeList(nodes: nodes, type: WalletType.zcash);
|
||||
await _changeDefaultNode(
|
||||
nodes: nodes,
|
||||
sharedPreferences: sharedPreferences,
|
||||
type: WalletType.zcash,
|
||||
currentNodePreferenceKey: PreferencesKey.currentZcashNodeIdKey,
|
||||
);
|
||||
default:
|
||||
break;
|
||||
}
|
||||
@@ -672,6 +680,8 @@ String _getDefaultNodeUri(WalletType type) {
|
||||
return baseDefaultNodeUri;
|
||||
case WalletType.arbitrum:
|
||||
return arbitrumDefaultNodeUri;
|
||||
case WalletType.zcash:
|
||||
return zcashDefaultNodeUri;
|
||||
case WalletType.banano:
|
||||
case WalletType.none:
|
||||
return '';
|
||||
@@ -1092,6 +1102,7 @@ Future<void> checkCurrentNodes(
|
||||
final currentTronNodeId = sharedPreferences.getInt(PreferencesKey.currentTronNodeIdKey);
|
||||
final currentWowneroNodeId = sharedPreferences.getInt(PreferencesKey.currentWowneroNodeIdKey);
|
||||
final currentZanoNodeId = sharedPreferences.getInt(PreferencesKey.currentZanoNodeIdKey);
|
||||
final currentZcashNodeId = sharedPreferences.getInt(PreferencesKey.currentZcashNodeIdKey);
|
||||
final currentMoneroNode =
|
||||
nodeSource.values.firstWhereOrNull((node) => node.key == currentMoneroNodeId);
|
||||
final currentBitcoinElectrumServer =
|
||||
@@ -1126,6 +1137,8 @@ Future<void> checkCurrentNodes(
|
||||
nodeSource.values.firstWhereOrNull((node) => node.key == currentWowneroNodeId);
|
||||
final currentZanoNode =
|
||||
nodeSource.values.firstWhereOrNull((node) => node.key == currentZanoNodeId);
|
||||
final currentZcashNode =
|
||||
nodeSource.values.firstWhereOrNull((node) => node.key == currentZcashNodeId);
|
||||
|
||||
if (currentMoneroNode == null) {
|
||||
final newCakeWalletNode = Node(uri: newCakeWalletMoneroUri, type: WalletType.monero);
|
||||
@@ -1240,6 +1253,12 @@ Future<void> checkCurrentNodes(
|
||||
await nodeSource.add(node);
|
||||
await sharedPreferences.setInt(PreferencesKey.currentDecredNodeIdKey, node.key as int);
|
||||
}
|
||||
|
||||
if (currentZcashNode == null) {
|
||||
final node = Node(uri: zcashDefaultNodeUri, type: WalletType.zcash, useSSL: true);
|
||||
await nodeSource.add(node);
|
||||
await sharedPreferences.setInt(PreferencesKey.currentZcashNodeIdKey, node.key as int);
|
||||
}
|
||||
}
|
||||
|
||||
Future<void> resetBitcoinElectrumServer(
|
||||
|
||||
@@ -2,6 +2,7 @@ import 'dart:convert';
|
||||
|
||||
import 'package:cake_wallet/.secrets.g.dart' as secrets;
|
||||
import 'package:cw_core/wallet_base.dart';
|
||||
import 'package:flutter/foundation.dart';
|
||||
import 'package:hashlib/hashlib.dart';
|
||||
|
||||
String createHashedWalletIdentifier(WalletBase wallet) {
|
||||
@@ -9,8 +10,10 @@ String createHashedWalletIdentifier(WalletBase wallet) {
|
||||
|
||||
final salt = secrets.walletGroupSalt;
|
||||
final combined = '$salt.$hashContent';
|
||||
|
||||
final bytes = utf8.encode(combined);
|
||||
final digest = sha256.convert(bytes);
|
||||
if (kDebugMode) {
|
||||
return "$combined;$digest";
|
||||
}
|
||||
return digest.toString();
|
||||
}
|
||||
|
||||
@@ -56,6 +56,9 @@ Future<List<Node>> loadDefaultNodes(WalletType type) async {
|
||||
case WalletType.arbitrum:
|
||||
path = 'assets/arbitrum_node_list.yml';
|
||||
break;
|
||||
case WalletType.zcash:
|
||||
path = 'assets/zcash_node_list.yml';
|
||||
break;
|
||||
case WalletType.banano:
|
||||
case WalletType.none:
|
||||
path = '';
|
||||
@@ -109,6 +112,7 @@ Future<void> resetToDefault(Box<Node> nodeSource) async {
|
||||
final dogecoinElectrumServerList = await loadDefaultNodes(WalletType.dogecoin);
|
||||
final baseNodes = await loadDefaultNodes(WalletType.base);
|
||||
final arbitrumNodes = await loadDefaultNodes(WalletType.arbitrum);
|
||||
final zcashNodes = await loadDefaultNodes(WalletType.zcash);
|
||||
|
||||
final nodes = moneroNodes +
|
||||
bitcoinElectrumServerList +
|
||||
@@ -124,7 +128,8 @@ Future<void> resetToDefault(Box<Node> nodeSource) async {
|
||||
decredNodes +
|
||||
dogecoinElectrumServerList +
|
||||
baseNodes +
|
||||
arbitrumNodes;
|
||||
arbitrumNodes +
|
||||
zcashNodes;
|
||||
|
||||
await nodeSource.clear();
|
||||
await nodeSource.addAll(nodes);
|
||||
|
||||
@@ -175,7 +175,7 @@ class AddressResolver {
|
||||
var addressPattern = AddressValidator.getAddressFromStringPattern(type);
|
||||
|
||||
if (addressPattern == null) {
|
||||
throw Exception('Unexpected token: $type for getAddressFromStringPattern');
|
||||
return null;
|
||||
}
|
||||
|
||||
if (requireSurroundingWhitespaces)
|
||||
|
||||
@@ -22,6 +22,7 @@ class PreferencesKey {
|
||||
static const currentSolanaNodeIdKey = 'current_node_id_sol';
|
||||
static const currentTronNodeIdKey = 'current_node_id_trx';
|
||||
static const currentWowneroNodeIdKey = 'current_node_id_wow';
|
||||
static const currentZcashNodeIdKey = 'current_node_id_zec';
|
||||
static const currentTransactionPriorityKeyLegacy = 'current_fee_priority';
|
||||
static const currentBalanceDisplayModeKey = 'current_balance_display_mode';
|
||||
static const shouldSaveRecipientAddressKey = 'save_recipient_address';
|
||||
|
||||
@@ -6,6 +6,7 @@ import 'package:cake_wallet/monero/monero.dart';
|
||||
import 'package:cake_wallet/wownero/wownero.dart';
|
||||
import 'package:cake_wallet/zano/zano.dart';
|
||||
import 'package:cake_wallet/decred/decred.dart';
|
||||
import 'package:cake_wallet/zcash/zcash.dart';
|
||||
import 'package:cw_core/transaction_priority.dart';
|
||||
import 'package:cw_core/wallet_type.dart';
|
||||
|
||||
@@ -37,6 +38,8 @@ List<TransactionPriority> priorityForWalletType(WalletType type) {
|
||||
return zano!.getTransactionPriorities();
|
||||
case WalletType.decred:
|
||||
return decred!.getTransactionPriorities();
|
||||
case WalletType.zcash:
|
||||
return zcash!.getTransactionPriorities();
|
||||
case WalletType.none:
|
||||
case WalletType.haven:
|
||||
return [];
|
||||
|
||||
@@ -16,10 +16,8 @@ import 'package:cw_core/utils/proxy_wrapper.dart';
|
||||
import 'package:cake_wallet/utils/exchange_provider_logger.dart';
|
||||
|
||||
class ChainflipExchangeProvider extends ExchangeProvider {
|
||||
ChainflipExchangeProvider({required this.tradesStore})
|
||||
: super(pairList: supportedPairs(_notSupported));
|
||||
ChainflipExchangeProvider({required this.tradesStore});
|
||||
|
||||
static final List<CryptoCurrency> _notSupported = [];
|
||||
static final List<CryptoCurrency> _supported = [
|
||||
CryptoCurrency.btc,
|
||||
CryptoCurrency.eth,
|
||||
|
||||
@@ -21,13 +21,8 @@ import 'package:cake_wallet/utils/exchange_provider_logger.dart';
|
||||
class ChangeNowExchangeProvider extends ExchangeProvider {
|
||||
ChangeNowExchangeProvider({required SettingsStore settingsStore})
|
||||
: _settingsStore = settingsStore,
|
||||
_lastUsedRateId = '',
|
||||
super(pairList: supportedPairs(_notSupported));
|
||||
_lastUsedRateId = '';
|
||||
|
||||
static const List<CryptoCurrency> _notSupported = [
|
||||
CryptoCurrency.zaddr,
|
||||
CryptoCurrency.xhv,
|
||||
];
|
||||
|
||||
static final apiKey =
|
||||
isMoneroOnly ? secrets.changeNowMoneroApiKey : secrets.changeNowCakeWalletApiKey;
|
||||
|
||||
@@ -6,12 +6,10 @@ import 'package:cake_wallet/exchange/trade_request.dart';
|
||||
import 'package:cw_core/crypto_currency.dart';
|
||||
|
||||
abstract class ExchangeProvider {
|
||||
ExchangeProvider({required this.pairList});
|
||||
ExchangeProvider();
|
||||
|
||||
String get title;
|
||||
|
||||
List<ExchangePair> pairList;
|
||||
|
||||
ExchangeProviderDescription get description;
|
||||
|
||||
bool get isAvailable;
|
||||
|
||||
@@ -16,33 +16,13 @@ import 'package:cw_core/utils/print_verbose.dart';
|
||||
import 'package:cake_wallet/utils/exchange_provider_logger.dart';
|
||||
|
||||
class ExolixExchangeProvider extends ExchangeProvider {
|
||||
ExolixExchangeProvider() : super(pairList: supportedPairs(_notSupported));
|
||||
ExolixExchangeProvider();
|
||||
|
||||
static final apiKey = isMoneroOnly ? secrets.exolixMoneroApiKey : secrets.exolixCakeWalletApiKey;
|
||||
static const apiBaseUrl = 'exolix.com';
|
||||
static const transactionsPath = '/api/v2/transactions';
|
||||
static const ratePath = '/api/v2/rate';
|
||||
|
||||
static const List<CryptoCurrency> _notSupported = [
|
||||
CryptoCurrency.usdt,
|
||||
CryptoCurrency.xhv,
|
||||
CryptoCurrency.btt,
|
||||
CryptoCurrency.firo,
|
||||
CryptoCurrency.zaddr,
|
||||
CryptoCurrency.xvg,
|
||||
CryptoCurrency.kmd,
|
||||
CryptoCurrency.paxg,
|
||||
CryptoCurrency.rune,
|
||||
CryptoCurrency.scrt,
|
||||
CryptoCurrency.btcln,
|
||||
CryptoCurrency.cro,
|
||||
CryptoCurrency.ftm,
|
||||
CryptoCurrency.frax,
|
||||
CryptoCurrency.gusd,
|
||||
CryptoCurrency.gtc,
|
||||
CryptoCurrency.weth,
|
||||
];
|
||||
|
||||
@override
|
||||
String get title => 'Exolix';
|
||||
|
||||
|
||||
@@ -16,9 +16,7 @@ import 'package:cw_core/utils/print_verbose.dart';
|
||||
import 'package:cake_wallet/utils/exchange_provider_logger.dart';
|
||||
|
||||
class LetsExchangeExchangeProvider extends ExchangeProvider {
|
||||
LetsExchangeExchangeProvider() : super(pairList: supportedPairs(_notSupported));
|
||||
|
||||
static const List<CryptoCurrency> _notSupported = [];
|
||||
LetsExchangeExchangeProvider();
|
||||
|
||||
static const apiKey = secrets.letsExchangeBearerToken;
|
||||
static const _baseUrl = 'api.letsexchange.io';
|
||||
|
||||
@@ -17,10 +17,7 @@ import 'package:cw_core/utils/print_verbose.dart';
|
||||
import 'package:cake_wallet/utils/exchange_provider_logger.dart';
|
||||
|
||||
class NearIntentsExchangeProvider extends ExchangeProvider {
|
||||
NearIntentsExchangeProvider()
|
||||
: super(pairList: supportedPairs(_notSupported));
|
||||
|
||||
static const List<CryptoCurrency> _notSupported = [];
|
||||
NearIntentsExchangeProvider();
|
||||
|
||||
static const apiKey = secrets.nearIntentsBearerToken;
|
||||
static const _baseUrl = '1click.chaindefuser.com';
|
||||
@@ -44,7 +41,6 @@ class NearIntentsExchangeProvider extends ExchangeProvider {
|
||||
// UTXO
|
||||
'LTC': 'ltc1qhdwz74m3wuuhppv2mckagqk9e2e49z5j4kucnv',
|
||||
'BTC': 'bc1qw508d6qejxtdg4y5r3zarvary0c5xw7kygt080',
|
||||
'ZZEC': 't1Zcash4hPS2bq8rTQkN9bKpZV1X4W3pZxK',
|
||||
'DOGE': 'D9t7rGQ9mE3hJ2z1w8pGQxkGmKjYwYc8pQ',
|
||||
'BCH': 'qpm2qsznhks23z7629mms6s4cwef74vcwvy22gdx6a',
|
||||
|
||||
@@ -63,6 +59,7 @@ class NearIntentsExchangeProvider extends ExchangeProvider {
|
||||
'TON': 'UQAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAM9c',
|
||||
'XLM': 'GA3D5O2W7YQZJQ3H4Y5QW6N7V8X9Z0A1B2C3D4E5F6G7H8I9J0',
|
||||
'ADA': 'addr1vyc33hdv5vag52f3d8h0qsngu52vm27x28zkzru333jma9gaxd38v',
|
||||
'ZEC': 't1VdfFUbyTT7ZSdeEaHuwB7veGD1NXoUhGS',
|
||||
};
|
||||
|
||||
String getNearDummyAddress(CryptoCurrency currency) {
|
||||
@@ -430,8 +427,7 @@ class NearIntentsExchangeProvider extends ExchangeProvider {
|
||||
try {
|
||||
final uri = Uri.https(_baseUrl, '$_versionPath$_tokenPath');
|
||||
|
||||
final response =
|
||||
await ProxyWrapper().get(clearnetUri: uri, headers: _headers);
|
||||
final response = await ProxyWrapper().get(clearnetUri: uri, headers: _headers);
|
||||
if (response.statusCode != 200) return [];
|
||||
|
||||
final data = json.decode(response.body) as List<dynamic>;
|
||||
@@ -532,14 +528,6 @@ class NearIntentsExchangeProvider extends ExchangeProvider {
|
||||
};
|
||||
}
|
||||
|
||||
String _normalizeTitleToNearSymbol(CryptoCurrency currency) {
|
||||
final title = currency.title.toUpperCase();
|
||||
return switch (title) {
|
||||
'TZEC' => 'ZEC',
|
||||
_ => title,
|
||||
};
|
||||
}
|
||||
|
||||
String? _normalizeTagToNearBlockchain(String? tag) {
|
||||
return switch (tag) {
|
||||
'TRX' => 'tron',
|
||||
@@ -559,7 +547,7 @@ class NearIntentsExchangeProvider extends ExchangeProvider {
|
||||
Token? currencyToNearAssetId(CryptoCurrency currency, List<Token> supported) {
|
||||
if (supported.isEmpty) return null;
|
||||
|
||||
final symbol = _normalizeTitleToNearSymbol(currency).toUpperCase();
|
||||
final symbol = currency.title.toUpperCase();
|
||||
final blockchain = _normalizeTagToNearBlockchain(currency.tag);
|
||||
|
||||
// Native asset (no contract)
|
||||
|
||||
@@ -16,23 +16,7 @@ import 'package:cw_core/utils/print_verbose.dart';
|
||||
import 'package:cake_wallet/utils/exchange_provider_logger.dart';
|
||||
|
||||
class SideShiftExchangeProvider extends ExchangeProvider {
|
||||
SideShiftExchangeProvider() : super(pairList: supportedPairs(_notSupported));
|
||||
|
||||
static const List<CryptoCurrency> _notSupported = [
|
||||
CryptoCurrency.xhv,
|
||||
CryptoCurrency.dcr,
|
||||
CryptoCurrency.kmd,
|
||||
CryptoCurrency.oxt,
|
||||
CryptoCurrency.pivx,
|
||||
CryptoCurrency.rune,
|
||||
CryptoCurrency.rvn,
|
||||
CryptoCurrency.scrt,
|
||||
CryptoCurrency.stx,
|
||||
CryptoCurrency.bttc,
|
||||
CryptoCurrency.usdt,
|
||||
CryptoCurrency.eos,
|
||||
CryptoCurrency.xmr,
|
||||
];
|
||||
SideShiftExchangeProvider();
|
||||
|
||||
static const affiliateId = secrets.sideShiftAffiliateId;
|
||||
static const apiBaseUrl = 'https://sideshift.ai/api';
|
||||
|
||||
@@ -16,12 +16,8 @@ import 'package:cw_core/crypto_currency.dart';
|
||||
import 'package:cake_wallet/utils/exchange_provider_logger.dart';
|
||||
|
||||
class SimpleSwapExchangeProvider extends ExchangeProvider {
|
||||
SimpleSwapExchangeProvider() : super(pairList: supportedPairs(_notSupported));
|
||||
SimpleSwapExchangeProvider();
|
||||
|
||||
static const List<CryptoCurrency> _notSupported = [
|
||||
CryptoCurrency.zaddr,
|
||||
CryptoCurrency.xhv,
|
||||
];
|
||||
|
||||
static final apiKey =
|
||||
DeviceInfo.instance.isMobile ? secrets.simpleSwapApiKey : secrets.simpleSwapApiKeyDesktop;
|
||||
@@ -347,8 +343,6 @@ class SimpleSwapExchangeProvider extends ExchangeProvider {
|
||||
|
||||
static String _normalizeCurrency(CryptoCurrency currency) {
|
||||
switch (currency) {
|
||||
case CryptoCurrency.zaddr:
|
||||
return 'zec';
|
||||
case CryptoCurrency.zec:
|
||||
return 'zec';
|
||||
case CryptoCurrency.bnb:
|
||||
|
||||
@@ -15,9 +15,7 @@ import 'package:cw_core/crypto_currency.dart';
|
||||
import 'package:cake_wallet/utils/exchange_provider_logger.dart';
|
||||
|
||||
class StealthExExchangeProvider extends ExchangeProvider {
|
||||
StealthExExchangeProvider() : super(pairList: supportedPairs(_notSupported));
|
||||
|
||||
static const List<CryptoCurrency> _notSupported = [];
|
||||
StealthExExchangeProvider();
|
||||
|
||||
static final apiKey = secrets.stealthExBearerToken;
|
||||
static final _additionalFeePercent = double.tryParse(secrets.stealthExAdditionalFeePercent);
|
||||
|
||||
@@ -15,9 +15,7 @@ import 'package:cw_core/utils/proxy_wrapper.dart';
|
||||
import 'package:cw_core/crypto_currency.dart';
|
||||
|
||||
class SwapsXyzExchangeProvider extends ExchangeProvider {
|
||||
SwapsXyzExchangeProvider() : super(pairList: supportedPairs(_notSupported));
|
||||
|
||||
static const List<CryptoCurrency> _notSupported = [];
|
||||
SwapsXyzExchangeProvider();
|
||||
|
||||
static final _apiKey = secrets.swapsXyzApiKey;
|
||||
static const _baseUrl = 'api-v2.swaps.xyz';
|
||||
|
||||
@@ -16,25 +16,7 @@ import 'package:cw_core/utils/print_verbose.dart';
|
||||
import 'package:cake_wallet/utils/exchange_provider_logger.dart';
|
||||
|
||||
class SwapTradeExchangeProvider extends ExchangeProvider {
|
||||
SwapTradeExchangeProvider() : super(pairList: supportedPairs(_notSupported));
|
||||
|
||||
static final List<CryptoCurrency> _notSupported = [
|
||||
...(CryptoCurrency.all
|
||||
.where((element) => ![
|
||||
CryptoCurrency.btc,
|
||||
CryptoCurrency.sol,
|
||||
CryptoCurrency.eth,
|
||||
CryptoCurrency.ltc,
|
||||
CryptoCurrency.ada,
|
||||
CryptoCurrency.bch,
|
||||
CryptoCurrency.usdterc20,
|
||||
CryptoCurrency.usdttrc20,
|
||||
CryptoCurrency.bnb,
|
||||
CryptoCurrency.xmr,
|
||||
CryptoCurrency.zec,
|
||||
].contains(element))
|
||||
.toList())
|
||||
];
|
||||
SwapTradeExchangeProvider();
|
||||
|
||||
static final markup = secrets.swapTradeExchangeMarkup;
|
||||
|
||||
@@ -220,8 +202,11 @@ class SwapTradeExchangeProvider extends ExchangeProvider {
|
||||
final responseBody = json.decode(response.body) as Map<String, dynamic>;
|
||||
|
||||
if (response.statusCode == 400 || responseBody["success"] == false) {
|
||||
final error = responseBody['errors'][0]['msg'] as String;
|
||||
|
||||
final List<dynamic> errorsList = responseBody['errors'] as List? ?? [];
|
||||
final error = errorsList.isNotEmpty
|
||||
? (errorsList[0]['msg'] as String?) ?? responseBody.toString()
|
||||
: responseBody.toString();
|
||||
|
||||
ExchangeProviderLogger.logError(
|
||||
provider: description,
|
||||
function: 'createTrade',
|
||||
|
||||
@@ -14,26 +14,7 @@ import 'package:hive/hive.dart';
|
||||
import 'package:cake_wallet/utils/exchange_provider_logger.dart';
|
||||
|
||||
class ThorChainExchangeProvider extends ExchangeProvider {
|
||||
ThorChainExchangeProvider({required this.tradesStore})
|
||||
: super(pairList: supportedPairs(_notSupported));
|
||||
|
||||
static final List<CryptoCurrency> _notSupported = [
|
||||
...(CryptoCurrency.all
|
||||
.where((element) => ![
|
||||
CryptoCurrency.btc,
|
||||
// CryptoCurrency.eth,
|
||||
CryptoCurrency.ltc,
|
||||
CryptoCurrency.bch,
|
||||
CryptoCurrency.usdtbsc,
|
||||
// CryptoCurrency.aave,
|
||||
// CryptoCurrency.dai,
|
||||
// CryptoCurrency.gusd,
|
||||
// CryptoCurrency.usdc,
|
||||
// CryptoCurrency.usdterc20,
|
||||
// CryptoCurrency.wbtc, // TODO: temporarily commented until https://github.com/cake-tech/cake_wallet/pull/1436 is merged
|
||||
].contains(element))
|
||||
.toList())
|
||||
];
|
||||
ThorChainExchangeProvider({required this.tradesStore});
|
||||
|
||||
static final isRefundAddressSupported = [CryptoCurrency.eth];
|
||||
|
||||
|
||||
@@ -17,8 +17,7 @@ import 'package:cake_wallet/utils/exchange_provider_logger.dart';
|
||||
class TrocadorExchangeProvider extends ExchangeProvider {
|
||||
TrocadorExchangeProvider({this.useTorOnly = false, this.providerStates = const {}})
|
||||
: _lastUsedRateId = '',
|
||||
_provider = [],
|
||||
super(pairList: supportedPairs(_notSupported));
|
||||
_provider = [];
|
||||
|
||||
bool useTorOnly;
|
||||
Map<String, bool> providerStates;
|
||||
@@ -48,11 +47,6 @@ class TrocadorExchangeProvider extends ExchangeProvider {
|
||||
'SwapSpace',
|
||||
];
|
||||
|
||||
static const List<CryptoCurrency> _notSupported = [
|
||||
CryptoCurrency.stx,
|
||||
CryptoCurrency.zaddr,
|
||||
];
|
||||
|
||||
static final apiKey = isMoneroOnly ? secrets.trocadorMoneroApiKey : secrets.trocadorApiKey;
|
||||
static const clearNetAuthority = 'api.trocador.app';
|
||||
static const onionApiAuthority = clearNetAuthority;
|
||||
|
||||
@@ -13,9 +13,7 @@ import 'package:cw_core/utils/print_verbose.dart';
|
||||
import 'package:cw_core/utils/proxy_wrapper.dart';
|
||||
import 'package:cake_wallet/utils/exchange_provider_logger.dart';
|
||||
class XOSwapExchangeProvider extends ExchangeProvider {
|
||||
XOSwapExchangeProvider() : super(pairList: supportedPairs(_notSupported));
|
||||
|
||||
static const List<CryptoCurrency> _notSupported = [];
|
||||
XOSwapExchangeProvider();
|
||||
|
||||
static const _apiAuthority = 'exchange.exodus.io';
|
||||
static const _apiPath = '/v3';
|
||||
|
||||
+9
-1
@@ -34,10 +34,12 @@ import 'package:cake_wallet/utils/exception_handler.dart';
|
||||
import 'package:cake_wallet/utils/feature_flag.dart';
|
||||
import 'package:cake_wallet/view_model/link_view_model.dart';
|
||||
import 'package:cake_wallet/utils/responsive_layout_util.dart';
|
||||
import 'package:cake_wallet/zcash/zcash.dart';
|
||||
import 'package:cw_core/address_info.dart';
|
||||
import 'package:cw_core/cake_hive.dart';
|
||||
import 'package:cw_core/erc20_token.dart';
|
||||
import 'package:cw_core/hive_type_ids.dart';
|
||||
import 'package:cw_core/key.dart';
|
||||
import 'package:cw_core/mweb_utxo.dart';
|
||||
import 'package:cw_core/node.dart';
|
||||
import 'package:cw_core/payjoin_session.dart';
|
||||
@@ -119,6 +121,12 @@ Future<void> runAppWithZone({Key? topLevelKey}) async {
|
||||
if (FeatureFlag.hasDevOptions) {
|
||||
ProxyWrapper.logger = MemoryProxyLogger();
|
||||
}
|
||||
var zcashPassword = await secureStorageShared.read(key: "com.cakewallet.cw_zcash/zec.db");
|
||||
if (zcashPassword == null || zcashPassword.isEmpty) {
|
||||
zcashPassword = generateKey().substring(0,32);
|
||||
secureStorageShared.write(key: "com.cakewallet.cw_zcash/zec.db", value: zcashPassword);
|
||||
}
|
||||
zcash?.unlockDatabase(zcashPassword);
|
||||
|
||||
// Basically when we're running a test
|
||||
if (topLevelKey != null) {
|
||||
@@ -266,7 +274,7 @@ Future<void> initializeAppConfigs({bool loadWallet = true}) async {
|
||||
payjoinSessionSource: payjoinSessionSource,
|
||||
anonpayInvoiceInfo: anonpayInvoiceInfo,
|
||||
havenSeedStore: havenSeedStore,
|
||||
initialMigrationVersion: 54,
|
||||
initialMigrationVersion: 55,
|
||||
);
|
||||
}
|
||||
|
||||
|
||||
@@ -1,5 +1,7 @@
|
||||
import 'package:cake_wallet/bitcoin/bitcoin.dart';
|
||||
import 'package:cake_wallet/store/settings_store.dart';
|
||||
import 'package:cake_wallet/di.dart';
|
||||
import 'package:cake_wallet/view_model/wallet_list/wallet_list_view_model.dart';
|
||||
import 'package:cw_core/utils/print_verbose.dart';
|
||||
import 'package:cw_core/wallet_type.dart';
|
||||
import 'package:mobx/mobx.dart';
|
||||
|
||||
@@ -15,6 +15,7 @@ bool isBIP39Wallet(WalletType walletType) {
|
||||
case WalletType.banano:
|
||||
case WalletType.monero:
|
||||
case WalletType.dogecoin:
|
||||
case WalletType.zcash:
|
||||
return true;
|
||||
case WalletType.wownero:
|
||||
case WalletType.haven:
|
||||
|
||||
@@ -17,6 +17,7 @@ import 'package:cake_wallet/wallet_type_utils.dart';
|
||||
import 'package:cw_core/wallet_type.dart';
|
||||
import 'package:flutter/material.dart';
|
||||
import 'package:flutter_mobx/flutter_mobx.dart';
|
||||
import 'package:flutter_svg/svg.dart';
|
||||
|
||||
class DesktopWalletSelectionDropDown extends StatefulWidget {
|
||||
final WalletListViewModel walletListViewModel;
|
||||
@@ -48,6 +49,7 @@ class _DesktopWalletSelectionDropDownState extends State<DesktopWalletSelectionD
|
||||
final zanoIcon = Image.asset('assets/images/crypto/zano.webp', height: 24, width: 24);
|
||||
final decredIcon = Image.asset('assets/images/crypto/decred.webp', height: 24, width: 24);
|
||||
final dogeIcon = Image.asset('assets/images/crypto/dogecoin.webp', height: 24, width: 24);
|
||||
final zcashIcon = Image.asset('assets/images/crypto/zcash.webp', height: 24, width: 24);
|
||||
final nonWalletTypeIcon = Image.asset('assets/images/close.png', height: 24, width: 24);
|
||||
|
||||
Image _newWalletImage(BuildContext context) => Image.asset(
|
||||
@@ -153,7 +155,7 @@ class _DesktopWalletSelectionDropDownState extends State<DesktopWalletSelectionD
|
||||
});
|
||||
}
|
||||
|
||||
Image _imageFor({required WalletType type, bool? isTestnet}) {
|
||||
Widget _imageFor({required WalletType type, bool? isTestnet}) {
|
||||
switch (type) {
|
||||
case WalletType.bitcoin:
|
||||
if (isTestnet == true) return tBitcoinIcon;
|
||||
@@ -190,6 +192,8 @@ class _DesktopWalletSelectionDropDownState extends State<DesktopWalletSelectionD
|
||||
return baseIcon;
|
||||
case WalletType.arbitrum:
|
||||
return arbitrumIcon;
|
||||
case WalletType.zcash:
|
||||
return zcashIcon;
|
||||
case WalletType.none:
|
||||
return nonWalletTypeIcon;
|
||||
}
|
||||
|
||||
@@ -3,7 +3,7 @@ import 'package:flutter/material.dart';
|
||||
class DropDownItemWidget extends StatelessWidget {
|
||||
const DropDownItemWidget({super.key, required this.title, required this.image});
|
||||
final double tileHeight = 60;
|
||||
final Image image;
|
||||
final Widget image;
|
||||
final String title;
|
||||
|
||||
@override
|
||||
|
||||
@@ -6,6 +6,7 @@ import 'package:cake_wallet/anonpay/anonpay_donation_link_info.dart';
|
||||
import 'package:cake_wallet/entities/preferences_key.dart';
|
||||
import 'package:cake_wallet/src/screens/receive/anonpay_receive_page.dart';
|
||||
import 'package:cake_wallet/src/widgets/cake_image_widget.dart';
|
||||
import 'package:cake_wallet/zcash/zcash.dart';
|
||||
import 'package:cw_core/receive_page_option.dart';
|
||||
import 'package:cake_wallet/src/screens/dashboard/widgets/present_receive_option_picker.dart';
|
||||
import 'package:cake_wallet/src/widgets/gradient_background.dart';
|
||||
@@ -14,6 +15,7 @@ import 'package:cake_wallet/utils/responsive_layout_util.dart';
|
||||
import 'package:cake_wallet/utils/share_util.dart';
|
||||
import 'package:cake_wallet/view_model/dashboard/receive_option_view_model.dart';
|
||||
import 'package:cake_wallet/view_model/dashboard/dashboard_view_model.dart';
|
||||
import 'package:cw_core/utils/print_verbose.dart';
|
||||
import 'package:cw_core/wallet_type.dart';
|
||||
import 'package:flutter/material.dart';
|
||||
import 'package:cake_wallet/view_model/wallet_address_list/wallet_address_list_view_model.dart';
|
||||
@@ -269,6 +271,10 @@ class AddressPage extends BasePage {
|
||||
addressListViewModel.setAddressType(bitcoin!.getOptionToType(option));
|
||||
return;
|
||||
}
|
||||
if (dashboardViewModel.type == WalletType.zcash) {
|
||||
addressListViewModel.setAddressType(zcash!.getOptionToType(option));
|
||||
return;
|
||||
}
|
||||
|
||||
switch (option) {
|
||||
case ReceivePageOption.anonPayInvoice:
|
||||
@@ -313,6 +319,10 @@ class AddressPage extends BasePage {
|
||||
addressListViewModel.type == WalletType.litecoin) {
|
||||
addressListViewModel.setAddressType(bitcoin!.getBitcoinAddressType(option));
|
||||
}
|
||||
if (addressListViewModel.type == WalletType.zcash) {
|
||||
printV("help me i'll kms if that wont work: ${zcash!.getZcashAddressType(option)}");
|
||||
addressListViewModel.setAddressType(zcash!.getZcashAddressType(option));
|
||||
}
|
||||
}
|
||||
});
|
||||
|
||||
|
||||
@@ -104,12 +104,12 @@ class TransactionsPage extends StatelessWidget {
|
||||
tags.add("MWEB");
|
||||
}
|
||||
}
|
||||
|
||||
return Observer(
|
||||
builder: (_) => TransactionRow(
|
||||
key: item.key,
|
||||
onTap: () => Navigator.of(context)
|
||||
.pushNamed(Routes.transactionDetails, arguments: transaction),
|
||||
isShield: transaction.additionalInfo['autoShield'] == true,
|
||||
direction: transaction.direction,
|
||||
formattedDate: DateFormat('HH:mm').format(transaction.date),
|
||||
formattedAmount: item.formattedCryptoAmount,
|
||||
|
||||
@@ -5,6 +5,7 @@ import 'package:flutter/material.dart';
|
||||
import 'package:cake_wallet/view_model/dashboard/dashboard_view_model.dart';
|
||||
import 'package:cw_core/wallet_type.dart';
|
||||
import 'package:flutter_mobx/flutter_mobx.dart';
|
||||
import 'package:flutter_svg/svg.dart';
|
||||
|
||||
class MenuWidget extends StatefulWidget {
|
||||
MenuWidget(this.dashboardViewModel, Key? key);
|
||||
@@ -40,7 +41,8 @@ class MenuWidgetState extends State<MenuWidget> {
|
||||
this.wowneroIcon = Image.asset('assets/images/crypto/wownero.webp'),
|
||||
this.zanoIcon = Image.asset('assets/images/crypto/zano.webp'),
|
||||
this.decredIcon = Image.asset('assets/images/crypto/decred.webp'),
|
||||
this.dogecoinIcon = Image.asset('assets/images/crypto/dogecoin.webp');
|
||||
this.dogecoinIcon = Image.asset('assets/images/crypto/dogecoin.webp'),
|
||||
this.zcashIcon = Image.asset('assets/images/crypto/zcash.webp');
|
||||
|
||||
final largeScreen = 731;
|
||||
|
||||
@@ -70,6 +72,7 @@ class MenuWidgetState extends State<MenuWidget> {
|
||||
Image zanoIcon;
|
||||
Image decredIcon;
|
||||
Image dogecoinIcon;
|
||||
Image zcashIcon;
|
||||
|
||||
@override
|
||||
void initState() {
|
||||
@@ -229,7 +232,7 @@ class MenuWidgetState extends State<MenuWidget> {
|
||||
);
|
||||
}
|
||||
|
||||
Image _iconFor({required WalletType type}) {
|
||||
Widget _iconFor({required WalletType type}) {
|
||||
switch (type) {
|
||||
case WalletType.monero:
|
||||
return moneroIcon;
|
||||
@@ -265,6 +268,8 @@ class MenuWidgetState extends State<MenuWidget> {
|
||||
return decredIcon;
|
||||
case WalletType.dogecoin:
|
||||
return dogecoinIcon;
|
||||
case WalletType.zcash:
|
||||
return zcashIcon;
|
||||
default:
|
||||
throw Exception('No icon for ${type.toString()}');
|
||||
}
|
||||
|
||||
@@ -1,5 +1,6 @@
|
||||
import 'package:flutter/material.dart';
|
||||
import 'package:cw_core/transaction_direction.dart';
|
||||
import 'package:flutter_svg/svg.dart';
|
||||
|
||||
class TransactionRow extends StatelessWidget {
|
||||
TransactionRow({
|
||||
@@ -10,6 +11,7 @@ class TransactionRow extends StatelessWidget {
|
||||
required this.tags,
|
||||
required this.title,
|
||||
required this.onTap,
|
||||
this.isShield = false,
|
||||
super.key,
|
||||
});
|
||||
|
||||
@@ -20,6 +22,7 @@ class TransactionRow extends StatelessWidget {
|
||||
final String formattedFiatAmount;
|
||||
final String title;
|
||||
final List<String> tags;
|
||||
final bool isShield;
|
||||
|
||||
@override
|
||||
Widget build(BuildContext context) {
|
||||
@@ -39,7 +42,11 @@ class TransactionRow extends StatelessWidget {
|
||||
shape: BoxShape.circle,
|
||||
color: Theme.of(context).colorScheme.surfaceContainerHighest,
|
||||
),
|
||||
child: Image.asset(direction == TransactionDirection.incoming
|
||||
child: (isShield) ? Padding(
|
||||
padding: const EdgeInsets.all(8.0),
|
||||
child: SvgPicture.asset('assets/images/tx_shield.svg'),
|
||||
) :
|
||||
Image.asset(direction == TransactionDirection.incoming
|
||||
? 'assets/images/down_arrow.png'
|
||||
: 'assets/images/up_arrow.png'),
|
||||
),
|
||||
|
||||
@@ -286,7 +286,7 @@ class WalletRestoreFromSeedFormState extends State<WalletRestoreFromSeedForm> {
|
||||
'wallet_restore_from_seed_blockheight_textfield_key',
|
||||
),
|
||||
onHeightOrDateEntered: widget.onHeightOrDateEntered,
|
||||
hasDatePicker: [WalletType.monero, WalletType.wownero].contains(
|
||||
hasDatePicker: [WalletType.monero, WalletType.wownero, WalletType.zcash].contains(
|
||||
widget.type,
|
||||
),
|
||||
walletType: widget.type,
|
||||
|
||||
@@ -146,7 +146,7 @@ class WalletRestorePage extends BasePage {
|
||||
bottom: MediaQuery.of(bottomSheetContext).viewInsets.bottom,
|
||||
),
|
||||
child: AddPassphraseBottomSheet(
|
||||
titleText: S.of(context).add_passphrase,
|
||||
titleText: S.of(bottomSheetContext).add_passphrase,
|
||||
onRestoreButtonPressed: (passphrase) async {
|
||||
await _onPassphraseBottomSheetRestoreButtonPressed(
|
||||
passphrase,
|
||||
|
||||
@@ -10,11 +10,16 @@ import 'package:cake_wallet/src/screens/settings/widgets/settings_picker_cell.da
|
||||
import 'package:cake_wallet/src/screens/settings/widgets/settings_version_cell.dart';
|
||||
import 'package:cake_wallet/utils/feature_flag.dart';
|
||||
import 'package:cake_wallet/view_model/settings/other_settings_view_model.dart';
|
||||
import 'package:cw_core/node.dart';
|
||||
import 'package:cw_core/pathForWallet.dart';
|
||||
import 'package:cw_core/wallet_info.dart';
|
||||
import 'package:cw_core/wallet_type.dart';
|
||||
import 'package:cw_core/db/sqlite.dart';
|
||||
import 'package:flutter/material.dart';
|
||||
import 'package:flutter_mobx/flutter_mobx.dart';
|
||||
import 'package:get_it/get_it.dart';
|
||||
import 'package:hive/hive.dart';
|
||||
import 'package:path/path.dart' as p;
|
||||
|
||||
class OtherSettingsPage extends BasePage {
|
||||
OtherSettingsPage(this._otherSettingsViewModel) {
|
||||
|
||||
@@ -2,6 +2,7 @@ import 'package:cake_wallet/bitcoin/bitcoin.dart';
|
||||
import 'package:cake_wallet/src/widgets/standard_switch.dart';
|
||||
import 'package:cake_wallet/utils/date_picker.dart';
|
||||
import 'package:cake_wallet/wownero/wownero.dart';
|
||||
import 'package:cake_wallet/zcash/zcash.dart';
|
||||
import 'package:cw_core/wallet_type.dart';
|
||||
import 'package:flutter/material.dart';
|
||||
import 'package:intl/intl.dart';
|
||||
@@ -189,10 +190,12 @@ class BlockchainHeightState extends State<BlockchainHeightWidget> {
|
||||
height = decred!.heightByDate(date);
|
||||
} else if (widget.walletType == WalletType.monero) {
|
||||
height = monero!.getHeightByDate(date: date);
|
||||
} else {
|
||||
assert(widget.walletType == WalletType.wownero,
|
||||
"unknown currency in BlockchainHeightWidget");
|
||||
} else if (widget.walletType == WalletType.wownero){
|
||||
height = wownero!.getHeightByDate(date: date);
|
||||
} else if (widget.walletType == WalletType.zcash) {
|
||||
height = await zcash!.getHeightByDate(date);
|
||||
} else {
|
||||
throw Exception("unknown currency in BlockchainHeightWidget");
|
||||
}
|
||||
}
|
||||
if (mounted) {
|
||||
|
||||
@@ -964,6 +964,10 @@ abstract class SettingsStoreBase with Store {
|
||||
if (node == null) {
|
||||
throw Exception('No node found for wallet type: ${walletType.toString()}');
|
||||
}
|
||||
if (node.type != walletType) {
|
||||
throw Exception("Node is not valid for $walletType (found: ${node.type}");
|
||||
}
|
||||
|
||||
return node;
|
||||
}
|
||||
|
||||
@@ -1202,6 +1206,7 @@ abstract class SettingsStoreBase with Store {
|
||||
final tronNodeId = sharedPreferences.getInt(PreferencesKey.currentTronNodeIdKey);
|
||||
final wowneroNodeId = sharedPreferences.getInt(PreferencesKey.currentWowneroNodeIdKey);
|
||||
final zanoNodeId = sharedPreferences.getInt(PreferencesKey.currentZanoNodeIdKey);
|
||||
final zcashNodeId = sharedPreferences.getInt(PreferencesKey.currentZcashNodeIdKey);
|
||||
final decredNodeId = sharedPreferences.getInt(PreferencesKey.currentDecredNodeIdKey);
|
||||
final dogecoinNodeId = sharedPreferences.getInt(PreferencesKey.currentDogecoinNodeIdKey);
|
||||
|
||||
@@ -1236,6 +1241,8 @@ abstract class SettingsStoreBase with Store {
|
||||
nodeSource.values.firstWhereOrNull((e) => e.uriRaw == wowneroDefaultNodeUri);
|
||||
final zanoNode = nodeSource.get(zanoNodeId) ??
|
||||
nodeSource.values.firstWhereOrNull((e) => e.uriRaw == zanoDefaultNodeUri);
|
||||
final zcashNode = nodeSource.get(zcashNodeId) ??
|
||||
nodeSource.values.firstWhereOrNull((e) => e.uriRaw == zcashDefaultNodeUri);
|
||||
final dogecoinNode = nodeSource.get(dogecoinNodeId) ??
|
||||
nodeSource.values.firstWhereOrNull((e) => e.uriRaw == dogecoinDefaultNodeUri);
|
||||
|
||||
@@ -1330,6 +1337,10 @@ abstract class SettingsStoreBase with Store {
|
||||
nodes[WalletType.zano] = zanoNode;
|
||||
}
|
||||
|
||||
if (zcashNode != null) {
|
||||
nodes[WalletType.zcash] = zcashNode;
|
||||
}
|
||||
|
||||
if (decredNode != null) {
|
||||
nodes[WalletType.decred] = decredNode;
|
||||
}
|
||||
@@ -1738,6 +1749,7 @@ abstract class SettingsStoreBase with Store {
|
||||
final tronNodeId = sharedPreferences.getInt(PreferencesKey.currentTronNodeIdKey);
|
||||
final wowneroNodeId = sharedPreferences.getInt(PreferencesKey.currentWowneroNodeIdKey);
|
||||
final zanoNodeId = sharedPreferences.getInt(PreferencesKey.currentZanoNodeIdKey);
|
||||
final zcashNodeId = sharedPreferences.getInt(PreferencesKey.currentZcashNodeIdKey);
|
||||
final decredNodeId = sharedPreferences.getInt(PreferencesKey.currentDecredNodeIdKey);
|
||||
final dogecoinNodeId = sharedPreferences.getInt(PreferencesKey.currentDogecoinNodeIdKey);
|
||||
final moneroNode = nodeSource.get(nodeId);
|
||||
@@ -1754,6 +1766,7 @@ abstract class SettingsStoreBase with Store {
|
||||
final tronNode = nodeSource.get(tronNodeId);
|
||||
final wowneroNode = nodeSource.get(wowneroNodeId);
|
||||
final zanoNode = nodeSource.get(zanoNodeId);
|
||||
final zcashNode = nodeSource.get(zcashNodeId);
|
||||
final decredNode = nodeSource.get(decredNodeId);
|
||||
final dogecoinNode = nodeSource.get(dogecoinNodeId);
|
||||
|
||||
@@ -1813,6 +1826,10 @@ abstract class SettingsStoreBase with Store {
|
||||
nodes[WalletType.zano] = zanoNode;
|
||||
}
|
||||
|
||||
if (zcashNode != null) {
|
||||
nodes[WalletType.zcash] = zcashNode;
|
||||
}
|
||||
|
||||
if (decredNode != null) {
|
||||
nodes[WalletType.decred] = decredNode;
|
||||
}
|
||||
@@ -1969,8 +1986,13 @@ abstract class SettingsStoreBase with Store {
|
||||
case WalletType.dogecoin:
|
||||
await _sharedPreferences.setInt(PreferencesKey.currentDogecoinNodeIdKey, node.key as int);
|
||||
break;
|
||||
default:
|
||||
case WalletType.zcash:
|
||||
await _sharedPreferences.setInt(PreferencesKey.currentZcashNodeIdKey, node.key as int);
|
||||
break;
|
||||
case WalletType.none:
|
||||
throw UnimplementedError();
|
||||
case WalletType.banano:
|
||||
throw UnimplementedError();
|
||||
}
|
||||
|
||||
nodes[walletType] = node;
|
||||
|
||||
@@ -22,7 +22,7 @@ import 'package:shared_preferences/shared_preferences.dart';
|
||||
class ExceptionHandler {
|
||||
static bool _hasError = false;
|
||||
static const _coolDownDurationInDays =
|
||||
bool.fromEnvironment('hasDevOptions', defaultValue: kDebugMode) ? 0 : 7;
|
||||
bool.fromEnvironment('hasDevOptions', defaultValue: kDebugMode || kProfileMode) ? 0 : 7;
|
||||
static File? _file;
|
||||
|
||||
static Future<void> _saveException(String? error, StackTrace? stackTrace,
|
||||
@@ -118,7 +118,7 @@ class ExceptionHandler {
|
||||
|
||||
if (kDebugMode || kProfileMode) {
|
||||
FlutterError.presentError(errorDetails);
|
||||
printV(errorDetails.toString());
|
||||
errorDetails.toString().split("\n").forEach(printV);
|
||||
return;
|
||||
}
|
||||
|
||||
@@ -198,6 +198,7 @@ class ExceptionHandler {
|
||||
'Exception: 6e00',
|
||||
'Exception: 6985',
|
||||
'Exception: 5515',
|
||||
'transport error'
|
||||
];
|
||||
|
||||
static bool isLedgerError(Object exception) =>
|
||||
|
||||
@@ -9,8 +9,8 @@ class FeatureFlag {
|
||||
static const bool isExolixEnabled = true;
|
||||
static const bool isBackgroundSyncEnabled = true;
|
||||
static bool get isInAppTorEnabled => CakeTor.instance is! CakeTorDisabled;
|
||||
static const int verificationWordsCount = kDebugMode ? 0 : 2;
|
||||
static const bool hasDevOptions = bool.fromEnvironment('hasDevOptions', defaultValue: kDebugMode);
|
||||
static const int verificationWordsCount = kDebugMode || kProfileMode ? 0 : 2;
|
||||
static const bool hasDevOptions = bool.fromEnvironment('hasDevOptions', defaultValue: kDebugMode || kProfileMode);
|
||||
static const bool hasBitcoinViewOnly = true;
|
||||
static const bool customBackgroundEnabled = false;
|
||||
static const bool duressPinEnabled = true;
|
||||
|
||||
@@ -41,6 +41,8 @@ String getQrImage(WalletType type, {int? selectedChainId}) {
|
||||
return 'assets/images/dcr_chain_qr.svg';
|
||||
case WalletType.dogecoin:
|
||||
return 'assets/images/doge_chain_qr.svg';
|
||||
case WalletType.zcash:
|
||||
return 'assets/images/zec_icon_qr.svg';
|
||||
case WalletType.banano:
|
||||
case WalletType.haven:
|
||||
case WalletType.none:
|
||||
|
||||
@@ -57,6 +57,7 @@ abstract class AdvancedPrivacySettingsViewModelBase with Store {
|
||||
case WalletType.arbitrum:
|
||||
case WalletType.solana:
|
||||
case WalletType.tron:
|
||||
case WalletType.zcash:
|
||||
return true;
|
||||
|
||||
case WalletType.bitcoin:
|
||||
@@ -103,6 +104,7 @@ abstract class AdvancedPrivacySettingsViewModelBase with Store {
|
||||
WalletType.wownero,
|
||||
WalletType.zano,
|
||||
WalletType.dogecoin,
|
||||
WalletType.zcash,
|
||||
].contains(type);
|
||||
|
||||
@computed
|
||||
|
||||
@@ -115,6 +115,8 @@ abstract class CakePayBuyCardViewModelBase with Store {
|
||||
];
|
||||
case WalletType.monero:
|
||||
return [CakePayPaymentMethod.XMR];
|
||||
case WalletType.zcash:
|
||||
return [CakePayPaymentMethod.ZEC];
|
||||
default:
|
||||
return const [];
|
||||
}
|
||||
@@ -139,11 +141,14 @@ abstract class CakePayBuyCardViewModelBase with Store {
|
||||
|
||||
@action
|
||||
Future<void> createOrder() async {
|
||||
if (walletType != WalletType.bitcoin &&
|
||||
walletType != WalletType.monero &&
|
||||
walletType != WalletType.litecoin) {
|
||||
if (![
|
||||
WalletType.bitcoin,
|
||||
WalletType.monero,
|
||||
WalletType.litecoin,
|
||||
WalletType.zcash,
|
||||
].contains(walletType)) {
|
||||
sendViewModel.state =
|
||||
FailureState('Unsupported wallet type, please use Bitcoin, Monero, or Litecoin.');
|
||||
FailureState('Unsupported wallet type, please use Bitcoin, Monero, Litecoin or Zcash.');
|
||||
}
|
||||
try {
|
||||
order = await _cakePayService.createOrder(
|
||||
|
||||
@@ -320,6 +320,7 @@ abstract class BalanceViewModelBase with Store {
|
||||
case WalletType.wownero:
|
||||
case WalletType.zano:
|
||||
case WalletType.decred:
|
||||
case WalletType.zcash:
|
||||
return true;
|
||||
default:
|
||||
return false;
|
||||
|
||||
@@ -957,6 +957,7 @@ abstract class DashboardViewModelBase with Store {
|
||||
return true;
|
||||
case WalletType.zano:
|
||||
case WalletType.haven:
|
||||
case WalletType.zcash:
|
||||
case WalletType.none:
|
||||
return false;
|
||||
}
|
||||
@@ -1284,6 +1285,7 @@ abstract class DashboardViewModelBase with Store {
|
||||
|
||||
if (wallet.chainId == 1 && tx.evmSignatureName == 'approval')
|
||||
return ' (${tx.evmSignatureName})';
|
||||
|
||||
return '';
|
||||
}
|
||||
|
||||
|
||||
@@ -231,6 +231,7 @@ abstract class HomeSettingsViewModelBase with Store {
|
||||
case WalletType.bitcoinCash:
|
||||
case WalletType.decred:
|
||||
case WalletType.dogecoin:
|
||||
case WalletType.zcash:
|
||||
return false;
|
||||
}
|
||||
|
||||
|
||||
@@ -1,4 +1,5 @@
|
||||
import 'package:cake_wallet/bitcoin/bitcoin.dart';
|
||||
import 'package:cake_wallet/zcash/zcash.dart';
|
||||
import 'package:cw_core/receive_page_option.dart';
|
||||
import 'package:cw_core/wallet_base.dart';
|
||||
import 'package:cw_core/wallet_type.dart';
|
||||
@@ -16,7 +17,9 @@ abstract class ReceiveOptionViewModelBase with Store {
|
||||
? bitcoin!.getSelectedAddressType(_wallet)
|
||||
: (_wallet.type == WalletType.decred && _wallet.isTestnet)
|
||||
? ReceivePageOption.testnet
|
||||
: ReceivePageOption.mainnet),
|
||||
: _wallet.type == WalletType.zcash
|
||||
? zcash!.getSelectedAddressType(_wallet)
|
||||
: ReceivePageOption.mainnet),
|
||||
_options = [] {
|
||||
final walletType = _wallet.type;
|
||||
switch (walletType) {
|
||||
@@ -46,6 +49,12 @@ abstract class ReceiveOptionViewModelBase with Store {
|
||||
_options = ReceivePageOptions;
|
||||
}
|
||||
break;
|
||||
case WalletType.zcash:
|
||||
_options = [
|
||||
...zcash!.getZcashReceivePageOptions(_wallet),
|
||||
...ReceivePageOptions.where((element) => element != ReceivePageOption.mainnet)
|
||||
];
|
||||
break;
|
||||
default:
|
||||
_options = ReceivePageOptions;
|
||||
}
|
||||
|
||||
@@ -9,6 +9,7 @@ import 'package:cake_wallet/solana/solana.dart';
|
||||
import 'package:cake_wallet/tron/tron.dart';
|
||||
import 'package:cake_wallet/wownero/wownero.dart';
|
||||
import 'package:cake_wallet/zano/zano.dart';
|
||||
import 'package:cake_wallet/zcash/zcash.dart';
|
||||
import 'package:cw_core/crypto_currency.dart';
|
||||
import 'package:cw_core/transaction_direction.dart';
|
||||
import 'package:cw_core/transaction_info.dart';
|
||||
@@ -52,6 +53,9 @@ class TransactionListItem extends ActionListItem with Keyable {
|
||||
}
|
||||
|
||||
String get formattedTitle {
|
||||
if (transaction.additionalInfo['autoShield'] == true) {
|
||||
return "Autoshield";
|
||||
}
|
||||
if (transaction.direction == TransactionDirection.incoming) {
|
||||
return S.current.received;
|
||||
}
|
||||
@@ -217,6 +221,11 @@ class TransactionListItem extends ActionListItem with Keyable {
|
||||
cryptoAmount: decred!.formatterDecredAmountToDouble(amount: transaction.amount),
|
||||
price: price);
|
||||
break;
|
||||
case WalletType.zcash:
|
||||
amount = calculateFiatAmountRaw(
|
||||
cryptoAmount: zcash!.formatterZcashAmountToDouble(amount: BigInt.from(transaction.amount)),
|
||||
price: price);
|
||||
|
||||
case WalletType.none:
|
||||
case WalletType.banano:
|
||||
case WalletType.haven:
|
||||
|
||||
@@ -922,6 +922,10 @@ abstract class ExchangeViewModelBase extends WalletChangeListenerViewModel with
|
||||
depositCurrency = CryptoCurrency.dcr;
|
||||
receiveCurrency = CryptoCurrency.xmr;
|
||||
break;
|
||||
case WalletType.zcash:
|
||||
depositCurrency = CryptoCurrency.zec;
|
||||
receiveCurrency = CryptoCurrency.xmr;
|
||||
break;
|
||||
case WalletType.none:
|
||||
break;
|
||||
}
|
||||
|
||||
@@ -97,6 +97,7 @@ abstract class NodeCreateOrEditViewModelBase with Store {
|
||||
case WalletType.dogecoin:
|
||||
case WalletType.zano:
|
||||
case WalletType.decred:
|
||||
case WalletType.zcash:
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -5,6 +5,7 @@ import 'package:cake_wallet/entities/priority_for_wallet_type.dart';
|
||||
import 'package:cake_wallet/core/wallet_change_listener_view_model.dart';
|
||||
import 'package:cake_wallet/evm/evm.dart';
|
||||
import 'package:cake_wallet/monero/monero.dart';
|
||||
import 'package:cake_wallet/zcash/zcash.dart';
|
||||
import 'package:cake_wallet/store/app_store.dart';
|
||||
import 'package:cake_wallet/view_model/dashboard/balance_view_model.dart';
|
||||
import 'package:cw_core/crypto_currency.dart';
|
||||
@@ -102,6 +103,7 @@ abstract class FeesViewModelBase extends WalletChangeListenerViewModel with Stor
|
||||
case WalletType.solana:
|
||||
case WalletType.tron:
|
||||
case WalletType.arbitrum:
|
||||
case WalletType.zcash:
|
||||
return false;
|
||||
}
|
||||
}
|
||||
@@ -185,6 +187,9 @@ abstract class FeesViewModelBase extends WalletChangeListenerViewModel with Stor
|
||||
case WalletType.zano:
|
||||
_settingsStore.setPriority(wallet.type, monero!.getMoneroTransactionPriorityAutomatic());
|
||||
break;
|
||||
case WalletType.zcash:
|
||||
_settingsStore.setPriority[wallet.type] = zcash!.getZcashTransactionPriorityAutomatic();
|
||||
break;
|
||||
case WalletType.bitcoin:
|
||||
_settingsStore.setPriority(wallet.type, bitcoin!.getBitcoinTransactionPriorityMedium());
|
||||
break;
|
||||
|
||||
@@ -18,6 +18,7 @@ import 'package:cake_wallet/store/settings_store.dart';
|
||||
import 'package:cake_wallet/tron/tron.dart';
|
||||
import 'package:cake_wallet/wownero/wownero.dart';
|
||||
import 'package:cake_wallet/zano/zano.dart';
|
||||
import 'package:cake_wallet/zcash/zcash.dart';
|
||||
import 'package:cw_core/balance.dart';
|
||||
import 'package:cw_core/crypto_currency.dart';
|
||||
import 'package:cw_core/format_fixed.dart';
|
||||
@@ -125,6 +126,9 @@ abstract class OutputBase with Store {
|
||||
_amount = zano!
|
||||
.formatterParseAmount(amount: _cryptoAmount, currency: cryptoCurrencyHandler());
|
||||
break;
|
||||
case WalletType.zcash:
|
||||
_amount = zcash!.formatterZcashParseAmount(_cryptoAmount);
|
||||
break;
|
||||
case WalletType.none:
|
||||
case WalletType.haven:
|
||||
case WalletType.nano:
|
||||
@@ -204,6 +208,10 @@ abstract class OutputBase with Store {
|
||||
estimatedFee = tron!.getTronTRC20EstimatedFee(_wallet).toString();
|
||||
}
|
||||
break;
|
||||
|
||||
case WalletType.zcash:
|
||||
estimatedFee = zcash!.formatterZcashAmountToDouble(amount: BigInt.from(fee)).toString();
|
||||
break;
|
||||
|
||||
/// EVMs
|
||||
case WalletType.ethereum:
|
||||
|
||||
@@ -45,6 +45,7 @@ import 'package:cake_wallet/view_model/send/send_view_model_state.dart';
|
||||
import 'package:cake_wallet/view_model/unspent_coins/unspent_coins_list_view_model.dart';
|
||||
import 'package:cake_wallet/wownero/wownero.dart';
|
||||
import 'package:cake_wallet/zano/zano.dart';
|
||||
import 'package:cake_wallet/zcash/zcash.dart';
|
||||
import 'package:cw_core/crypto_currency.dart';
|
||||
import 'package:cw_core/erc20_token.dart';
|
||||
import 'package:cw_core/exceptions.dart';
|
||||
@@ -803,8 +804,8 @@ abstract class SendViewModelBase extends WalletChangeListenerViewModel with Stor
|
||||
wallet.type != WalletType.banano &&
|
||||
wallet.type != WalletType.solana &&
|
||||
wallet.type != WalletType.tron &&
|
||||
wallet.type != WalletType.arbitrum) {
|
||||
// Wallet type is generic for all EVM chains, so we need to check the chainId
|
||||
wallet.type != WalletType.arbitrum &&
|
||||
wallet.type != WalletType.zcash) {
|
||||
throw Exception('Priority is null for wallet type: ${wallet.type}');
|
||||
}
|
||||
|
||||
@@ -861,6 +862,12 @@ abstract class SendViewModelBase extends WalletChangeListenerViewModel with Stor
|
||||
case WalletType.decred:
|
||||
this.coinTypeToSpendFrom = UnspentCoinType.any;
|
||||
return decred!.createDecredTransactionCredentials(outputs, priority!);
|
||||
case WalletType.zcash:
|
||||
return zcash!.createZcashTransactionCredentials(
|
||||
outputs,
|
||||
currency: selectedCryptoCurrency,
|
||||
// priority: priority,
|
||||
);
|
||||
default:
|
||||
throw Exception('Unexpected wallet type: ${wallet.type}');
|
||||
}
|
||||
|
||||
@@ -1,5 +1,6 @@
|
||||
import 'package:cake_wallet/bitcoin/bitcoin.dart';
|
||||
import 'package:cake_wallet/entities/priority_for_wallet_type.dart';
|
||||
import 'package:cake_wallet/monero/monero.dart';
|
||||
import 'package:cake_wallet/store/settings_store.dart';
|
||||
import 'package:cake_wallet/utils/package_info.dart';
|
||||
import 'package:cake_wallet/view_model/send/send_view_model.dart';
|
||||
|
||||
@@ -95,6 +95,8 @@ abstract class TransactionDetailsViewModelBase with Store {
|
||||
case WalletType.dogecoin:
|
||||
_addDogecoinListItems(tx, dateFormat);
|
||||
break;
|
||||
case WalletType.zcash:
|
||||
_addZcashListItems(tx, dateFormat);
|
||||
case WalletType.none:
|
||||
case WalletType.banano:
|
||||
break;
|
||||
@@ -211,7 +213,8 @@ abstract class TransactionDetailsViewModelBase with Store {
|
||||
return 'https://${wallet.isTestnet ? "testnet" : "dcrdata"}.decred.org/tx/${txId.split(':')[0]}';
|
||||
case WalletType.dogecoin:
|
||||
return 'https://blockchair.com/dogecoin/transaction/${txId}';
|
||||
|
||||
case WalletType.zcash:
|
||||
return 'https://blockchair.com/zcash/transaction/${txId}';
|
||||
case WalletType.none:
|
||||
return '';
|
||||
}
|
||||
@@ -257,6 +260,8 @@ abstract class TransactionDetailsViewModelBase with Store {
|
||||
return S.current.view_transaction_on + 'basescan.org';
|
||||
case WalletType.arbitrum:
|
||||
return S.current.view_transaction_on + 'arbiscan.io';
|
||||
case WalletType.zcash:
|
||||
return S.current.view_transaction_on + 'blockchair.com';
|
||||
case WalletType.none:
|
||||
return '';
|
||||
}
|
||||
@@ -755,6 +760,57 @@ abstract class TransactionDetailsViewModelBase with Store {
|
||||
items.addAll(_items);
|
||||
}
|
||||
|
||||
void _addZcashListItems(TransactionInfo tx, DateFormat dateFormat) {
|
||||
final memo = tx.additionalInfo['memo'] as String?;
|
||||
|
||||
final _items = [
|
||||
StandartListItem(
|
||||
title: S.current.transaction_details_transaction_id,
|
||||
value: tx.txHash,
|
||||
key: ValueKey('standard_list_item_transaction_details_id_key'),
|
||||
),
|
||||
if (tx.to != null)
|
||||
StandartListItem(
|
||||
title: S.current.transaction_details_recipient_address,
|
||||
value: tx.to!,
|
||||
key: ValueKey('standard_list_item_transaction_details_recipient_address_key'),
|
||||
),
|
||||
StandartListItem(
|
||||
title: S.current.transaction_details_date,
|
||||
value: dateFormat.format(tx.date),
|
||||
key: ValueKey('standard_list_item_transaction_details_date_key'),
|
||||
),
|
||||
StandartListItem(
|
||||
title: S.current.confirmations,
|
||||
value: tx.confirmations.toString(),
|
||||
key: ValueKey('standard_list_item_transaction_confirmations_key'),
|
||||
),
|
||||
StandartListItem(
|
||||
title: S.current.transaction_details_height,
|
||||
value: '${tx.height ?? 0}',
|
||||
key: ValueKey('standard_list_item_transaction_details_height_key'),
|
||||
),
|
||||
StandartListItem(
|
||||
title: S.current.transaction_details_amount,
|
||||
value: tx.amountFormatted(),
|
||||
key: ValueKey('standard_list_item_transaction_details_amount_key'),
|
||||
),
|
||||
if (tx.feeFormatted() != null && tx.feeFormatted()!.isNotEmpty)
|
||||
StandartListItem(
|
||||
title: S.current.transaction_details_fee,
|
||||
value: tx.feeFormatted()!,
|
||||
key: ValueKey('standard_list_item_transaction_details_fee_key'),
|
||||
),
|
||||
if (memo != null && memo.isNotEmpty)
|
||||
StandartListItem(
|
||||
title: S.current.memo,
|
||||
value: memo,
|
||||
key: ValueKey('standard_list_item_transaction_details_memo_key'),
|
||||
),
|
||||
];
|
||||
items.addAll(_items);
|
||||
}
|
||||
|
||||
void _addDogecoinListItems(TransactionInfo tx, DateFormat dateFormat) {
|
||||
final _items = [
|
||||
StandartListItem(
|
||||
|
||||
@@ -28,6 +28,7 @@ import 'package:cake_wallet/view_model/wallet_address_list/wallet_address_hidden
|
||||
import 'package:cake_wallet/view_model/wallet_address_list/wallet_address_list_header.dart';
|
||||
import 'package:cake_wallet/view_model/wallet_address_list/wallet_address_list_item.dart';
|
||||
import 'package:cake_wallet/wownero/wownero.dart';
|
||||
import 'package:cake_wallet/zcash/zcash.dart';
|
||||
import 'package:cw_core/amount_converter.dart';
|
||||
import 'package:cw_core/currency.dart';
|
||||
import 'package:cw_core/currency_for_wallet_type.dart';
|
||||
@@ -165,6 +166,8 @@ abstract class WalletAddressListViewModelBase extends WalletChangeListenerViewMo
|
||||
return BaseURI(amount: amount, address: address.address);
|
||||
case WalletType.arbitrum:
|
||||
return ArbitrumURI(amount: amount, address: address.address);
|
||||
case WalletType.zcash:
|
||||
return ZcashURI(amount: amount, address: address.address);
|
||||
case WalletType.none:
|
||||
throw Exception('Unexpected type: ${type.toString()}');
|
||||
}
|
||||
@@ -313,6 +316,14 @@ abstract class WalletAddressListViewModelBase extends WalletChangeListenerViewMo
|
||||
});
|
||||
}
|
||||
|
||||
if (wallet.type == WalletType.zcash) {
|
||||
final addrInfos = zcash!.getAddressInfos(wallet);
|
||||
addrInfos.forEach((info) {
|
||||
addressList.add(
|
||||
new WalletAddressListItem(isPrimary: false, address: info.address, name: info.label));
|
||||
});
|
||||
}
|
||||
|
||||
for (var i = 0; i < addressList.length; i++) {
|
||||
if (!(addressList[i] is WalletAddressListItem)) continue;
|
||||
(addressList[i] as WalletAddressListItem).isHidden = wallet.walletAddresses.hiddenAddresses
|
||||
@@ -409,6 +420,7 @@ abstract class WalletAddressListViewModelBase extends WalletChangeListenerViewMo
|
||||
WalletType.litecoin,
|
||||
WalletType.decred,
|
||||
WalletType.dogecoin,
|
||||
WalletType.zcash,
|
||||
].contains(wallet.type);
|
||||
|
||||
@computed
|
||||
@@ -528,6 +540,9 @@ abstract class WalletAddressListViewModelBase extends WalletChangeListenerViewMo
|
||||
if ([WalletType.bitcoin, WalletType.litecoin].contains(wallet.type)) {
|
||||
await bitcoin!.setAddressType(wallet, option);
|
||||
}
|
||||
if (wallet.type == WalletType.zcash) {
|
||||
await zcash!.setAddressType(wallet, option);
|
||||
}
|
||||
}
|
||||
|
||||
void _init() {
|
||||
|
||||
@@ -144,6 +144,7 @@ abstract class WalletKeysViewModelBase with Store {
|
||||
case WalletType.base:
|
||||
case WalletType.arbitrum:
|
||||
case WalletType.solana:
|
||||
case WalletType.zcash:
|
||||
case WalletType.tron:
|
||||
items.addAll([
|
||||
if (_wallet.privateKey != null)
|
||||
@@ -285,6 +286,8 @@ abstract class WalletKeysViewModelBase with Store {
|
||||
return 'decred-wallet';
|
||||
case WalletType.dogecoin:
|
||||
return 'dogecoin-wallet';
|
||||
case WalletType.zcash:
|
||||
return 'zcash-wallet';
|
||||
default:
|
||||
throw Exception('Unexpected wallet type: ${_wallet.type.toString()}');
|
||||
}
|
||||
|
||||
@@ -6,6 +6,7 @@ import 'package:cake_wallet/bitcoin_cash/bitcoin_cash.dart';
|
||||
import 'package:cake_wallet/solana/solana.dart';
|
||||
import 'package:cake_wallet/tron/tron.dart';
|
||||
import 'package:cake_wallet/wownero/wownero.dart';
|
||||
import 'package:cake_wallet/zcash/zcash.dart';
|
||||
import 'package:mobx/mobx.dart';
|
||||
import 'package:cake_wallet/bitcoin/bitcoin.dart';
|
||||
import 'package:cake_wallet/core/wallet_creation_service.dart';
|
||||
@@ -138,6 +139,12 @@ abstract class WalletNewVMBase extends WalletCreationVM with Store {
|
||||
password: walletPassword,
|
||||
passphrase: passphrase,
|
||||
);
|
||||
case WalletType.zcash:
|
||||
return zcash!.createZcashNewWalletCredentials(
|
||||
name: name,
|
||||
password: walletPassword,
|
||||
passphrase: passphrase,
|
||||
);
|
||||
case WalletType.decred:
|
||||
return decred!.createDecredNewWalletCredentials(name: name);
|
||||
case WalletType.none:
|
||||
|
||||
@@ -19,6 +19,7 @@ import 'package:cake_wallet/view_model/seed_settings_view_model.dart';
|
||||
import 'package:cake_wallet/view_model/wallet_creation_vm.dart';
|
||||
import 'package:cake_wallet/wownero/wownero.dart';
|
||||
import 'package:cake_wallet/zano/zano.dart';
|
||||
import 'package:cake_wallet/zcash/zcash.dart';
|
||||
import 'package:cw_core/wallet_base.dart';
|
||||
import 'package:cw_core/wallet_credentials.dart';
|
||||
import 'package:cw_core/wallet_info.dart';
|
||||
@@ -59,10 +60,12 @@ abstract class WalletRestoreViewModelBase extends WalletCreationVM with Store {
|
||||
break;
|
||||
case WalletType.bitcoinCash:
|
||||
case WalletType.zano:
|
||||
case WalletType.none:
|
||||
case WalletType.zcash:
|
||||
case WalletType.dogecoin:
|
||||
availableModes = [WalletRestoreMode.seed];
|
||||
break;
|
||||
case WalletType.none:
|
||||
availableModes = [];
|
||||
}
|
||||
walletCreationService.changeWalletType(type: type);
|
||||
if (restoredWallet != null) {
|
||||
@@ -79,9 +82,13 @@ abstract class WalletRestoreViewModelBase extends WalletCreationVM with Store {
|
||||
late final bool hasSeedLanguageSelector =
|
||||
[WalletType.monero, WalletType.haven, WalletType.wownero].contains(type);
|
||||
|
||||
late final bool hasBlockchainHeightSelector =
|
||||
[WalletType.monero, WalletType.haven, WalletType.wownero].contains(type);
|
||||
|
||||
late final bool hasBlockchainHeightSelector = [
|
||||
WalletType.monero,
|
||||
WalletType.haven,
|
||||
WalletType.wownero,
|
||||
WalletType.zcash
|
||||
].contains(type);
|
||||
|
||||
late final bool hasRestoreFromPrivateKey = [
|
||||
WalletType.ethereum,
|
||||
WalletType.polygon,
|
||||
@@ -202,9 +209,17 @@ abstract class WalletRestoreViewModelBase extends WalletCreationVM with Store {
|
||||
);
|
||||
case WalletType.decred:
|
||||
return decred!.createDecredRestoreWalletFromSeedCredentials(
|
||||
name: name,
|
||||
mnemonic: seed,
|
||||
password: password,
|
||||
);
|
||||
case WalletType.zcash:
|
||||
return zcash!.createZcashRestoreWalletFromSeedCredentials(
|
||||
name: name,
|
||||
mnemonic: seed,
|
||||
password: password,
|
||||
passphrase: passphrase,
|
||||
height: height,
|
||||
);
|
||||
case WalletType.none:
|
||||
case WalletType.haven:
|
||||
|
||||
@@ -84,7 +84,7 @@ abstract class WalletSeedViewModelBase with Store {
|
||||
|
||||
bool shouldPerformVerification() {
|
||||
bool isCI = bool.fromEnvironment('CI_BUILD', defaultValue: false);
|
||||
bool isDebug = kDebugMode;
|
||||
bool isDebug = kDebugMode || kProfileMode;
|
||||
|
||||
if (isDebug && !isCI) {
|
||||
printV("Skipping verification in debug mode - $isDebug (and when it's not in CI - $isCI).");
|
||||
|
||||
File diff suppressed because it is too large
Load Diff
Reference in New Issue
Block a user