mirror of
https://github.com/cypherstack/stack_wallet.git
synced 2025-02-02 03:06:29 +00:00
commit
d321151e2d
114 changed files with 3441 additions and 2491 deletions
122
lib/hive/db.dart
122
lib/hive/db.dart
|
@ -40,8 +40,6 @@ class DB {
|
|||
String boxNameUsedSerialsCache({required Coin coin}) =>
|
||||
"${coin.name}_usedSerialsCache";
|
||||
|
||||
static bool _initialized = false;
|
||||
|
||||
Box<dynamic>? _boxAddressBook;
|
||||
Box<String>? _boxDebugInfo;
|
||||
Box<NodeModel>? _boxNodeModels;
|
||||
|
@ -88,69 +86,65 @@ class DB {
|
|||
|
||||
// open hive boxes
|
||||
Future<void> init() async {
|
||||
if (!_initialized) {
|
||||
if (Hive.isBoxOpen(boxNameDBInfo)) {
|
||||
_boxDBInfo = Hive.box<dynamic>(boxNameDBInfo);
|
||||
} else {
|
||||
_boxDBInfo = await Hive.openBox<dynamic>(boxNameDBInfo);
|
||||
}
|
||||
await Hive.openBox<String>(boxNameWalletsToDeleteOnStart);
|
||||
|
||||
if (Hive.isBoxOpen(boxNamePrefs)) {
|
||||
_boxPrefs = Hive.box<dynamic>(boxNamePrefs);
|
||||
} else {
|
||||
_boxPrefs = await Hive.openBox<dynamic>(boxNamePrefs);
|
||||
}
|
||||
|
||||
_boxAddressBook = await Hive.openBox<dynamic>(boxNameAddressBook);
|
||||
_boxDebugInfo = await Hive.openBox<String>(boxNameDebugInfo);
|
||||
|
||||
if (Hive.isBoxOpen(boxNameNodeModels)) {
|
||||
_boxNodeModels = Hive.box<NodeModel>(boxNameNodeModels);
|
||||
} else {
|
||||
_boxNodeModels = await Hive.openBox<NodeModel>(boxNameNodeModels);
|
||||
}
|
||||
|
||||
if (Hive.isBoxOpen(boxNamePrimaryNodes)) {
|
||||
_boxPrimaryNodes = Hive.box<NodeModel>(boxNamePrimaryNodes);
|
||||
} else {
|
||||
_boxPrimaryNodes = await Hive.openBox<NodeModel>(boxNamePrimaryNodes);
|
||||
}
|
||||
|
||||
if (Hive.isBoxOpen(boxNameAllWalletsData)) {
|
||||
_boxAllWalletsData = Hive.box<dynamic>(boxNameAllWalletsData);
|
||||
} else {
|
||||
_boxAllWalletsData = await Hive.openBox<dynamic>(boxNameAllWalletsData);
|
||||
}
|
||||
|
||||
if (Hive.isBoxOpen(boxNameDesktopData)) {
|
||||
_boxDesktopData = Hive.box<String>(boxNameDesktopData);
|
||||
} else {
|
||||
_boxDesktopData = await Hive.openBox<String>(boxNameDesktopData);
|
||||
}
|
||||
|
||||
_boxNotifications =
|
||||
await Hive.openBox<NotificationModel>(boxNameNotifications);
|
||||
_boxWatchedTransactions =
|
||||
await Hive.openBox<NotificationModel>(boxNameWatchedTransactions);
|
||||
_boxWatchedTrades =
|
||||
await Hive.openBox<NotificationModel>(boxNameWatchedTrades);
|
||||
_boxTrades = await Hive.openBox<ExchangeTransaction>(boxNameTrades);
|
||||
_boxTradesV2 = await Hive.openBox<Trade>(boxNameTradesV2);
|
||||
_boxTradeNotes = await Hive.openBox<String>(boxNameTradeNotes);
|
||||
_boxTradeLookup =
|
||||
await Hive.openBox<TradeWalletLookup>(boxNameTradeLookup);
|
||||
_walletInfoSource =
|
||||
await Hive.openBox<xmr.WalletInfo>(xmr.WalletInfo.boxName);
|
||||
_boxFavoriteWallets = await Hive.openBox<String>(boxNameFavoriteWallets);
|
||||
|
||||
await Future.wait([
|
||||
Hive.openBox<dynamic>(boxNamePriceCache),
|
||||
_loadWalletBoxes(),
|
||||
_loadSharedCoinCacheBoxes(),
|
||||
]);
|
||||
_initialized = true;
|
||||
if (Hive.isBoxOpen(boxNameDBInfo)) {
|
||||
_boxDBInfo = Hive.box<dynamic>(boxNameDBInfo);
|
||||
} else {
|
||||
_boxDBInfo = await Hive.openBox<dynamic>(boxNameDBInfo);
|
||||
}
|
||||
await Hive.openBox<String>(boxNameWalletsToDeleteOnStart);
|
||||
|
||||
if (Hive.isBoxOpen(boxNamePrefs)) {
|
||||
_boxPrefs = Hive.box<dynamic>(boxNamePrefs);
|
||||
} else {
|
||||
_boxPrefs = await Hive.openBox<dynamic>(boxNamePrefs);
|
||||
}
|
||||
|
||||
_boxAddressBook = await Hive.openBox<dynamic>(boxNameAddressBook);
|
||||
_boxDebugInfo = await Hive.openBox<String>(boxNameDebugInfo);
|
||||
|
||||
if (Hive.isBoxOpen(boxNameNodeModels)) {
|
||||
_boxNodeModels = Hive.box<NodeModel>(boxNameNodeModels);
|
||||
} else {
|
||||
_boxNodeModels = await Hive.openBox<NodeModel>(boxNameNodeModels);
|
||||
}
|
||||
|
||||
if (Hive.isBoxOpen(boxNamePrimaryNodes)) {
|
||||
_boxPrimaryNodes = Hive.box<NodeModel>(boxNamePrimaryNodes);
|
||||
} else {
|
||||
_boxPrimaryNodes = await Hive.openBox<NodeModel>(boxNamePrimaryNodes);
|
||||
}
|
||||
|
||||
if (Hive.isBoxOpen(boxNameAllWalletsData)) {
|
||||
_boxAllWalletsData = Hive.box<dynamic>(boxNameAllWalletsData);
|
||||
} else {
|
||||
_boxAllWalletsData = await Hive.openBox<dynamic>(boxNameAllWalletsData);
|
||||
}
|
||||
|
||||
if (Hive.isBoxOpen(boxNameDesktopData)) {
|
||||
_boxDesktopData = Hive.box<String>(boxNameDesktopData);
|
||||
} else {
|
||||
_boxDesktopData = await Hive.openBox<String>(boxNameDesktopData);
|
||||
}
|
||||
|
||||
_boxNotifications =
|
||||
await Hive.openBox<NotificationModel>(boxNameNotifications);
|
||||
_boxWatchedTransactions =
|
||||
await Hive.openBox<NotificationModel>(boxNameWatchedTransactions);
|
||||
_boxWatchedTrades =
|
||||
await Hive.openBox<NotificationModel>(boxNameWatchedTrades);
|
||||
_boxTrades = await Hive.openBox<ExchangeTransaction>(boxNameTrades);
|
||||
_boxTradesV2 = await Hive.openBox<Trade>(boxNameTradesV2);
|
||||
_boxTradeNotes = await Hive.openBox<String>(boxNameTradeNotes);
|
||||
_boxTradeLookup = await Hive.openBox<TradeWalletLookup>(boxNameTradeLookup);
|
||||
_walletInfoSource =
|
||||
await Hive.openBox<xmr.WalletInfo>(xmr.WalletInfo.boxName);
|
||||
_boxFavoriteWallets = await Hive.openBox<String>(boxNameFavoriteWallets);
|
||||
|
||||
await Future.wait([
|
||||
Hive.openBox<dynamic>(boxNamePriceCache),
|
||||
_loadWalletBoxes(),
|
||||
_loadSharedCoinCacheBoxes(),
|
||||
]);
|
||||
}
|
||||
|
||||
Future<void> _loadWalletBoxes() async {
|
||||
|
|
|
@ -32,7 +32,7 @@ import 'package:stackwallet/pages/loading_view.dart';
|
|||
import 'package:stackwallet/pages/pinpad_views/create_pin_view.dart';
|
||||
import 'package:stackwallet/pages/pinpad_views/lock_screen_view.dart';
|
||||
import 'package:stackwallet/pages/settings_views/global_settings_view/stack_backup_views/restore_from_encrypted_string_view.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/desktop_login_view.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/password/desktop_login_view.dart';
|
||||
import 'package:stackwallet/providers/desktop/storage_crypto_handler_provider.dart';
|
||||
import 'package:stackwallet/providers/global/auto_swb_service_provider.dart';
|
||||
import 'package:stackwallet/providers/global/base_currencies_provider.dart';
|
||||
|
|
|
@ -1,8 +1,9 @@
|
|||
import 'package:decimal/decimal.dart';
|
||||
import 'package:flutter/foundation.dart';
|
||||
import 'package:stackwallet/models/exchange/response_objects/trade.dart';
|
||||
import 'package:stackwallet/pages/exchange_view/sub_widgets/exchange_rate_sheet.dart';
|
||||
|
||||
class IncompleteExchangeModel {
|
||||
class IncompleteExchangeModel extends ChangeNotifier {
|
||||
final String sendTicker;
|
||||
final String receiveTicker;
|
||||
|
||||
|
@ -15,12 +16,49 @@ class IncompleteExchangeModel {
|
|||
|
||||
final bool reversed;
|
||||
|
||||
String? recipientAddress;
|
||||
String? refundAddress;
|
||||
String? _recipientAddress;
|
||||
|
||||
String? rateId;
|
||||
String? get recipientAddress => _recipientAddress;
|
||||
|
||||
Trade? trade;
|
||||
set recipientAddress(String? recipientAddress) {
|
||||
if (_recipientAddress != recipientAddress) {
|
||||
_recipientAddress = recipientAddress;
|
||||
notifyListeners();
|
||||
}
|
||||
}
|
||||
|
||||
String? _refundAddress;
|
||||
|
||||
String? get refundAddress => _refundAddress;
|
||||
|
||||
set refundAddress(String? refundAddress) {
|
||||
if (_refundAddress != refundAddress) {
|
||||
_refundAddress = refundAddress;
|
||||
notifyListeners();
|
||||
}
|
||||
}
|
||||
|
||||
String? _rateId;
|
||||
|
||||
String? get rateId => _rateId;
|
||||
|
||||
set rateId(String? rateId) {
|
||||
if (_rateId != rateId) {
|
||||
_rateId = rateId;
|
||||
notifyListeners();
|
||||
}
|
||||
}
|
||||
|
||||
Trade? _trade;
|
||||
|
||||
Trade? get trade => _trade;
|
||||
|
||||
set trade(Trade? trade) {
|
||||
if (_trade != trade) {
|
||||
_trade = trade;
|
||||
notifyListeners();
|
||||
}
|
||||
}
|
||||
|
||||
IncompleteExchangeModel({
|
||||
required this.sendTicker,
|
||||
|
@ -30,6 +68,6 @@ class IncompleteExchangeModel {
|
|||
required this.receiveAmount,
|
||||
required this.rateType,
|
||||
required this.reversed,
|
||||
this.rateId,
|
||||
});
|
||||
String? rateId,
|
||||
}) : _rateId = rateId;
|
||||
}
|
||||
|
|
|
@ -4,7 +4,7 @@ import 'package:stackwallet/pages/add_wallet_views/add_wallet_view/sub_widgets/a
|
|||
import 'package:stackwallet/pages/add_wallet_views/add_wallet_view/sub_widgets/mobile_coin_list.dart';
|
||||
import 'package:stackwallet/pages/add_wallet_views/add_wallet_view/sub_widgets/next_button.dart';
|
||||
import 'package:stackwallet/pages/add_wallet_views/add_wallet_view/sub_widgets/searchable_coin_list.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/home/my_stack_view/exit_to_my_stack_button.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/my_stack_view/exit_to_my_stack_button.dart';
|
||||
import 'package:stackwallet/utilities/assets.dart';
|
||||
import 'package:stackwallet/utilities/constants.dart';
|
||||
import 'package:stackwallet/utilities/enums/coin_enum.dart';
|
||||
|
|
|
@ -3,7 +3,7 @@ import 'package:stackwallet/pages/add_wallet_views/create_or_restore_wallet_view
|
|||
import 'package:stackwallet/pages/add_wallet_views/create_or_restore_wallet_view/sub_widgets/create_or_restore_wallet_subtitle.dart';
|
||||
import 'package:stackwallet/pages/add_wallet_views/create_or_restore_wallet_view/sub_widgets/create_or_restore_wallet_title.dart';
|
||||
import 'package:stackwallet/pages/add_wallet_views/create_or_restore_wallet_view/sub_widgets/create_wallet_button_group.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/home/my_stack_view/exit_to_my_stack_button.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/my_stack_view/exit_to_my_stack_button.dart';
|
||||
import 'package:stackwallet/utilities/enums/coin_enum.dart';
|
||||
import 'package:stackwallet/utilities/theme/stack_colors.dart';
|
||||
import 'package:stackwallet/utilities/util.dart';
|
||||
|
|
|
@ -5,14 +5,13 @@ import 'package:flutter_riverpod/flutter_riverpod.dart';
|
|||
import 'package:stackwallet/notifications/show_flush_bar.dart';
|
||||
import 'package:stackwallet/pages/add_wallet_views/new_wallet_recovery_phrase_warning_view/new_wallet_recovery_phrase_warning_view.dart';
|
||||
import 'package:stackwallet/pages/add_wallet_views/restore_wallet_view/restore_options_view/restore_options_view.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/home/my_stack_view/exit_to_my_stack_button.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/my_stack_view/exit_to_my_stack_button.dart';
|
||||
import 'package:stackwallet/providers/global/wallets_service_provider.dart';
|
||||
import 'package:stackwallet/providers/ui/verify_recovery_phrase/mnemonic_word_count_state_provider.dart';
|
||||
import 'package:stackwallet/utilities/assets.dart';
|
||||
import 'package:stackwallet/utilities/constants.dart';
|
||||
import 'package:stackwallet/utilities/enums/add_wallet_type_enum.dart';
|
||||
import 'package:stackwallet/utilities/enums/coin_enum.dart';
|
||||
import 'package:stackwallet/utilities/enums/flush_bar_type.dart';
|
||||
import 'package:stackwallet/utilities/name_generator.dart';
|
||||
import 'package:stackwallet/utilities/text_styles.dart';
|
||||
import 'package:stackwallet/utilities/theme/stack_colors.dart';
|
||||
|
|
|
@ -9,8 +9,8 @@ import 'package:stackwallet/notifications/show_flush_bar.dart';
|
|||
import 'package:stackwallet/pages/add_wallet_views/new_wallet_recovery_phrase_view/sub_widgets/mnemonic_table.dart';
|
||||
import 'package:stackwallet/pages/add_wallet_views/new_wallet_recovery_phrase_warning_view/new_wallet_recovery_phrase_warning_view.dart';
|
||||
import 'package:stackwallet/pages/add_wallet_views/verify_recovery_phrase_view/verify_recovery_phrase_view.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/home/desktop_home_view.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/home/my_stack_view/exit_to_my_stack_button.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/desktop_home_view.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/my_stack_view/exit_to_my_stack_button.dart';
|
||||
import 'package:stackwallet/providers/providers.dart';
|
||||
import 'package:stackwallet/services/coins/manager.dart';
|
||||
import 'package:stackwallet/utilities/assets.dart';
|
||||
|
|
|
@ -5,7 +5,7 @@ import 'package:flutter_riverpod/flutter_riverpod.dart';
|
|||
import 'package:flutter_svg/flutter_svg.dart';
|
||||
import 'package:stackwallet/pages/add_wallet_views/new_wallet_recovery_phrase_view/new_wallet_recovery_phrase_view.dart';
|
||||
import 'package:stackwallet/pages/add_wallet_views/new_wallet_recovery_phrase_warning_view/recovery_phrase_explanation_dialog.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/home/my_stack_view/exit_to_my_stack_button.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/my_stack_view/exit_to_my_stack_button.dart';
|
||||
import 'package:stackwallet/providers/global/secure_store_provider.dart';
|
||||
import 'package:stackwallet/providers/providers.dart';
|
||||
import 'package:stackwallet/services/coins/coin_service.dart';
|
||||
|
@ -97,7 +97,8 @@ class _NewWalletRecoveryPhraseWarningViewState
|
|||
onPressed: () async {
|
||||
await showDialog<void>(
|
||||
context: context,
|
||||
builder: (context) => const RecoveryPhraseExplanationDialog(),
|
||||
builder: (context) =>
|
||||
const RecoveryPhraseExplanationDialog(),
|
||||
);
|
||||
},
|
||||
),
|
||||
|
@ -179,6 +180,7 @@ class _NewWalletRecoveryPhraseWarningViewState
|
|||
.extension<StackColors>()!
|
||||
.textDark,
|
||||
fontSize: 18,
|
||||
height: 1.3,
|
||||
),
|
||||
),
|
||||
TextSpan(
|
||||
|
@ -188,6 +190,7 @@ class _NewWalletRecoveryPhraseWarningViewState
|
|||
.extension<StackColors>()!
|
||||
.accentColorBlue,
|
||||
fontSize: 18,
|
||||
height: 1.3,
|
||||
),
|
||||
),
|
||||
TextSpan(
|
||||
|
@ -197,6 +200,7 @@ class _NewWalletRecoveryPhraseWarningViewState
|
|||
.extension<StackColors>()!
|
||||
.textDark,
|
||||
fontSize: 18,
|
||||
height: 1.3,
|
||||
),
|
||||
),
|
||||
TextSpan(
|
||||
|
@ -206,6 +210,7 @@ class _NewWalletRecoveryPhraseWarningViewState
|
|||
.extension<StackColors>()!
|
||||
.accentColorBlue,
|
||||
fontSize: 18,
|
||||
height: 1.3,
|
||||
),
|
||||
),
|
||||
TextSpan(
|
||||
|
@ -215,6 +220,7 @@ class _NewWalletRecoveryPhraseWarningViewState
|
|||
.extension<StackColors>()!
|
||||
.textDark,
|
||||
fontSize: 18,
|
||||
height: 1.3,
|
||||
),
|
||||
),
|
||||
],
|
||||
|
@ -367,10 +373,12 @@ class _NewWalletRecoveryPhraseWarningViewState
|
|||
),
|
||||
Flexible(
|
||||
child: Text(
|
||||
"I understand that Stack Wallet does not keep and cannot restore your recovery phrase, and If I lose my recovery phrase, I will not be able to access my funds.",
|
||||
"I understand that Stack Wallet does not keep and cannot restore my recovery phrase, and If I lose my recovery phrase, I will not be able to access my funds.",
|
||||
style: isDesktop
|
||||
? STextStyles.desktopTextMedium(context)
|
||||
: STextStyles.baseXS(context),
|
||||
: STextStyles.baseXS(context).copyWith(
|
||||
height: 1.3,
|
||||
),
|
||||
),
|
||||
),
|
||||
],
|
||||
|
|
|
@ -10,7 +10,7 @@ import 'package:stackwallet/pages/add_wallet_views/restore_wallet_view/restore_o
|
|||
import 'package:stackwallet/pages/add_wallet_views/restore_wallet_view/restore_options_view/sub_widgets/restore_options_platform_layout.dart';
|
||||
import 'package:stackwallet/pages/add_wallet_views/restore_wallet_view/restore_wallet_view.dart';
|
||||
import 'package:stackwallet/pages/add_wallet_views/restore_wallet_view/sub_widgets/mnemonic_word_count_select_sheet.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/home/my_stack_view/exit_to_my_stack_button.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/my_stack_view/exit_to_my_stack_button.dart';
|
||||
import 'package:stackwallet/providers/ui/color_theme_provider.dart';
|
||||
import 'package:stackwallet/providers/ui/verify_recovery_phrase/mnemonic_word_count_state_provider.dart';
|
||||
import 'package:stackwallet/utilities/assets.dart';
|
||||
|
|
|
@ -17,8 +17,8 @@ import 'package:stackwallet/pages/add_wallet_views/restore_wallet_view/sub_widge
|
|||
import 'package:stackwallet/pages/add_wallet_views/restore_wallet_view/sub_widgets/restore_succeeded_dialog.dart';
|
||||
import 'package:stackwallet/pages/add_wallet_views/restore_wallet_view/sub_widgets/restoring_dialog.dart';
|
||||
import 'package:stackwallet/pages/home_view/home_view.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/home/desktop_home_view.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/home/my_stack_view/exit_to_my_stack_button.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/desktop_home_view.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/my_stack_view/exit_to_my_stack_button.dart';
|
||||
import 'package:stackwallet/providers/global/secure_store_provider.dart';
|
||||
import 'package:stackwallet/providers/providers.dart';
|
||||
import 'package:stackwallet/services/coins/coin_service.dart';
|
||||
|
@ -32,7 +32,6 @@ import 'package:stackwallet/utilities/constants.dart';
|
|||
import 'package:stackwallet/utilities/custom_text_selection_controls.dart';
|
||||
import 'package:stackwallet/utilities/default_nodes.dart';
|
||||
import 'package:stackwallet/utilities/enums/coin_enum.dart';
|
||||
import 'package:stackwallet/utilities/enums/flush_bar_type.dart';
|
||||
import 'package:stackwallet/utilities/enums/form_input_status_enum.dart';
|
||||
import 'package:stackwallet/utilities/logger.dart';
|
||||
import 'package:stackwallet/utilities/text_styles.dart';
|
||||
|
|
|
@ -7,13 +7,12 @@ import 'package:stackwallet/notifications/show_flush_bar.dart';
|
|||
import 'package:stackwallet/pages/add_wallet_views/new_wallet_recovery_phrase_view/new_wallet_recovery_phrase_view.dart';
|
||||
import 'package:stackwallet/pages/add_wallet_views/verify_recovery_phrase_view/sub_widgets/word_table.dart';
|
||||
import 'package:stackwallet/pages/home_view/home_view.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/home/desktop_home_view.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/home/my_stack_view/exit_to_my_stack_button.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/desktop_home_view.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/my_stack_view/exit_to_my_stack_button.dart';
|
||||
import 'package:stackwallet/providers/providers.dart';
|
||||
import 'package:stackwallet/services/coins/manager.dart';
|
||||
import 'package:stackwallet/utilities/assets.dart';
|
||||
import 'package:stackwallet/utilities/constants.dart';
|
||||
import 'package:stackwallet/utilities/enums/flush_bar_type.dart';
|
||||
import 'package:stackwallet/utilities/text_styles.dart';
|
||||
import 'package:stackwallet/utilities/theme/stack_colors.dart';
|
||||
import 'package:stackwallet/utilities/util.dart';
|
||||
|
|
|
@ -7,8 +7,7 @@ import 'package:stackwallet/models/trade_wallet_lookup.dart';
|
|||
import 'package:stackwallet/pages/pinpad_views/lock_screen_view.dart';
|
||||
import 'package:stackwallet/pages/send_view/sub_widgets/sending_transaction_dialog.dart';
|
||||
import 'package:stackwallet/pages/wallet_view/wallet_view.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/home/my_stack_view/wallet_view/sub_widgets/desktop_auth_send.dart';
|
||||
import 'package:stackwallet/providers/exchange/trade_sent_from_stack_lookup_provider.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/my_stack_view/wallet_view/sub_widgets/desktop_auth_send.dart';
|
||||
import 'package:stackwallet/providers/providers.dart';
|
||||
import 'package:stackwallet/route_generator.dart';
|
||||
import 'package:stackwallet/services/coins/firo/firo_wallet.dart';
|
||||
|
|
|
@ -18,8 +18,6 @@ import 'package:stackwallet/pages/exchange_view/sub_widgets/exchange_provider_op
|
|||
import 'package:stackwallet/pages/exchange_view/sub_widgets/exchange_rate_sheet.dart';
|
||||
import 'package:stackwallet/pages/exchange_view/sub_widgets/rate_type_toggle.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/desktop_exchange/exchange_steps/step_scaffold.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/desktop_exchange/exchange_steps/subwidgets/desktop_step_1.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/desktop_exchange/exchange_steps/subwidgets/desktop_step_2.dart';
|
||||
import 'package:stackwallet/providers/providers.dart';
|
||||
import 'package:stackwallet/services/exchange/change_now/change_now_exchange.dart';
|
||||
import 'package:stackwallet/services/exchange/simpleswap/simpleswap_exchange.dart';
|
||||
|
@ -1022,19 +1020,16 @@ class _ExchangeFormState extends ConsumerState<ExchangeForm> {
|
|||
ref.read(exchangeSendFromWalletIdStateProvider.state).state =
|
||||
Tuple2(walletId!, coin!);
|
||||
if (isDesktop) {
|
||||
ref.read(ssss.state).state = model;
|
||||
await showDialog<void>(
|
||||
context: context,
|
||||
barrierDismissible: false,
|
||||
builder: (context) {
|
||||
return DesktopDialog(
|
||||
return const DesktopDialog(
|
||||
maxWidth: 720,
|
||||
maxHeight: double.infinity,
|
||||
child: StepScaffold(
|
||||
step: 2,
|
||||
model: model,
|
||||
body: DesktopStep2(
|
||||
model: model,
|
||||
),
|
||||
initialStep: 2,
|
||||
),
|
||||
);
|
||||
},
|
||||
|
@ -1051,19 +1046,16 @@ class _ExchangeFormState extends ConsumerState<ExchangeForm> {
|
|||
ref.read(exchangeSendFromWalletIdStateProvider.state).state = null;
|
||||
|
||||
if (isDesktop) {
|
||||
ref.read(ssss.state).state = model;
|
||||
await showDialog<void>(
|
||||
context: context,
|
||||
barrierDismissible: false,
|
||||
builder: (context) {
|
||||
return DesktopDialog(
|
||||
return const DesktopDialog(
|
||||
maxWidth: 720,
|
||||
maxHeight: double.infinity,
|
||||
child: StepScaffold(
|
||||
step: 1,
|
||||
model: model,
|
||||
body: DesktopStep1(
|
||||
model: model,
|
||||
),
|
||||
initialStep: 1,
|
||||
),
|
||||
);
|
||||
},
|
||||
|
|
|
@ -2,12 +2,14 @@ import 'package:flutter/gestures.dart';
|
|||
import 'package:flutter/material.dart';
|
||||
import 'package:flutter_svg/svg.dart';
|
||||
import 'package:stackwallet/pages/stack_privacy_calls.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/password/create_password_view.dart';
|
||||
import 'package:stackwallet/utilities/assets.dart';
|
||||
import 'package:stackwallet/utilities/prefs.dart';
|
||||
import 'package:stackwallet/utilities/text_styles.dart';
|
||||
import 'package:stackwallet/utilities/theme/stack_colors.dart';
|
||||
import 'package:stackwallet/utilities/util.dart';
|
||||
import 'package:stackwallet/widgets/background.dart';
|
||||
import 'package:stackwallet/widgets/desktop/secondary_button.dart';
|
||||
import 'package:url_launcher/url_launcher.dart';
|
||||
|
||||
class IntroView extends StatefulWidget {
|
||||
|
@ -135,6 +137,20 @@ class _IntroViewState extends State<IntroView> {
|
|||
GetStartedButton(
|
||||
isDesktop: isDesktop,
|
||||
),
|
||||
if (isDesktop)
|
||||
const SizedBox(
|
||||
height: 20,
|
||||
),
|
||||
if (isDesktop)
|
||||
SecondaryButton(
|
||||
label: "Restore from Stack backup",
|
||||
onPressed: () {
|
||||
Navigator.of(context).pushNamed(
|
||||
CreatePasswordView.routeName,
|
||||
arguments: true,
|
||||
);
|
||||
},
|
||||
),
|
||||
const Spacer(
|
||||
flex: 65,
|
||||
),
|
||||
|
@ -257,7 +273,7 @@ class GetStartedButton extends StatelessWidget {
|
|||
),
|
||||
)
|
||||
: SizedBox(
|
||||
width: 328,
|
||||
width: double.infinity,
|
||||
height: 70,
|
||||
child: TextButton(
|
||||
style: Theme.of(context)
|
||||
|
@ -270,7 +286,7 @@ class GetStartedButton extends StatelessWidget {
|
|||
);
|
||||
},
|
||||
child: Text(
|
||||
"Get started",
|
||||
"Create new Stack",
|
||||
style: STextStyles.button(context).copyWith(fontSize: 20),
|
||||
),
|
||||
),
|
||||
|
|
|
@ -62,6 +62,7 @@ class _LockscreenViewState extends ConsumerState<LockscreenView> {
|
|||
bool _attemptLock = false;
|
||||
late Duration _timeout;
|
||||
static const maxAttemptsBeforeThrottling = 3;
|
||||
Timer? _timer;
|
||||
|
||||
Future<void> _onUnlock() async {
|
||||
final now = DateTime.now().toUtc();
|
||||
|
@ -273,11 +274,11 @@ class _LockscreenViewState extends ConsumerState<LockscreenView> {
|
|||
_timeout = const Duration(minutes: 60);
|
||||
}
|
||||
|
||||
unawaited(
|
||||
Future<void>.delayed(_timeout).then((_) {
|
||||
_timer?.cancel();
|
||||
_timer = Timer(_timeout, () {
|
||||
_attemptLock = false;
|
||||
_attempts = 0;
|
||||
}));
|
||||
});
|
||||
}
|
||||
|
||||
if (_attemptLock) {
|
||||
|
|
|
@ -8,7 +8,7 @@ import 'package:stackwallet/notifications/show_flush_bar.dart';
|
|||
import 'package:stackwallet/pages/pinpad_views/lock_screen_view.dart';
|
||||
import 'package:stackwallet/pages/send_view/sub_widgets/sending_transaction_dialog.dart';
|
||||
import 'package:stackwallet/pages/wallet_view/wallet_view.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/home/my_stack_view/wallet_view/sub_widgets/desktop_auth_send.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/my_stack_view/wallet_view/sub_widgets/desktop_auth_send.dart';
|
||||
import 'package:stackwallet/providers/providers.dart';
|
||||
import 'package:stackwallet/providers/wallet/public_private_balance_state_provider.dart';
|
||||
import 'package:stackwallet/route_generator.dart';
|
||||
|
@ -17,7 +17,6 @@ import 'package:stackwallet/services/coins/firo/firo_wallet.dart';
|
|||
import 'package:stackwallet/utilities/assets.dart';
|
||||
import 'package:stackwallet/utilities/constants.dart';
|
||||
import 'package:stackwallet/utilities/enums/coin_enum.dart';
|
||||
import 'package:stackwallet/utilities/enums/flush_bar_type.dart';
|
||||
import 'package:stackwallet/utilities/format.dart';
|
||||
import 'package:stackwallet/utilities/text_styles.dart';
|
||||
import 'package:stackwallet/utilities/theme/stack_colors.dart';
|
||||
|
@ -28,9 +27,12 @@ import 'package:stackwallet/widgets/custom_buttons/app_bar_icon_button.dart';
|
|||
import 'package:stackwallet/widgets/desktop/desktop_dialog.dart';
|
||||
import 'package:stackwallet/widgets/desktop/desktop_dialog_close_button.dart';
|
||||
import 'package:stackwallet/widgets/desktop/primary_button.dart';
|
||||
import 'package:stackwallet/widgets/icon_widgets/x_icon.dart';
|
||||
import 'package:stackwallet/widgets/rounded_container.dart';
|
||||
import 'package:stackwallet/widgets/rounded_white_container.dart';
|
||||
import 'package:stackwallet/widgets/stack_dialog.dart';
|
||||
import 'package:stackwallet/widgets/stack_text_field.dart';
|
||||
import 'package:stackwallet/widgets/textfield_icon_button.dart';
|
||||
|
||||
class ConfirmTransactionView extends ConsumerStatefulWidget {
|
||||
const ConfirmTransactionView({
|
||||
|
@ -60,6 +62,9 @@ class _ConfirmTransactionViewState
|
|||
late final String routeOnSuccessName;
|
||||
late final bool isDesktop;
|
||||
|
||||
late final FocusNode _noteFocusNode;
|
||||
late final TextEditingController noteController;
|
||||
|
||||
Future<void> _attemptSend(BuildContext context) async {
|
||||
unawaited(
|
||||
showDialog<dynamic>(
|
||||
|
@ -72,7 +77,7 @@ class _ConfirmTransactionViewState
|
|||
),
|
||||
);
|
||||
|
||||
final note = transactionInfo["note"] as String? ?? "";
|
||||
final note = noteController.text;
|
||||
final manager =
|
||||
ref.read(walletsChangeNotifierProvider).getManager(walletId);
|
||||
|
||||
|
@ -194,9 +199,20 @@ class _ConfirmTransactionViewState
|
|||
transactionInfo = widget.transactionInfo;
|
||||
walletId = widget.walletId;
|
||||
routeOnSuccessName = widget.routeOnSuccessName;
|
||||
_noteFocusNode = FocusNode();
|
||||
noteController = TextEditingController();
|
||||
noteController.text = transactionInfo["note"] as String? ?? "";
|
||||
super.initState();
|
||||
}
|
||||
|
||||
@override
|
||||
void dispose() {
|
||||
noteController.dispose();
|
||||
|
||||
_noteFocusNode.dispose();
|
||||
super.dispose();
|
||||
}
|
||||
|
||||
@override
|
||||
Widget build(BuildContext context) {
|
||||
final managerProvider = ref.watch(walletsChangeNotifierProvider
|
||||
|
@ -563,50 +579,132 @@ class _ConfirmTransactionViewState
|
|||
],
|
||||
),
|
||||
),
|
||||
Container(
|
||||
height: 1,
|
||||
color: Theme.of(context)
|
||||
.extension<StackColors>()!
|
||||
.background,
|
||||
),
|
||||
Padding(
|
||||
padding: const EdgeInsets.all(12),
|
||||
child: Column(
|
||||
mainAxisSize: MainAxisSize.min,
|
||||
crossAxisAlignment: CrossAxisAlignment.start,
|
||||
children: [
|
||||
Text(
|
||||
"Note",
|
||||
style: STextStyles.desktopTextExtraExtraSmall(
|
||||
context),
|
||||
),
|
||||
const SizedBox(
|
||||
height: 2,
|
||||
),
|
||||
Text(
|
||||
transactionInfo["note"] as String,
|
||||
style: STextStyles.desktopTextExtraExtraSmall(
|
||||
context)
|
||||
.copyWith(
|
||||
color: Theme.of(context)
|
||||
.extension<StackColors>()!
|
||||
.textDark,
|
||||
),
|
||||
)
|
||||
],
|
||||
),
|
||||
),
|
||||
// Container(
|
||||
// height: 1,
|
||||
// color: Theme.of(context)
|
||||
// .extension<StackColors>()!
|
||||
// .background,
|
||||
// ),
|
||||
// Padding(
|
||||
// padding: const EdgeInsets.all(12),
|
||||
// child: Column(
|
||||
// mainAxisSize: MainAxisSize.min,
|
||||
// crossAxisAlignment: CrossAxisAlignment.start,
|
||||
// children: [
|
||||
// Text(
|
||||
// "Note",
|
||||
// style: STextStyles.desktopTextExtraExtraSmall(
|
||||
// context),
|
||||
// ),
|
||||
// const SizedBox(
|
||||
// height: 2,
|
||||
// ),
|
||||
// Text(
|
||||
// transactionInfo["note"] as String,
|
||||
// style: STextStyles.desktopTextExtraExtraSmall(
|
||||
// context)
|
||||
// .copyWith(
|
||||
// color: Theme.of(context)
|
||||
// .extension<StackColors>()!
|
||||
// .textDark,
|
||||
// ),
|
||||
// )
|
||||
// ],
|
||||
// ),
|
||||
// ),
|
||||
],
|
||||
),
|
||||
),
|
||||
),
|
||||
if (isDesktop)
|
||||
Padding(
|
||||
padding: const EdgeInsets.only(
|
||||
left: 32,
|
||||
right: 32,
|
||||
),
|
||||
child: Column(
|
||||
mainAxisSize: MainAxisSize.min,
|
||||
crossAxisAlignment: CrossAxisAlignment.start,
|
||||
children: [
|
||||
Text(
|
||||
"Note (optional)",
|
||||
style:
|
||||
STextStyles.desktopTextExtraSmall(context).copyWith(
|
||||
color: Theme.of(context)
|
||||
.extension<StackColors>()!
|
||||
.textFieldActiveSearchIconRight,
|
||||
),
|
||||
textAlign: TextAlign.left,
|
||||
),
|
||||
const SizedBox(
|
||||
height: 10,
|
||||
),
|
||||
ClipRRect(
|
||||
borderRadius: BorderRadius.circular(
|
||||
Constants.size.circularBorderRadius,
|
||||
),
|
||||
child: TextField(
|
||||
minLines: 1,
|
||||
maxLines: 5,
|
||||
autocorrect: isDesktop ? false : true,
|
||||
enableSuggestions: isDesktop ? false : true,
|
||||
controller: noteController,
|
||||
focusNode: _noteFocusNode,
|
||||
style:
|
||||
STextStyles.desktopTextExtraSmall(context).copyWith(
|
||||
color: Theme.of(context)
|
||||
.extension<StackColors>()!
|
||||
.textFieldActiveText,
|
||||
height: 1.8,
|
||||
),
|
||||
onChanged: (_) => setState(() {}),
|
||||
decoration: standardInputDecoration(
|
||||
"Type something...",
|
||||
_noteFocusNode,
|
||||
context,
|
||||
desktopMed: true,
|
||||
).copyWith(
|
||||
contentPadding: const EdgeInsets.only(
|
||||
left: 16,
|
||||
top: 11,
|
||||
bottom: 12,
|
||||
right: 5,
|
||||
),
|
||||
suffixIcon: noteController.text.isNotEmpty
|
||||
? Padding(
|
||||
padding: const EdgeInsets.only(right: 0),
|
||||
child: UnconstrainedBox(
|
||||
child: Row(
|
||||
children: [
|
||||
TextFieldIconButton(
|
||||
child: const XIcon(),
|
||||
onTap: () async {
|
||||
setState(
|
||||
() => noteController.text = "",
|
||||
);
|
||||
},
|
||||
),
|
||||
],
|
||||
),
|
||||
),
|
||||
)
|
||||
: null,
|
||||
),
|
||||
),
|
||||
),
|
||||
const SizedBox(
|
||||
height: 20,
|
||||
)
|
||||
],
|
||||
),
|
||||
),
|
||||
if (isDesktop)
|
||||
Padding(
|
||||
padding: const EdgeInsets.only(
|
||||
left: 32,
|
||||
),
|
||||
child: Text(
|
||||
"Transaction fee (estimated)",
|
||||
"Transaction fee",
|
||||
style: STextStyles.desktopTextExtraExtraSmall(context),
|
||||
),
|
||||
),
|
||||
|
|
|
@ -34,6 +34,7 @@ import 'package:stackwallet/utilities/flutter_secure_storage_interface.dart';
|
|||
import 'package:stackwallet/utilities/format.dart';
|
||||
import 'package:stackwallet/utilities/logger.dart';
|
||||
import 'package:stackwallet/utilities/prefs.dart';
|
||||
import 'package:stackwallet/utilities/util.dart';
|
||||
import 'package:tuple/tuple.dart';
|
||||
import 'package:uuid/uuid.dart';
|
||||
import 'package:wakelock/wakelock.dart';
|
||||
|
@ -764,6 +765,10 @@ abstract class SWB {
|
|||
}
|
||||
|
||||
Logging.instance.log("done with SWB restore", level: LogLevel.Warning);
|
||||
if (Util.isDesktop) {
|
||||
await Wallets.sharedInstance
|
||||
.loadAfterStackRestore(_prefs, managers.map((e) => e.item2).toList());
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
|
|
|
@ -12,7 +12,6 @@ import 'package:stackwallet/pages/settings_views/global_settings_view/stack_back
|
|||
import 'package:stackwallet/route_generator.dart';
|
||||
import 'package:stackwallet/utilities/assets.dart';
|
||||
import 'package:stackwallet/utilities/constants.dart';
|
||||
import 'package:stackwallet/utilities/enums/flush_bar_type.dart';
|
||||
import 'package:stackwallet/utilities/logger.dart';
|
||||
import 'package:stackwallet/utilities/text_styles.dart';
|
||||
import 'package:stackwallet/utilities/theme/stack_colors.dart';
|
||||
|
|
|
@ -9,6 +9,9 @@ import 'package:stackwallet/pages/settings_views/global_settings_view/stack_back
|
|||
import 'package:stackwallet/pages/settings_views/global_settings_view/stack_backup_views/stack_backup_view.dart';
|
||||
import 'package:stackwallet/pages/settings_views/global_settings_view/stack_backup_views/sub_widgets/restoring_item_card.dart';
|
||||
import 'package:stackwallet/pages/settings_views/global_settings_view/stack_backup_views/sub_widgets/restoring_wallet_card.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/desktop_home_view.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/desktop_menu.dart';
|
||||
import 'package:stackwallet/providers/desktop/current_desktop_menu_item.dart';
|
||||
import 'package:stackwallet/providers/global/secure_store_provider.dart';
|
||||
import 'package:stackwallet/providers/providers.dart';
|
||||
import 'package:stackwallet/providers/stack_restore/stack_restoring_ui_state_provider.dart';
|
||||
|
@ -20,25 +23,23 @@ import 'package:stackwallet/utilities/theme/stack_colors.dart';
|
|||
import 'package:stackwallet/utilities/util.dart';
|
||||
import 'package:stackwallet/widgets/conditional_parent.dart';
|
||||
import 'package:stackwallet/widgets/custom_buttons/app_bar_icon_button.dart';
|
||||
import 'package:stackwallet/widgets/desktop/primary_button.dart';
|
||||
import 'package:stackwallet/widgets/desktop/secondary_button.dart';
|
||||
import 'package:stackwallet/widgets/icon_widgets/addressbook_icon.dart';
|
||||
import 'package:stackwallet/widgets/loading_indicator.dart';
|
||||
import 'package:stackwallet/widgets/rounded_container.dart';
|
||||
|
||||
import '../../../../../pages_desktop_specific/home/desktop_home_view.dart';
|
||||
import '../../../../../pages_desktop_specific/home/desktop_menu.dart';
|
||||
import '../../../../../providers/desktop/current_desktop_menu_item.dart';
|
||||
import '../../../../../widgets/desktop/primary_button.dart';
|
||||
|
||||
class StackRestoreProgressView extends ConsumerStatefulWidget {
|
||||
const StackRestoreProgressView({
|
||||
Key? key,
|
||||
required this.jsonString,
|
||||
this.fromFile = false,
|
||||
this.shouldPushToHome = false,
|
||||
}) : super(key: key);
|
||||
|
||||
final String jsonString;
|
||||
final bool fromFile;
|
||||
final bool shouldPushToHome;
|
||||
|
||||
@override
|
||||
ConsumerState<StackRestoreProgressView> createState() =>
|
||||
|
@ -696,11 +697,21 @@ class _StackRestoreProgressViewState
|
|||
.state)
|
||||
.state = keyID;
|
||||
|
||||
Navigator.of(context, rootNavigator: true)
|
||||
.popUntil(
|
||||
ModalRoute.withName(
|
||||
DesktopHomeView.routeName),
|
||||
);
|
||||
if (widget.shouldPushToHome) {
|
||||
unawaited(
|
||||
Navigator.of(context)
|
||||
.pushNamedAndRemoveUntil(
|
||||
DesktopHomeView.routeName,
|
||||
(route) => false,
|
||||
),
|
||||
);
|
||||
} else {
|
||||
Navigator.of(context, rootNavigator: true)
|
||||
.popUntil(
|
||||
ModalRoute.withName(
|
||||
DesktopHomeView.routeName),
|
||||
);
|
||||
}
|
||||
},
|
||||
)
|
||||
: SecondaryButton(
|
||||
|
|
|
@ -5,7 +5,7 @@ import 'package:flutter_riverpod/flutter_riverpod.dart';
|
|||
import 'package:flutter_svg/svg.dart';
|
||||
import 'package:stackwallet/hive/db.dart';
|
||||
import 'package:stackwallet/pages/pinpad_views/create_pin_view.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/create_password/create_password_view.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/password/create_password_view.dart';
|
||||
import 'package:stackwallet/providers/global/prefs_provider.dart';
|
||||
import 'package:stackwallet/providers/global/price_provider.dart';
|
||||
import 'package:stackwallet/services/exchange/exchange_data_loading_service.dart';
|
||||
|
@ -141,7 +141,8 @@ class _StackPrivacyCalls extends ConsumerState<StackPrivacyCalls> {
|
|||
textAlign: TextAlign.left,
|
||||
text: TextSpan(
|
||||
style: isDesktop
|
||||
? STextStyles.desktopTextExtraExtraSmall(context)
|
||||
? STextStyles.desktopTextExtraExtraSmall(
|
||||
context)
|
||||
: STextStyles.label(context).copyWith(
|
||||
fontSize: 12.0,
|
||||
),
|
||||
|
@ -214,8 +215,9 @@ class _StackPrivacyCalls extends ConsumerState<StackPrivacyCalls> {
|
|||
children: [
|
||||
Expanded(
|
||||
child: PrimaryButton(
|
||||
label:
|
||||
!widget.isSettings ? "Continue" : "Save changes",
|
||||
label: !widget.isSettings
|
||||
? "Continue"
|
||||
: "Save changes",
|
||||
onPressed: () {
|
||||
ref
|
||||
.read(prefsChangeNotifierProvider)
|
||||
|
@ -228,8 +230,8 @@ class _StackPrivacyCalls extends ConsumerState<StackPrivacyCalls> {
|
|||
value: isEasy)
|
||||
.then((_) {
|
||||
if (isEasy) {
|
||||
unawaited(
|
||||
ExchangeDataLoadingService().loadAll(ref));
|
||||
unawaited(ExchangeDataLoadingService()
|
||||
.loadAll(ref));
|
||||
ref
|
||||
.read(priceAnd24hChangeNotifierProvider)
|
||||
.start(true);
|
||||
|
|
|
@ -3,7 +3,7 @@ import 'package:flutter/material.dart';
|
|||
import 'package:flutter_riverpod/flutter_riverpod.dart';
|
||||
import 'package:flutter_svg/flutter_svg.dart';
|
||||
import 'package:stackwallet/pages/wallet_view/wallet_view.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/home/my_stack_view/wallet_view/desktop_wallet_view.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/my_stack_view/wallet_view/desktop_wallet_view.dart';
|
||||
import 'package:stackwallet/providers/providers.dart';
|
||||
import 'package:stackwallet/services/coins/manager.dart';
|
||||
import 'package:stackwallet/utilities/assets.dart';
|
||||
|
|
|
@ -5,8 +5,8 @@ import 'package:stackwallet/models/contact.dart';
|
|||
import 'package:stackwallet/models/contact_address_entry.dart';
|
||||
import 'package:stackwallet/pages/address_book_views/subviews/add_address_book_entry_view.dart';
|
||||
import 'package:stackwallet/pages/address_book_views/subviews/address_book_filter_view.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/home/address_book_view/subwidgets/desktop_address_book_scaffold.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/home/address_book_view/subwidgets/desktop_contact_details.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/address_book_view/subwidgets/desktop_address_book_scaffold.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/address_book_view/subwidgets/desktop_contact_details.dart';
|
||||
import 'package:stackwallet/providers/global/address_book_service_provider.dart';
|
||||
import 'package:stackwallet/providers/providers.dart';
|
||||
import 'package:stackwallet/providers/ui/address_book_providers/address_book_filter_provider.dart';
|
|
@ -49,7 +49,7 @@ class DesktopAddressCard extends StatelessWidget {
|
|||
crossAxisAlignment: CrossAxisAlignment.start,
|
||||
children: [
|
||||
SelectableText(
|
||||
"${entry.label} (${entry.coin.ticker})",
|
||||
"${contactId == "default" ? entry.other! : entry.label} (${entry.coin.ticker})",
|
||||
style: STextStyles.desktopTextExtraExtraSmall(context).copyWith(
|
||||
color: Theme.of(context).extension<StackColors>()!.textDark,
|
||||
),
|
|
@ -4,8 +4,8 @@ import 'package:flutter_svg/flutter_svg.dart';
|
|||
import 'package:stackwallet/models/contact.dart';
|
||||
import 'package:stackwallet/models/paymint/transactions_model.dart';
|
||||
import 'package:stackwallet/pages/address_book_views/subviews/add_new_contact_address_view.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/home/address_book_view/subwidgets/desktop_address_card.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/home/address_book_view/subwidgets/desktop_contact_options_menu_popup.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/address_book_view/subwidgets/desktop_address_card.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/address_book_view/subwidgets/desktop_contact_options_menu_popup.dart';
|
||||
import 'package:stackwallet/providers/global/address_book_service_provider.dart';
|
||||
import 'package:stackwallet/providers/global/wallets_provider.dart';
|
||||
import 'package:stackwallet/providers/ui/address_book_providers/address_entry_data_provider.dart';
|
|
@ -1,51 +1,256 @@
|
|||
import 'package:flutter/material.dart';
|
||||
import 'package:stackwallet/models/exchange/incomplete_exchange.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/desktop_exchange/subwidgets/desktop_exchange_steps_indicator.dart';
|
||||
import 'package:stackwallet/utilities/text_styles.dart';
|
||||
import 'package:stackwallet/widgets/custom_buttons/app_bar_icon_button.dart';
|
||||
import 'dart:async';
|
||||
|
||||
class StepScaffold extends StatefulWidget {
|
||||
import 'package:decimal/decimal.dart';
|
||||
import 'package:flutter/material.dart';
|
||||
import 'package:flutter_riverpod/flutter_riverpod.dart';
|
||||
import 'package:qr_flutter/qr_flutter.dart';
|
||||
import 'package:stackwallet/models/exchange/incomplete_exchange.dart';
|
||||
import 'package:stackwallet/models/exchange/response_objects/trade.dart';
|
||||
import 'package:stackwallet/pages/exchange_view/send_from_view.dart';
|
||||
import 'package:stackwallet/pages/exchange_view/sub_widgets/exchange_rate_sheet.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/desktop_exchange/exchange_steps/subwidgets/desktop_step_1.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/desktop_exchange/exchange_steps/subwidgets/desktop_step_2.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/desktop_exchange/exchange_steps/subwidgets/desktop_step_3.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/desktop_exchange/exchange_steps/subwidgets/desktop_step_4.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/desktop_exchange/subwidgets/desktop_exchange_steps_indicator.dart';
|
||||
import 'package:stackwallet/providers/exchange/exchange_provider.dart';
|
||||
import 'package:stackwallet/providers/global/trades_service_provider.dart';
|
||||
import 'package:stackwallet/route_generator.dart';
|
||||
import 'package:stackwallet/services/exchange/exchange_response.dart';
|
||||
import 'package:stackwallet/services/notifications_api.dart';
|
||||
import 'package:stackwallet/utilities/assets.dart';
|
||||
import 'package:stackwallet/utilities/enums/coin_enum.dart';
|
||||
import 'package:stackwallet/utilities/text_styles.dart';
|
||||
import 'package:stackwallet/utilities/theme/stack_colors.dart';
|
||||
import 'package:stackwallet/widgets/custom_buttons/app_bar_icon_button.dart';
|
||||
import 'package:stackwallet/widgets/custom_loading_overlay.dart';
|
||||
import 'package:stackwallet/widgets/desktop/desktop_dialog.dart';
|
||||
import 'package:stackwallet/widgets/desktop/desktop_dialog_close_button.dart';
|
||||
import 'package:stackwallet/widgets/desktop/primary_button.dart';
|
||||
import 'package:stackwallet/widgets/desktop/secondary_button.dart';
|
||||
import 'package:stackwallet/widgets/desktop/simple_desktop_dialog.dart';
|
||||
import 'package:stackwallet/widgets/fade_stack.dart';
|
||||
|
||||
final ssss = StateProvider<IncompleteExchangeModel?>((_) => null);
|
||||
|
||||
final desktopExchangeModelProvider =
|
||||
ChangeNotifierProvider<IncompleteExchangeModel?>(
|
||||
(ref) => ref.watch(ssss.state).state);
|
||||
|
||||
class StepScaffold extends ConsumerStatefulWidget {
|
||||
const StepScaffold({
|
||||
Key? key,
|
||||
required this.body,
|
||||
required this.step,
|
||||
required this.model,
|
||||
required this.initialStep,
|
||||
}) : super(key: key);
|
||||
|
||||
final Widget body;
|
||||
final int step;
|
||||
final IncompleteExchangeModel model;
|
||||
final int initialStep;
|
||||
|
||||
@override
|
||||
State<StepScaffold> createState() => _StepScaffoldState();
|
||||
ConsumerState<StepScaffold> createState() => _StepScaffoldState();
|
||||
}
|
||||
|
||||
class _StepScaffoldState extends State<StepScaffold> {
|
||||
int currentStep = 0;
|
||||
late final IncompleteExchangeModel model;
|
||||
class _StepScaffoldState extends ConsumerState<StepScaffold> {
|
||||
int currentStep = 1;
|
||||
bool enableNext = false;
|
||||
|
||||
late final Duration duration;
|
||||
|
||||
void updateEnableNext(bool enableNext) {
|
||||
if (enableNext != this.enableNext) {
|
||||
setState(() => this.enableNext = enableNext);
|
||||
}
|
||||
}
|
||||
|
||||
Future<bool> createTrade() async {
|
||||
unawaited(
|
||||
showDialog<void>(
|
||||
context: context,
|
||||
barrierDismissible: false,
|
||||
builder: (_) => WillPopScope(
|
||||
onWillPop: () async => false,
|
||||
child: Container(
|
||||
color: Theme.of(context)
|
||||
.extension<StackColors>()!
|
||||
.overlay
|
||||
.withOpacity(0.6),
|
||||
child: const CustomLoadingOverlay(
|
||||
message: "Creating a trade",
|
||||
eventBus: null,
|
||||
),
|
||||
),
|
||||
),
|
||||
),
|
||||
);
|
||||
|
||||
final ExchangeResponse<Trade> response = await ref
|
||||
.read(exchangeProvider)
|
||||
.createTrade(
|
||||
from: ref.read(desktopExchangeModelProvider)!.sendTicker,
|
||||
to: ref.read(desktopExchangeModelProvider)!.receiveTicker,
|
||||
fixedRate: ref.read(desktopExchangeModelProvider)!.rateType !=
|
||||
ExchangeRateType.estimated,
|
||||
amount: ref.read(desktopExchangeModelProvider)!.reversed
|
||||
? ref.read(desktopExchangeModelProvider)!.receiveAmount
|
||||
: ref.read(desktopExchangeModelProvider)!.sendAmount,
|
||||
addressTo: ref.read(desktopExchangeModelProvider)!.recipientAddress!,
|
||||
extraId: null,
|
||||
addressRefund: ref.read(desktopExchangeModelProvider)!.refundAddress!,
|
||||
refundExtraId: "",
|
||||
rateId: ref.read(desktopExchangeModelProvider)!.rateId,
|
||||
reversed: ref.read(desktopExchangeModelProvider)!.reversed,
|
||||
);
|
||||
|
||||
if (response.value == null) {
|
||||
if (mounted) {
|
||||
Navigator.of(context).pop();
|
||||
}
|
||||
|
||||
unawaited(
|
||||
showDialog<void>(
|
||||
context: context,
|
||||
barrierDismissible: true,
|
||||
builder: (_) => SimpleDesktopDialog(
|
||||
title: "Failed to create trade",
|
||||
message: response.exception?.toString() ?? ""),
|
||||
),
|
||||
);
|
||||
return false;
|
||||
}
|
||||
|
||||
// save trade to hive
|
||||
await ref.read(tradesServiceProvider).add(
|
||||
trade: response.value!,
|
||||
shouldNotifyListeners: true,
|
||||
);
|
||||
|
||||
String status = response.value!.status;
|
||||
|
||||
ref.read(desktopExchangeModelProvider)!.trade = response.value!;
|
||||
|
||||
// extra info if status is waiting
|
||||
if (status == "Waiting") {
|
||||
status += " for deposit";
|
||||
}
|
||||
|
||||
if (mounted) {
|
||||
Navigator.of(context).pop();
|
||||
}
|
||||
|
||||
unawaited(
|
||||
NotificationApi.showNotification(
|
||||
changeNowId: ref.read(desktopExchangeModelProvider)!.trade!.tradeId,
|
||||
title: status,
|
||||
body:
|
||||
"Trade ID ${ref.read(desktopExchangeModelProvider)!.trade!.tradeId}",
|
||||
walletId: "",
|
||||
iconAssetName: Assets.svg.arrowRotate,
|
||||
date: ref.read(desktopExchangeModelProvider)!.trade!.timestamp,
|
||||
shouldWatchForUpdates: true,
|
||||
coinName: "coinName",
|
||||
),
|
||||
);
|
||||
|
||||
return true;
|
||||
// if (mounted) {
|
||||
// unawaited(
|
||||
// showDialog<void>(
|
||||
// context: context,
|
||||
// barrierColor: Colors.transparent,
|
||||
// barrierDismissible: false,
|
||||
// builder: (context) {
|
||||
// return DesktopDialog(
|
||||
// maxWidth: 720,
|
||||
// maxHeight: double.infinity,
|
||||
// child: StepScaffold(
|
||||
// initialStep: 4,
|
||||
// ),
|
||||
// );
|
||||
// },
|
||||
// ),
|
||||
// );
|
||||
// }
|
||||
}
|
||||
|
||||
void onBack() {
|
||||
if (currentStep > 1 && currentStep < 4) {
|
||||
setState(() => currentStep = currentStep - 1);
|
||||
} else if (currentStep == 1) {
|
||||
Navigator.of(context, rootNavigator: true).pop();
|
||||
}
|
||||
}
|
||||
|
||||
void sendFromStack() {
|
||||
final trade = ref.read(desktopExchangeModelProvider)!.trade!;
|
||||
final amount = Decimal.parse(trade.payInAmount);
|
||||
final address = trade.payInAddress;
|
||||
|
||||
final coin = coinFromTickerCaseInsensitive(trade.payInCurrency);
|
||||
|
||||
showDialog<void>(
|
||||
context: context,
|
||||
builder: (context) => Navigator(
|
||||
initialRoute: SendFromView.routeName,
|
||||
onGenerateRoute: RouteGenerator.generateRoute,
|
||||
onGenerateInitialRoutes: (_, __) {
|
||||
return [
|
||||
FadePageRoute(
|
||||
SendFromView(
|
||||
coin: coin,
|
||||
trade: trade,
|
||||
amount: amount,
|
||||
address: address,
|
||||
shouldPopRoot: true,
|
||||
fromDesktopStep4: true,
|
||||
),
|
||||
const RouteSettings(
|
||||
name: SendFromView.routeName,
|
||||
),
|
||||
),
|
||||
];
|
||||
},
|
||||
),
|
||||
);
|
||||
}
|
||||
|
||||
@override
|
||||
void initState() {
|
||||
currentStep = widget.step;
|
||||
model = widget.model;
|
||||
duration = const Duration(milliseconds: 250);
|
||||
currentStep = widget.initialStep;
|
||||
super.initState();
|
||||
}
|
||||
|
||||
@override
|
||||
Widget build(BuildContext context) {
|
||||
final model = ref.watch(desktopExchangeModelProvider);
|
||||
return Column(
|
||||
mainAxisAlignment: MainAxisAlignment.start,
|
||||
children: [
|
||||
Row(
|
||||
mainAxisAlignment: MainAxisAlignment.spaceBetween,
|
||||
children: [
|
||||
const AppBarBackButton(
|
||||
isCompact: true,
|
||||
iconSize: 23,
|
||||
),
|
||||
Text(
|
||||
"Exchange ${model.sendTicker.toUpperCase()} to ${model.receiveTicker.toUpperCase()}",
|
||||
style: STextStyles.desktopH3(context),
|
||||
Row(
|
||||
children: [
|
||||
currentStep != 4
|
||||
? AppBarBackButton(
|
||||
isCompact: true,
|
||||
iconSize: 23,
|
||||
onPressed: onBack,
|
||||
)
|
||||
: const SizedBox(
|
||||
width: 32,
|
||||
),
|
||||
Text(
|
||||
"Exchange ${model?.sendTicker.toUpperCase()} to ${model?.receiveTicker.toUpperCase()}",
|
||||
style: STextStyles.desktopH3(context),
|
||||
),
|
||||
],
|
||||
),
|
||||
if (currentStep == 4)
|
||||
DesktopDialogCloseButton(
|
||||
onPressedOverride: () {
|
||||
Navigator.of(context, rootNavigator: true).pop();
|
||||
},
|
||||
),
|
||||
],
|
||||
),
|
||||
const SizedBox(
|
||||
|
@ -66,7 +271,139 @@ class _StepScaffoldState extends State<StepScaffold> {
|
|||
padding: const EdgeInsets.symmetric(
|
||||
horizontal: 32,
|
||||
),
|
||||
child: widget.body,
|
||||
child: FadeStack(
|
||||
index: currentStep - 1,
|
||||
children: [
|
||||
const DesktopStep1(),
|
||||
DesktopStep2(
|
||||
enableNextChanged: updateEnableNext,
|
||||
),
|
||||
const DesktopStep3(),
|
||||
const DesktopStep4(),
|
||||
],
|
||||
),
|
||||
),
|
||||
Padding(
|
||||
padding: const EdgeInsets.only(
|
||||
top: 20,
|
||||
left: 32,
|
||||
right: 32,
|
||||
bottom: 32,
|
||||
),
|
||||
child: Row(
|
||||
children: [
|
||||
Expanded(
|
||||
child: AnimatedCrossFade(
|
||||
duration: const Duration(milliseconds: 250),
|
||||
crossFadeState: currentStep == 4
|
||||
? CrossFadeState.showSecond
|
||||
: CrossFadeState.showFirst,
|
||||
firstChild: SecondaryButton(
|
||||
label: "Back",
|
||||
buttonHeight: ButtonHeight.l,
|
||||
onPressed: onBack,
|
||||
),
|
||||
secondChild: SecondaryButton(
|
||||
label: "Send from Stack Wallet",
|
||||
buttonHeight: ButtonHeight.l,
|
||||
onPressed: sendFromStack,
|
||||
),
|
||||
),
|
||||
),
|
||||
const SizedBox(
|
||||
width: 16,
|
||||
),
|
||||
Expanded(
|
||||
child: AnimatedCrossFade(
|
||||
duration: const Duration(milliseconds: 250),
|
||||
crossFadeState: currentStep == 4
|
||||
? CrossFadeState.showSecond
|
||||
: CrossFadeState.showFirst,
|
||||
firstChild: AnimatedCrossFade(
|
||||
duration: const Duration(milliseconds: 250),
|
||||
crossFadeState: currentStep == 3
|
||||
? CrossFadeState.showSecond
|
||||
: CrossFadeState.showFirst,
|
||||
firstChild: PrimaryButton(
|
||||
label: "Next",
|
||||
enabled: currentStep != 2 ? true : enableNext,
|
||||
buttonHeight: ButtonHeight.l,
|
||||
onPressed: () async {
|
||||
setState(() => currentStep = currentStep + 1);
|
||||
},
|
||||
),
|
||||
secondChild: PrimaryButton(
|
||||
label: "Confirm",
|
||||
enabled: currentStep != 2 ? true : enableNext,
|
||||
buttonHeight: ButtonHeight.l,
|
||||
onPressed: () async {
|
||||
if (currentStep == 3) {
|
||||
final success = await createTrade();
|
||||
if (!success) {
|
||||
return;
|
||||
}
|
||||
}
|
||||
setState(() => currentStep = currentStep + 1);
|
||||
},
|
||||
),
|
||||
),
|
||||
secondChild: PrimaryButton(
|
||||
label: "Show QR code",
|
||||
enabled: currentStep != 2 ? true : enableNext,
|
||||
buttonHeight: ButtonHeight.l,
|
||||
onPressed: () {
|
||||
showDialog<dynamic>(
|
||||
context: context,
|
||||
barrierColor: Colors.transparent,
|
||||
barrierDismissible: true,
|
||||
builder: (_) {
|
||||
return DesktopDialog(
|
||||
maxHeight: 720,
|
||||
maxWidth: 720,
|
||||
child: Column(
|
||||
mainAxisAlignment: MainAxisAlignment.center,
|
||||
crossAxisAlignment: CrossAxisAlignment.center,
|
||||
children: [
|
||||
Text(
|
||||
"Send ${ref.watch(desktopExchangeModelProvider.select((value) => value!.sendAmount.toStringAsFixed(8)))} ${ref.watch(desktopExchangeModelProvider.select((value) => value!.sendTicker))} to this address",
|
||||
style: STextStyles.desktopH3(context),
|
||||
),
|
||||
const SizedBox(
|
||||
height: 48,
|
||||
),
|
||||
Center(
|
||||
child: QrImage(
|
||||
// TODO: grab coin uri scheme from somewhere
|
||||
// data: "${coin.uriScheme}:$receivingAddress",
|
||||
data: ref.watch(desktopExchangeModelProvider
|
||||
.select((value) =>
|
||||
value!.trade!.payInAddress)),
|
||||
size: 290,
|
||||
foregroundColor: Theme.of(context)
|
||||
.extension<StackColors>()!
|
||||
.accentColorDark,
|
||||
),
|
||||
),
|
||||
const SizedBox(
|
||||
height: 48,
|
||||
),
|
||||
SecondaryButton(
|
||||
label: "Cancel",
|
||||
width: 310,
|
||||
buttonHeight: ButtonHeight.l,
|
||||
onPressed: Navigator.of(context).pop,
|
||||
),
|
||||
],
|
||||
),
|
||||
);
|
||||
},
|
||||
);
|
||||
},
|
||||
),
|
||||
),
|
||||
),
|
||||
],
|
||||
),
|
||||
),
|
||||
],
|
||||
);
|
||||
|
|
|
@ -1,26 +1,18 @@
|
|||
import 'package:flutter/material.dart';
|
||||
import 'package:flutter_riverpod/flutter_riverpod.dart';
|
||||
import 'package:stackwallet/models/exchange/incomplete_exchange.dart';
|
||||
import 'package:stackwallet/pages/exchange_view/sub_widgets/exchange_rate_sheet.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/desktop_exchange/exchange_steps/step_scaffold.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/desktop_exchange/exchange_steps/subwidgets/desktop_step_2.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/desktop_exchange/exchange_steps/subwidgets/desktop_step_item.dart';
|
||||
import 'package:stackwallet/providers/providers.dart';
|
||||
import 'package:stackwallet/utilities/text_styles.dart';
|
||||
import 'package:stackwallet/utilities/theme/stack_colors.dart';
|
||||
import 'package:stackwallet/widgets/desktop/desktop_dialog.dart';
|
||||
import 'package:stackwallet/widgets/desktop/primary_button.dart';
|
||||
import 'package:stackwallet/widgets/desktop/secondary_button.dart';
|
||||
import 'package:stackwallet/widgets/rounded_white_container.dart';
|
||||
|
||||
class DesktopStep1 extends ConsumerWidget {
|
||||
const DesktopStep1({
|
||||
Key? key,
|
||||
required this.model,
|
||||
}) : super(key: key);
|
||||
|
||||
final IncompleteExchangeModel model;
|
||||
|
||||
@override
|
||||
Widget build(BuildContext context, WidgetRef ref) {
|
||||
return Column(
|
||||
|
@ -55,7 +47,7 @@ class DesktopStep1 extends ConsumerWidget {
|
|||
DesktopStepItem(
|
||||
label: "You send",
|
||||
value:
|
||||
"${model.sendAmount.toStringAsFixed(8)} ${model.sendTicker.toUpperCase()}",
|
||||
"${ref.watch(desktopExchangeModelProvider.select((value) => value!.sendAmount.toStringAsFixed(8)))} ${ref.watch(desktopExchangeModelProvider.select((value) => value!.sendTicker.toUpperCase()))}",
|
||||
),
|
||||
Container(
|
||||
height: 1,
|
||||
|
@ -64,63 +56,20 @@ class DesktopStep1 extends ConsumerWidget {
|
|||
DesktopStepItem(
|
||||
label: "You receive",
|
||||
value:
|
||||
"~${model.receiveAmount.toStringAsFixed(8)} ${model.receiveTicker.toUpperCase()}",
|
||||
"~${ref.watch(desktopExchangeModelProvider.select((value) => value!.receiveAmount.toStringAsFixed(8)))} ${ref.watch(desktopExchangeModelProvider.select((value) => value!.receiveTicker.toUpperCase()))}",
|
||||
),
|
||||
Container(
|
||||
height: 1,
|
||||
color: Theme.of(context).extension<StackColors>()!.background,
|
||||
),
|
||||
DesktopStepItem(
|
||||
label: model.rateType == ExchangeRateType.estimated
|
||||
label: ref.watch(desktopExchangeModelProvider
|
||||
.select((value) => value!.rateType)) ==
|
||||
ExchangeRateType.estimated
|
||||
? "Estimated rate"
|
||||
: "Fixed rate",
|
||||
value: model.rateInfo,
|
||||
),
|
||||
],
|
||||
),
|
||||
),
|
||||
Padding(
|
||||
padding: const EdgeInsets.only(
|
||||
top: 20,
|
||||
bottom: 32,
|
||||
),
|
||||
child: Row(
|
||||
children: [
|
||||
Expanded(
|
||||
child: SecondaryButton(
|
||||
label: "Back",
|
||||
buttonHeight: ButtonHeight.l,
|
||||
onPressed: Navigator.of(context).pop,
|
||||
),
|
||||
),
|
||||
const SizedBox(
|
||||
width: 16,
|
||||
),
|
||||
Expanded(
|
||||
child: PrimaryButton(
|
||||
label: "Next",
|
||||
buttonHeight: ButtonHeight.l,
|
||||
onPressed: () async {
|
||||
await showDialog<void>(
|
||||
context: context,
|
||||
barrierColor: Colors.transparent,
|
||||
barrierDismissible: false,
|
||||
builder: (context) {
|
||||
return DesktopDialog(
|
||||
maxWidth: 720,
|
||||
maxHeight: double.infinity,
|
||||
child: StepScaffold(
|
||||
step: 2,
|
||||
model: model,
|
||||
body: DesktopStep2(
|
||||
model: model,
|
||||
),
|
||||
),
|
||||
);
|
||||
},
|
||||
);
|
||||
},
|
||||
),
|
||||
value: ref.watch(desktopExchangeModelProvider
|
||||
.select((value) => value!.rateInfo)),
|
||||
),
|
||||
],
|
||||
),
|
||||
|
|
|
@ -2,11 +2,9 @@ import 'package:flutter/material.dart';
|
|||
import 'package:flutter/services.dart';
|
||||
import 'package:flutter_riverpod/flutter_riverpod.dart';
|
||||
import 'package:stackwallet/models/contact_address_entry.dart';
|
||||
import 'package:stackwallet/models/exchange/incomplete_exchange.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/desktop_exchange/exchange_steps/step_scaffold.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/desktop_exchange/exchange_steps/subwidgets/desktop_step_3.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/desktop_exchange/subwidgets/desktop_choose_from_stack.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/home/my_stack_view/wallet_view/sub_widgets/address_book_address_chooser/address_book_address_chooser.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/my_stack_view/wallet_view/sub_widgets/address_book_address_chooser/address_book_address_chooser.dart';
|
||||
import 'package:stackwallet/providers/exchange/exchange_send_from_wallet_id_provider.dart';
|
||||
import 'package:stackwallet/providers/global/wallets_provider.dart';
|
||||
import 'package:stackwallet/utilities/clipboard_interface.dart';
|
||||
|
@ -18,31 +16,29 @@ import 'package:stackwallet/utilities/theme/stack_colors.dart';
|
|||
import 'package:stackwallet/widgets/custom_buttons/blue_text_button.dart';
|
||||
import 'package:stackwallet/widgets/desktop/desktop_dialog.dart';
|
||||
import 'package:stackwallet/widgets/desktop/desktop_dialog_close_button.dart';
|
||||
import 'package:stackwallet/widgets/desktop/primary_button.dart';
|
||||
import 'package:stackwallet/widgets/desktop/secondary_button.dart';
|
||||
import 'package:stackwallet/widgets/icon_widgets/addressbook_icon.dart';
|
||||
import 'package:stackwallet/widgets/icon_widgets/clipboard_icon.dart';
|
||||
import 'package:stackwallet/widgets/icon_widgets/x_icon.dart';
|
||||
import 'package:stackwallet/widgets/rounded_white_container.dart';
|
||||
import 'package:stackwallet/widgets/stack_text_field.dart';
|
||||
import 'package:stackwallet/widgets/textfield_icon_button.dart';
|
||||
import 'package:tuple/tuple.dart';
|
||||
|
||||
class DesktopStep2 extends ConsumerStatefulWidget {
|
||||
const DesktopStep2({
|
||||
Key? key,
|
||||
required this.model,
|
||||
required this.enableNextChanged,
|
||||
this.clipboard = const ClipboardWrapper(),
|
||||
}) : super(key: key);
|
||||
|
||||
final IncompleteExchangeModel model;
|
||||
final ClipboardInterface clipboard;
|
||||
final void Function(bool) enableNextChanged;
|
||||
|
||||
@override
|
||||
ConsumerState<DesktopStep2> createState() => _DesktopStep2State();
|
||||
}
|
||||
|
||||
class _DesktopStep2State extends ConsumerState<DesktopStep2> {
|
||||
late final IncompleteExchangeModel model;
|
||||
late final ClipboardInterface clipboard;
|
||||
|
||||
late final TextEditingController _toController;
|
||||
|
@ -51,8 +47,6 @@ class _DesktopStep2State extends ConsumerState<DesktopStep2> {
|
|||
late final FocusNode _toFocusNode;
|
||||
late final FocusNode _refundFocusNode;
|
||||
|
||||
bool enableNext = false;
|
||||
|
||||
bool isStackCoin(String ticker) {
|
||||
try {
|
||||
coinFromTickerCaseInsensitive(ticker);
|
||||
|
@ -65,10 +59,10 @@ class _DesktopStep2State extends ConsumerState<DesktopStep2> {
|
|||
void selectRecipientAddressFromStack() async {
|
||||
try {
|
||||
final coin = coinFromTickerCaseInsensitive(
|
||||
model.receiveTicker,
|
||||
ref.read(desktopExchangeModelProvider)!.receiveTicker,
|
||||
);
|
||||
|
||||
final address = await showDialog<String?>(
|
||||
final info = await showDialog<Tuple2<String, String>?>(
|
||||
context: context,
|
||||
barrierColor: Colors.transparent,
|
||||
builder: (context) => DesktopDialog(
|
||||
|
@ -83,29 +77,25 @@ class _DesktopStep2State extends ConsumerState<DesktopStep2> {
|
|||
),
|
||||
);
|
||||
|
||||
if (address is String) {
|
||||
final manager =
|
||||
ref.read(walletsChangeNotifierProvider).getManager(address);
|
||||
|
||||
_toController.text = manager.walletName;
|
||||
model.recipientAddress = await manager.currentReceivingAddress;
|
||||
if (info is Tuple2<String, String>) {
|
||||
_toController.text = info.item1;
|
||||
ref.read(desktopExchangeModelProvider)!.recipientAddress = info.item2;
|
||||
}
|
||||
} catch (e, s) {
|
||||
Logging.instance.log("$e\n$s", level: LogLevel.Info);
|
||||
}
|
||||
setState(() {
|
||||
enableNext =
|
||||
_toController.text.isNotEmpty && _refundController.text.isNotEmpty;
|
||||
});
|
||||
|
||||
widget.enableNextChanged.call(
|
||||
_toController.text.isNotEmpty && _refundController.text.isNotEmpty);
|
||||
}
|
||||
|
||||
void selectRefundAddressFromStack() async {
|
||||
try {
|
||||
final coin = coinFromTickerCaseInsensitive(
|
||||
model.sendTicker,
|
||||
ref.read(desktopExchangeModelProvider)!.sendTicker,
|
||||
);
|
||||
|
||||
final address = await showDialog<String?>(
|
||||
final info = await showDialog<Tuple2<String, String>?>(
|
||||
context: context,
|
||||
barrierColor: Colors.transparent,
|
||||
builder: (context) => DesktopDialog(
|
||||
|
@ -119,25 +109,20 @@ class _DesktopStep2State extends ConsumerState<DesktopStep2> {
|
|||
),
|
||||
),
|
||||
);
|
||||
if (address is String) {
|
||||
final manager =
|
||||
ref.read(walletsChangeNotifierProvider).getManager(address);
|
||||
|
||||
_refundController.text = manager.walletName;
|
||||
model.refundAddress = await manager.currentReceivingAddress;
|
||||
if (info is Tuple2<String, String>) {
|
||||
_refundController.text = info.item1;
|
||||
ref.read(desktopExchangeModelProvider)!.refundAddress = info.item2;
|
||||
}
|
||||
} catch (e, s) {
|
||||
Logging.instance.log("$e\n$s", level: LogLevel.Info);
|
||||
}
|
||||
setState(() {
|
||||
enableNext =
|
||||
_toController.text.isNotEmpty && _refundController.text.isNotEmpty;
|
||||
});
|
||||
widget.enableNextChanged.call(
|
||||
_toController.text.isNotEmpty && _refundController.text.isNotEmpty);
|
||||
}
|
||||
|
||||
void selectRecipientFromAddressBook() async {
|
||||
final coin = coinFromTickerCaseInsensitive(
|
||||
model.receiveTicker,
|
||||
ref.read(desktopExchangeModelProvider)!.receiveTicker,
|
||||
);
|
||||
|
||||
final entry = await showDialog<ContactAddressEntry?>(
|
||||
|
@ -176,17 +161,15 @@ class _DesktopStep2State extends ConsumerState<DesktopStep2> {
|
|||
|
||||
if (entry != null) {
|
||||
_toController.text = entry.address;
|
||||
model.recipientAddress = entry.address;
|
||||
setState(() {
|
||||
enableNext =
|
||||
_toController.text.isNotEmpty && _refundController.text.isNotEmpty;
|
||||
});
|
||||
ref.read(desktopExchangeModelProvider)!.recipientAddress = entry.address;
|
||||
widget.enableNextChanged.call(
|
||||
_toController.text.isNotEmpty && _refundController.text.isNotEmpty);
|
||||
}
|
||||
}
|
||||
|
||||
void selectRefundFromAddressBook() async {
|
||||
final coin = coinFromTickerCaseInsensitive(
|
||||
model.sendTicker,
|
||||
ref.read(desktopExchangeModelProvider)!.sendTicker,
|
||||
);
|
||||
|
||||
final entry = await showDialog<ContactAddressEntry?>(
|
||||
|
@ -225,17 +208,14 @@ class _DesktopStep2State extends ConsumerState<DesktopStep2> {
|
|||
|
||||
if (entry != null) {
|
||||
_refundController.text = entry.address;
|
||||
model.refundAddress = entry.address;
|
||||
setState(() {
|
||||
enableNext =
|
||||
_toController.text.isNotEmpty && _refundController.text.isNotEmpty;
|
||||
});
|
||||
ref.read(desktopExchangeModelProvider)!.refundAddress = entry.address;
|
||||
widget.enableNextChanged.call(
|
||||
_toController.text.isNotEmpty && _refundController.text.isNotEmpty);
|
||||
}
|
||||
}
|
||||
|
||||
@override
|
||||
void initState() {
|
||||
model = widget.model;
|
||||
clipboard = widget.clipboard;
|
||||
|
||||
_toController = TextEditingController();
|
||||
|
@ -246,7 +226,7 @@ class _DesktopStep2State extends ConsumerState<DesktopStep2> {
|
|||
|
||||
final tuple = ref.read(exchangeSendFromWalletIdStateProvider.state).state;
|
||||
if (tuple != null) {
|
||||
if (model.receiveTicker.toLowerCase() ==
|
||||
if (ref.read(desktopExchangeModelProvider)!.receiveTicker.toLowerCase() ==
|
||||
tuple.item2.ticker.toLowerCase()) {
|
||||
ref
|
||||
.read(walletsChangeNotifierProvider)
|
||||
|
@ -254,10 +234,11 @@ class _DesktopStep2State extends ConsumerState<DesktopStep2> {
|
|||
.currentReceivingAddress
|
||||
.then((value) {
|
||||
_toController.text = value;
|
||||
model.recipientAddress = _toController.text;
|
||||
ref.read(desktopExchangeModelProvider)!.recipientAddress =
|
||||
_toController.text;
|
||||
});
|
||||
} else {
|
||||
if (model.sendTicker.toUpperCase() ==
|
||||
if (ref.read(desktopExchangeModelProvider)!.sendTicker.toUpperCase() ==
|
||||
tuple.item2.ticker.toUpperCase()) {
|
||||
ref
|
||||
.read(walletsChangeNotifierProvider)
|
||||
|
@ -265,7 +246,8 @@ class _DesktopStep2State extends ConsumerState<DesktopStep2> {
|
|||
.currentReceivingAddress
|
||||
.then((value) {
|
||||
_refundController.text = value;
|
||||
model.refundAddress = _refundController.text;
|
||||
ref.read(desktopExchangeModelProvider)!.refundAddress =
|
||||
_refundController.text;
|
||||
});
|
||||
}
|
||||
}
|
||||
|
@ -316,7 +298,8 @@ class _DesktopStep2State extends ConsumerState<DesktopStep2> {
|
|||
.extension<StackColors>()!
|
||||
.textFieldActiveSearchIconRight),
|
||||
),
|
||||
if (isStackCoin(model.receiveTicker))
|
||||
if (isStackCoin(ref.watch(desktopExchangeModelProvider
|
||||
.select((value) => value!.receiveTicker))))
|
||||
BlueTextButton(
|
||||
text: "Choose from stack",
|
||||
onTap: selectRecipientAddressFromStack,
|
||||
|
@ -349,13 +332,11 @@ class _DesktopStep2State extends ConsumerState<DesktopStep2> {
|
|||
focusNode: _toFocusNode,
|
||||
style: STextStyles.field(context),
|
||||
onChanged: (value) {
|
||||
setState(() {
|
||||
enableNext = _toController.text.isNotEmpty &&
|
||||
_refundController.text.isNotEmpty;
|
||||
});
|
||||
widget.enableNextChanged.call(_toController.text.isNotEmpty &&
|
||||
_refundController.text.isNotEmpty);
|
||||
},
|
||||
decoration: standardInputDecoration(
|
||||
"Enter the ${model.receiveTicker.toUpperCase()} payout address",
|
||||
"Enter the ${ref.watch(desktopExchangeModelProvider.select((value) => value!.receiveTicker.toUpperCase()))} payout address",
|
||||
_toFocusNode,
|
||||
context,
|
||||
desktopMed: true,
|
||||
|
@ -380,11 +361,12 @@ class _DesktopStep2State extends ConsumerState<DesktopStep2> {
|
|||
"sendViewClearAddressFieldButtonKey"),
|
||||
onTap: () {
|
||||
_toController.text = "";
|
||||
model.recipientAddress = _toController.text;
|
||||
setState(() {
|
||||
enableNext = _toController.text.isNotEmpty &&
|
||||
_refundController.text.isNotEmpty;
|
||||
});
|
||||
ref
|
||||
.read(desktopExchangeModelProvider)!
|
||||
.recipientAddress = _toController.text;
|
||||
widget.enableNextChanged.call(
|
||||
_toController.text.isNotEmpty &&
|
||||
_refundController.text.isNotEmpty);
|
||||
},
|
||||
child: const XIcon(),
|
||||
)
|
||||
|
@ -398,12 +380,12 @@ class _DesktopStep2State extends ConsumerState<DesktopStep2> {
|
|||
data!.text!.isNotEmpty) {
|
||||
final content = data.text!.trim();
|
||||
_toController.text = content;
|
||||
model.recipientAddress = _toController.text;
|
||||
setState(() {
|
||||
enableNext =
|
||||
_toController.text.isNotEmpty &&
|
||||
_refundController.text.isNotEmpty;
|
||||
});
|
||||
ref
|
||||
.read(desktopExchangeModelProvider)!
|
||||
.recipientAddress = _toController.text;
|
||||
widget.enableNextChanged.call(
|
||||
_toController.text.isNotEmpty &&
|
||||
_refundController.text.isNotEmpty);
|
||||
}
|
||||
},
|
||||
child: _toController.text.isEmpty
|
||||
|
@ -411,7 +393,8 @@ class _DesktopStep2State extends ConsumerState<DesktopStep2> {
|
|||
: const XIcon(),
|
||||
),
|
||||
if (_toController.text.isEmpty &&
|
||||
isStackCoin(model.receiveTicker))
|
||||
isStackCoin(ref.watch(desktopExchangeModelProvider
|
||||
.select((value) => value!.receiveTicker))))
|
||||
TextFieldIconButton(
|
||||
key: const Key("sendViewAddressBookButtonKey"),
|
||||
onTap: selectRecipientFromAddressBook,
|
||||
|
@ -430,7 +413,7 @@ class _DesktopStep2State extends ConsumerState<DesktopStep2> {
|
|||
RoundedWhiteContainer(
|
||||
borderColor: Theme.of(context).extension<StackColors>()!.background,
|
||||
child: Text(
|
||||
"This is the wallet where your ${model.receiveTicker.toUpperCase()} will be sent to.",
|
||||
"This is the wallet where your ${ref.watch(desktopExchangeModelProvider.select((value) => value!.receiveTicker.toUpperCase()))} will be sent to.",
|
||||
style: STextStyles.desktopTextExtraExtraSmall(context),
|
||||
),
|
||||
),
|
||||
|
@ -447,7 +430,8 @@ class _DesktopStep2State extends ConsumerState<DesktopStep2> {
|
|||
.extension<StackColors>()!
|
||||
.textFieldActiveSearchIconRight),
|
||||
),
|
||||
if (isStackCoin(model.sendTicker))
|
||||
if (isStackCoin(ref.watch(desktopExchangeModelProvider
|
||||
.select((value) => value!.sendTicker))))
|
||||
BlueTextButton(
|
||||
text: "Choose from stack",
|
||||
onTap: selectRefundAddressFromStack,
|
||||
|
@ -479,13 +463,11 @@ class _DesktopStep2State extends ConsumerState<DesktopStep2> {
|
|||
focusNode: _refundFocusNode,
|
||||
style: STextStyles.field(context),
|
||||
onChanged: (value) {
|
||||
setState(() {
|
||||
enableNext = _toController.text.isNotEmpty &&
|
||||
_refundController.text.isNotEmpty;
|
||||
});
|
||||
widget.enableNextChanged.call(_toController.text.isNotEmpty &&
|
||||
_refundController.text.isNotEmpty);
|
||||
},
|
||||
decoration: standardInputDecoration(
|
||||
"Enter ${model.sendTicker.toUpperCase()} refund address",
|
||||
"Enter ${ref.watch(desktopExchangeModelProvider.select((value) => value!.sendTicker.toUpperCase()))} refund address",
|
||||
_refundFocusNode,
|
||||
context,
|
||||
desktopMed: true,
|
||||
|
@ -510,12 +492,13 @@ class _DesktopStep2State extends ConsumerState<DesktopStep2> {
|
|||
"sendViewClearAddressFieldButtonKey"),
|
||||
onTap: () {
|
||||
_refundController.text = "";
|
||||
model.refundAddress = _refundController.text;
|
||||
ref
|
||||
.read(desktopExchangeModelProvider)!
|
||||
.refundAddress = _refundController.text;
|
||||
|
||||
setState(() {
|
||||
enableNext = _toController.text.isNotEmpty &&
|
||||
_refundController.text.isNotEmpty;
|
||||
});
|
||||
widget.enableNextChanged.call(
|
||||
_toController.text.isNotEmpty &&
|
||||
_refundController.text.isNotEmpty);
|
||||
},
|
||||
child: const XIcon(),
|
||||
)
|
||||
|
@ -530,13 +513,13 @@ class _DesktopStep2State extends ConsumerState<DesktopStep2> {
|
|||
final content = data.text!.trim();
|
||||
|
||||
_refundController.text = content;
|
||||
model.refundAddress = _refundController.text;
|
||||
ref
|
||||
.read(desktopExchangeModelProvider)!
|
||||
.refundAddress = _refundController.text;
|
||||
|
||||
setState(() {
|
||||
enableNext =
|
||||
_toController.text.isNotEmpty &&
|
||||
_refundController.text.isNotEmpty;
|
||||
});
|
||||
widget.enableNextChanged.call(
|
||||
_toController.text.isNotEmpty &&
|
||||
_refundController.text.isNotEmpty);
|
||||
}
|
||||
},
|
||||
child: _refundController.text.isEmpty
|
||||
|
@ -544,7 +527,8 @@ class _DesktopStep2State extends ConsumerState<DesktopStep2> {
|
|||
: const XIcon(),
|
||||
),
|
||||
if (_refundController.text.isEmpty &&
|
||||
isStackCoin(model.sendTicker))
|
||||
isStackCoin(ref.watch(desktopExchangeModelProvider
|
||||
.select((value) => value!.sendTicker))))
|
||||
TextFieldIconButton(
|
||||
key: const Key("sendViewAddressBookButtonKey"),
|
||||
onTap: selectRefundFromAddressBook,
|
||||
|
@ -567,53 +551,6 @@ class _DesktopStep2State extends ConsumerState<DesktopStep2> {
|
|||
style: STextStyles.desktopTextExtraExtraSmall(context),
|
||||
),
|
||||
),
|
||||
Padding(
|
||||
padding: const EdgeInsets.only(
|
||||
top: 20,
|
||||
bottom: 32,
|
||||
),
|
||||
child: Row(
|
||||
children: [
|
||||
Expanded(
|
||||
child: SecondaryButton(
|
||||
label: "Back",
|
||||
buttonHeight: ButtonHeight.l,
|
||||
onPressed: Navigator.of(context).pop,
|
||||
),
|
||||
),
|
||||
const SizedBox(
|
||||
width: 16,
|
||||
),
|
||||
Expanded(
|
||||
child: PrimaryButton(
|
||||
label: "Next",
|
||||
enabled: enableNext,
|
||||
buttonHeight: ButtonHeight.l,
|
||||
onPressed: () async {
|
||||
await showDialog<void>(
|
||||
context: context,
|
||||
barrierColor: Colors.transparent,
|
||||
barrierDismissible: false,
|
||||
builder: (context) {
|
||||
return DesktopDialog(
|
||||
maxWidth: 720,
|
||||
maxHeight: double.infinity,
|
||||
child: StepScaffold(
|
||||
step: 3,
|
||||
model: model,
|
||||
body: DesktopStep3(
|
||||
model: model,
|
||||
),
|
||||
),
|
||||
);
|
||||
},
|
||||
);
|
||||
},
|
||||
),
|
||||
),
|
||||
],
|
||||
),
|
||||
),
|
||||
],
|
||||
);
|
||||
}
|
||||
|
|
|
@ -1,157 +1,23 @@
|
|||
import 'dart:async';
|
||||
|
||||
import 'package:flutter/material.dart';
|
||||
import 'package:flutter_riverpod/flutter_riverpod.dart';
|
||||
import 'package:stackwallet/models/exchange/incomplete_exchange.dart';
|
||||
import 'package:stackwallet/models/exchange/response_objects/trade.dart';
|
||||
import 'package:stackwallet/pages/exchange_view/sub_widgets/exchange_rate_sheet.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/desktop_exchange/exchange_steps/step_scaffold.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/desktop_exchange/exchange_steps/subwidgets/desktop_step_4.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/desktop_exchange/exchange_steps/subwidgets/desktop_step_item.dart';
|
||||
import 'package:stackwallet/providers/exchange/current_exchange_name_state_provider.dart';
|
||||
import 'package:stackwallet/providers/exchange/exchange_provider.dart';
|
||||
import 'package:stackwallet/providers/global/trades_service_provider.dart';
|
||||
import 'package:stackwallet/services/exchange/exchange_response.dart';
|
||||
import 'package:stackwallet/services/notifications_api.dart';
|
||||
import 'package:stackwallet/utilities/assets.dart';
|
||||
import 'package:stackwallet/utilities/text_styles.dart';
|
||||
import 'package:stackwallet/utilities/theme/stack_colors.dart';
|
||||
import 'package:stackwallet/widgets/custom_loading_overlay.dart';
|
||||
import 'package:stackwallet/widgets/desktop/desktop_dialog.dart';
|
||||
import 'package:stackwallet/widgets/desktop/primary_button.dart';
|
||||
import 'package:stackwallet/widgets/desktop/secondary_button.dart';
|
||||
import 'package:stackwallet/widgets/desktop/simple_desktop_dialog.dart';
|
||||
import 'package:stackwallet/widgets/rounded_white_container.dart';
|
||||
|
||||
class DesktopStep3 extends ConsumerStatefulWidget {
|
||||
const DesktopStep3({
|
||||
Key? key,
|
||||
required this.model,
|
||||
}) : super(key: key);
|
||||
|
||||
final IncompleteExchangeModel model;
|
||||
|
||||
@override
|
||||
ConsumerState<DesktopStep3> createState() => _DesktopStep3State();
|
||||
}
|
||||
|
||||
class _DesktopStep3State extends ConsumerState<DesktopStep3> {
|
||||
late final IncompleteExchangeModel model;
|
||||
|
||||
Future<void> createTrade() async {
|
||||
unawaited(
|
||||
showDialog<void>(
|
||||
context: context,
|
||||
barrierDismissible: false,
|
||||
builder: (_) => WillPopScope(
|
||||
onWillPop: () async => false,
|
||||
child: Container(
|
||||
color: Theme.of(context)
|
||||
.extension<StackColors>()!
|
||||
.overlay
|
||||
.withOpacity(0.6),
|
||||
child: const CustomLoadingOverlay(
|
||||
message: "Creating a trade",
|
||||
eventBus: null,
|
||||
),
|
||||
),
|
||||
),
|
||||
),
|
||||
);
|
||||
|
||||
final ExchangeResponse<Trade> response =
|
||||
await ref.read(exchangeProvider).createTrade(
|
||||
from: model.sendTicker,
|
||||
to: model.receiveTicker,
|
||||
fixedRate: model.rateType != ExchangeRateType.estimated,
|
||||
amount: model.reversed ? model.receiveAmount : model.sendAmount,
|
||||
addressTo: model.recipientAddress!,
|
||||
extraId: null,
|
||||
addressRefund: model.refundAddress!,
|
||||
refundExtraId: "",
|
||||
rateId: model.rateId,
|
||||
reversed: model.reversed,
|
||||
);
|
||||
|
||||
if (response.value == null) {
|
||||
if (mounted) {
|
||||
Navigator.of(context).pop();
|
||||
}
|
||||
|
||||
unawaited(
|
||||
showDialog<void>(
|
||||
context: context,
|
||||
barrierDismissible: true,
|
||||
builder: (_) => SimpleDesktopDialog(
|
||||
title: "Failed to create trade",
|
||||
message: response.exception?.toString() ?? ""),
|
||||
),
|
||||
);
|
||||
return;
|
||||
}
|
||||
|
||||
// save trade to hive
|
||||
await ref.read(tradesServiceProvider).add(
|
||||
trade: response.value!,
|
||||
shouldNotifyListeners: true,
|
||||
);
|
||||
|
||||
String status = response.value!.status;
|
||||
|
||||
model.trade = response.value!;
|
||||
|
||||
// extra info if status is waiting
|
||||
if (status == "Waiting") {
|
||||
status += " for deposit";
|
||||
}
|
||||
|
||||
if (mounted) {
|
||||
Navigator.of(context).pop();
|
||||
}
|
||||
|
||||
unawaited(
|
||||
NotificationApi.showNotification(
|
||||
changeNowId: model.trade!.tradeId,
|
||||
title: status,
|
||||
body: "Trade ID ${model.trade!.tradeId}",
|
||||
walletId: "",
|
||||
iconAssetName: Assets.svg.arrowRotate,
|
||||
date: model.trade!.timestamp,
|
||||
shouldWatchForUpdates: true,
|
||||
coinName: "coinName",
|
||||
),
|
||||
);
|
||||
|
||||
if (mounted) {
|
||||
unawaited(
|
||||
showDialog<void>(
|
||||
context: context,
|
||||
barrierColor: Colors.transparent,
|
||||
barrierDismissible: false,
|
||||
builder: (context) {
|
||||
return DesktopDialog(
|
||||
maxWidth: 720,
|
||||
maxHeight: double.infinity,
|
||||
child: StepScaffold(
|
||||
step: 4,
|
||||
model: model,
|
||||
body: DesktopStep4(
|
||||
model: model,
|
||||
),
|
||||
),
|
||||
);
|
||||
},
|
||||
),
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
@override
|
||||
void initState() {
|
||||
model = widget.model;
|
||||
super.initState();
|
||||
}
|
||||
|
||||
@override
|
||||
Widget build(BuildContext context) {
|
||||
return Column(
|
||||
|
@ -179,7 +45,7 @@ class _DesktopStep3State extends ConsumerState<DesktopStep3> {
|
|||
DesktopStepItem(
|
||||
label: "You send",
|
||||
value:
|
||||
"${model.sendAmount.toStringAsFixed(8)} ${model.sendTicker.toUpperCase()}",
|
||||
"${ref.watch(desktopExchangeModelProvider.select((value) => value!.sendAmount.toStringAsFixed(8)))} ${ref.watch(desktopExchangeModelProvider.select((value) => value!.sendTicker.toUpperCase()))}",
|
||||
),
|
||||
Container(
|
||||
height: 1,
|
||||
|
@ -188,17 +54,20 @@ class _DesktopStep3State extends ConsumerState<DesktopStep3> {
|
|||
DesktopStepItem(
|
||||
label: "You receive",
|
||||
value:
|
||||
"~${model.receiveAmount.toStringAsFixed(8)} ${model.receiveTicker.toUpperCase()}",
|
||||
"~${ref.watch(desktopExchangeModelProvider.select((value) => value!.receiveAmount.toStringAsFixed(8)))} ${ref.watch(desktopExchangeModelProvider.select((value) => value!.receiveTicker.toUpperCase()))}",
|
||||
),
|
||||
Container(
|
||||
height: 1,
|
||||
color: Theme.of(context).extension<StackColors>()!.background,
|
||||
),
|
||||
DesktopStepItem(
|
||||
label: model.rateType == ExchangeRateType.estimated
|
||||
label: ref.watch(desktopExchangeModelProvider
|
||||
.select((value) => value!.rateType)) ==
|
||||
ExchangeRateType.estimated
|
||||
? "Estimated rate"
|
||||
: "Fixed rate",
|
||||
value: model.rateInfo,
|
||||
value: ref.watch(desktopExchangeModelProvider
|
||||
.select((value) => value!.rateInfo)),
|
||||
),
|
||||
Container(
|
||||
height: 1,
|
||||
|
@ -206,8 +75,11 @@ class _DesktopStep3State extends ConsumerState<DesktopStep3> {
|
|||
),
|
||||
DesktopStepItem(
|
||||
vertical: true,
|
||||
label: "Recipient ${model.receiveTicker.toUpperCase()} address",
|
||||
value: model.recipientAddress!,
|
||||
label:
|
||||
"Recipient ${ref.watch(desktopExchangeModelProvider.select((value) => value!.receiveTicker.toUpperCase()))} address",
|
||||
value: ref.watch(desktopExchangeModelProvider
|
||||
.select((value) => value!.recipientAddress)) ??
|
||||
"Error",
|
||||
),
|
||||
Container(
|
||||
height: 1,
|
||||
|
@ -215,35 +87,11 @@ class _DesktopStep3State extends ConsumerState<DesktopStep3> {
|
|||
),
|
||||
DesktopStepItem(
|
||||
vertical: true,
|
||||
label: "Refund ${model.sendTicker.toUpperCase()} address",
|
||||
value: model.refundAddress!,
|
||||
),
|
||||
],
|
||||
),
|
||||
),
|
||||
Padding(
|
||||
padding: const EdgeInsets.only(
|
||||
top: 20,
|
||||
bottom: 32,
|
||||
),
|
||||
child: Row(
|
||||
children: [
|
||||
Expanded(
|
||||
child: SecondaryButton(
|
||||
label: "Back",
|
||||
buttonHeight: ButtonHeight.l,
|
||||
onPressed: Navigator.of(context).pop,
|
||||
),
|
||||
),
|
||||
const SizedBox(
|
||||
width: 16,
|
||||
),
|
||||
Expanded(
|
||||
child: PrimaryButton(
|
||||
label: "Confirm",
|
||||
buttonHeight: ButtonHeight.l,
|
||||
onPressed: createTrade,
|
||||
),
|
||||
label:
|
||||
"Refund ${ref.watch(desktopExchangeModelProvider.select((value) => value!.sendTicker.toUpperCase()))} address",
|
||||
value: ref.watch(desktopExchangeModelProvider
|
||||
.select((value) => value!.refundAddress)) ??
|
||||
"Error",
|
||||
),
|
||||
],
|
||||
),
|
||||
|
|
|
@ -1,38 +1,26 @@
|
|||
import 'dart:async';
|
||||
|
||||
import 'package:decimal/decimal.dart';
|
||||
import 'package:flutter/material.dart';
|
||||
import 'package:flutter_riverpod/flutter_riverpod.dart';
|
||||
import 'package:qr_flutter/qr_flutter.dart';
|
||||
import 'package:stackwallet/models/exchange/incomplete_exchange.dart';
|
||||
import 'package:stackwallet/pages/exchange_view/send_from_view.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/desktop_exchange/exchange_steps/step_scaffold.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/desktop_exchange/exchange_steps/subwidgets/desktop_step_item.dart';
|
||||
import 'package:stackwallet/providers/providers.dart';
|
||||
import 'package:stackwallet/route_generator.dart';
|
||||
import 'package:stackwallet/utilities/enums/coin_enum.dart';
|
||||
import 'package:stackwallet/utilities/text_styles.dart';
|
||||
import 'package:stackwallet/utilities/theme/stack_colors.dart';
|
||||
import 'package:stackwallet/widgets/desktop/desktop_dialog.dart';
|
||||
import 'package:stackwallet/widgets/desktop/primary_button.dart';
|
||||
import 'package:stackwallet/widgets/desktop/secondary_button.dart';
|
||||
import 'package:stackwallet/widgets/rounded_container.dart';
|
||||
import 'package:stackwallet/widgets/rounded_white_container.dart';
|
||||
|
||||
class DesktopStep4 extends ConsumerStatefulWidget {
|
||||
const DesktopStep4({
|
||||
Key? key,
|
||||
required this.model,
|
||||
}) : super(key: key);
|
||||
|
||||
final IncompleteExchangeModel model;
|
||||
|
||||
@override
|
||||
ConsumerState<DesktopStep4> createState() => _DesktopStep4State();
|
||||
}
|
||||
|
||||
class _DesktopStep4State extends ConsumerState<DesktopStep4> {
|
||||
late final IncompleteExchangeModel model;
|
||||
|
||||
String _statusString = "New";
|
||||
|
||||
Timer? _statusTimer;
|
||||
|
@ -51,8 +39,13 @@ class _DesktopStep4State extends ConsumerState<DesktopStep4> {
|
|||
}
|
||||
|
||||
Future<void> _updateStatus() async {
|
||||
final statusResponse =
|
||||
await ref.read(exchangeProvider).updateTrade(model.trade!);
|
||||
final trade = ref.read(desktopExchangeModelProvider)?.trade;
|
||||
|
||||
if (trade == null) {
|
||||
return;
|
||||
}
|
||||
|
||||
final statusResponse = await ref.read(exchangeProvider).updateTrade(trade);
|
||||
String status = "Waiting";
|
||||
if (statusResponse.value != null) {
|
||||
status = statusResponse.value!.status;
|
||||
|
@ -72,8 +65,6 @@ class _DesktopStep4State extends ConsumerState<DesktopStep4> {
|
|||
|
||||
@override
|
||||
void initState() {
|
||||
model = widget.model;
|
||||
|
||||
_statusTimer = Timer.periodic(const Duration(seconds: 60), (_) {
|
||||
_updateStatus();
|
||||
});
|
||||
|
@ -93,14 +84,14 @@ class _DesktopStep4State extends ConsumerState<DesktopStep4> {
|
|||
return Column(
|
||||
children: [
|
||||
Text(
|
||||
"Send ${model.sendTicker.toUpperCase()} to the address below",
|
||||
"Send ${ref.watch(desktopExchangeModelProvider.select((value) => value!.sendTicker.toUpperCase()))} to the address below",
|
||||
style: STextStyles.desktopTextMedium(context),
|
||||
),
|
||||
const SizedBox(
|
||||
height: 8,
|
||||
),
|
||||
Text(
|
||||
"Send ${model.sendTicker.toUpperCase()} to the address below. Once it is received, ${model.trade!.exchangeName} will send the ${model.receiveTicker.toUpperCase()} to the recipient address you provided. You can find this trade details and check its status in the list of trades.",
|
||||
"Send ${ref.watch(desktopExchangeModelProvider.select((value) => value!.sendTicker.toUpperCase()))} to the address below. Once it is received, ${ref.watch(desktopExchangeModelProvider.select((value) => value!.trade?.exchangeName))} will send the ${ref.watch(desktopExchangeModelProvider.select((value) => value!.receiveTicker.toUpperCase()))} to the recipient address you provided. You can find this trade details and check its status in the list of trades.",
|
||||
style: STextStyles.desktopTextExtraExtraSmall(context),
|
||||
),
|
||||
const SizedBox(
|
||||
|
@ -111,7 +102,7 @@ class _DesktopStep4State extends ConsumerState<DesktopStep4> {
|
|||
child: RichText(
|
||||
text: TextSpan(
|
||||
text:
|
||||
"You must send at least ${model.sendAmount.toString()} ${model.sendTicker}. ",
|
||||
"You must send at least ${ref.watch(desktopExchangeModelProvider.select((value) => value!.sendAmount.toString()))} ${ref.watch(desktopExchangeModelProvider.select((value) => value!.sendTicker))}. ",
|
||||
style: STextStyles.label700(context).copyWith(
|
||||
color: Theme.of(context)
|
||||
.extension<StackColors>()!
|
||||
|
@ -121,7 +112,7 @@ class _DesktopStep4State extends ConsumerState<DesktopStep4> {
|
|||
children: [
|
||||
TextSpan(
|
||||
text:
|
||||
"If you send less than ${model.sendAmount.toString()} ${model.sendTicker}, your transaction may not be converted and it may not be refunded.",
|
||||
"If you send less than ${ref.watch(desktopExchangeModelProvider.select((value) => value!.sendAmount.toString()))} ${ref.watch(desktopExchangeModelProvider.select((value) => value!.sendTicker))}, your transaction may not be converted and it may not be refunded.",
|
||||
style: STextStyles.label(context).copyWith(
|
||||
color: Theme.of(context)
|
||||
.extension<StackColors>()!
|
||||
|
@ -143,8 +134,11 @@ class _DesktopStep4State extends ConsumerState<DesktopStep4> {
|
|||
children: [
|
||||
DesktopStepItem(
|
||||
vertical: true,
|
||||
label: "Send ${model.sendTicker.toUpperCase()} to this address",
|
||||
value: model.trade!.payInAddress,
|
||||
label:
|
||||
"Send ${ref.watch(desktopExchangeModelProvider.select((value) => value!.sendTicker.toUpperCase()))} to this address",
|
||||
value: ref.watch(desktopExchangeModelProvider
|
||||
.select((value) => value!.trade?.payInAddress)) ??
|
||||
"Error",
|
||||
),
|
||||
Container(
|
||||
height: 1,
|
||||
|
@ -153,7 +147,7 @@ class _DesktopStep4State extends ConsumerState<DesktopStep4> {
|
|||
DesktopStepItem(
|
||||
label: "Amount",
|
||||
value:
|
||||
"${model.sendAmount.toStringAsFixed(8)} ${model.sendTicker.toUpperCase()}",
|
||||
"${ref.watch(desktopExchangeModelProvider.select((value) => value!.sendAmount.toStringAsFixed(8)))} ${ref.watch(desktopExchangeModelProvider.select((value) => value!.sendTicker.toUpperCase()))}",
|
||||
),
|
||||
Container(
|
||||
height: 1,
|
||||
|
@ -161,7 +155,9 @@ class _DesktopStep4State extends ConsumerState<DesktopStep4> {
|
|||
),
|
||||
DesktopStepItem(
|
||||
label: "Trade ID",
|
||||
value: model.trade!.tradeId,
|
||||
value: ref.watch(desktopExchangeModelProvider
|
||||
.select((value) => value!.trade?.tradeId)) ??
|
||||
"Error",
|
||||
),
|
||||
Container(
|
||||
height: 1,
|
||||
|
@ -191,110 +187,6 @@ class _DesktopStep4State extends ConsumerState<DesktopStep4> {
|
|||
],
|
||||
),
|
||||
),
|
||||
Padding(
|
||||
padding: const EdgeInsets.only(
|
||||
top: 20,
|
||||
bottom: 32,
|
||||
),
|
||||
child: Row(
|
||||
children: [
|
||||
Expanded(
|
||||
child: SecondaryButton(
|
||||
label: "Send from Stack Wallet",
|
||||
buttonHeight: ButtonHeight.l,
|
||||
onPressed: () {
|
||||
final trade = model.trade!;
|
||||
final amount = Decimal.parse(trade.payInAmount);
|
||||
final address = trade.payInAddress;
|
||||
|
||||
final coin =
|
||||
coinFromTickerCaseInsensitive(trade.payInCurrency);
|
||||
|
||||
showDialog<void>(
|
||||
context: context,
|
||||
builder: (context) => Navigator(
|
||||
initialRoute: SendFromView.routeName,
|
||||
onGenerateRoute: RouteGenerator.generateRoute,
|
||||
onGenerateInitialRoutes: (_, __) {
|
||||
return [
|
||||
FadePageRoute(
|
||||
SendFromView(
|
||||
coin: coin,
|
||||
trade: trade,
|
||||
amount: amount,
|
||||
address: address,
|
||||
shouldPopRoot: true,
|
||||
fromDesktopStep4: true,
|
||||
),
|
||||
const RouteSettings(
|
||||
name: SendFromView.routeName,
|
||||
),
|
||||
),
|
||||
];
|
||||
},
|
||||
),
|
||||
);
|
||||
},
|
||||
),
|
||||
),
|
||||
const SizedBox(
|
||||
width: 16,
|
||||
),
|
||||
Expanded(
|
||||
child: PrimaryButton(
|
||||
label: "Show QR code",
|
||||
buttonHeight: ButtonHeight.l,
|
||||
onPressed: () {
|
||||
showDialog<dynamic>(
|
||||
context: context,
|
||||
barrierColor: Colors.transparent,
|
||||
barrierDismissible: true,
|
||||
builder: (_) {
|
||||
return DesktopDialog(
|
||||
maxHeight: 720,
|
||||
maxWidth: 720,
|
||||
child: Column(
|
||||
mainAxisAlignment: MainAxisAlignment.center,
|
||||
crossAxisAlignment: CrossAxisAlignment.center,
|
||||
children: [
|
||||
Text(
|
||||
"Send ${model.sendAmount.toStringAsFixed(8)} ${model.sendTicker} to this address",
|
||||
style: STextStyles.desktopH3(context),
|
||||
),
|
||||
const SizedBox(
|
||||
height: 48,
|
||||
),
|
||||
Center(
|
||||
child: QrImage(
|
||||
// TODO: grab coin uri scheme from somewhere
|
||||
// data: "${coin.uriScheme}:$receivingAddress",
|
||||
data: model.trade!.payInAddress,
|
||||
size: 290,
|
||||
foregroundColor: Theme.of(context)
|
||||
.extension<StackColors>()!
|
||||
.accentColorDark,
|
||||
),
|
||||
),
|
||||
const SizedBox(
|
||||
height: 48,
|
||||
),
|
||||
SecondaryButton(
|
||||
label: "Cancel",
|
||||
width: 310,
|
||||
buttonHeight: ButtonHeight.l,
|
||||
onPressed: Navigator.of(context).pop,
|
||||
),
|
||||
],
|
||||
),
|
||||
);
|
||||
},
|
||||
);
|
||||
},
|
||||
),
|
||||
),
|
||||
],
|
||||
),
|
||||
),
|
||||
],
|
||||
);
|
||||
}
|
||||
|
|
|
@ -17,6 +17,7 @@ import 'package:stackwallet/widgets/rounded_white_container.dart';
|
|||
import 'package:stackwallet/widgets/stack_text_field.dart';
|
||||
import 'package:stackwallet/widgets/textfield_icon_button.dart';
|
||||
import 'package:stackwallet/widgets/wallet_info_row/sub_widgets/wallet_info_row_coin_icon.dart';
|
||||
import 'package:tuple/tuple.dart';
|
||||
|
||||
class DesktopChooseFromStack extends ConsumerStatefulWidget {
|
||||
const DesktopChooseFromStack({
|
||||
|
@ -222,8 +223,18 @@ class _DesktopChooseFromStackState
|
|||
),
|
||||
BlueTextButton(
|
||||
text: "Select wallet",
|
||||
onTap: () {
|
||||
Navigator.of(context).pop(manager.walletId);
|
||||
onTap: () async {
|
||||
final address =
|
||||
await manager.currentReceivingAddress;
|
||||
|
||||
if (mounted) {
|
||||
Navigator.of(context).pop(
|
||||
Tuple2(
|
||||
manager.walletName,
|
||||
address,
|
||||
),
|
||||
);
|
||||
}
|
||||
},
|
||||
),
|
||||
],
|
||||
|
|
|
@ -10,34 +10,58 @@ class DesktopExchangeStepsIndicator extends StatelessWidget {
|
|||
final int currentStep;
|
||||
|
||||
Color getColor(BuildContext context, int step) {
|
||||
if (currentStep > step) {
|
||||
if (currentStep >= step) {
|
||||
return Theme.of(context)
|
||||
.extension<StackColors>()!
|
||||
.accentColorBlue
|
||||
.withOpacity(0.5);
|
||||
} else if (currentStep < step) {
|
||||
return Theme.of(context).extension<StackColors>()!.textSubtitle3;
|
||||
} else {
|
||||
return Theme.of(context).extension<StackColors>()!.accentColorBlue;
|
||||
return Theme.of(context).extension<StackColors>()!.textSubtitle3;
|
||||
}
|
||||
}
|
||||
|
||||
static const double verticalSpacing = 6;
|
||||
static const double horizontalSpacing = 16;
|
||||
static const double barHeight = 4;
|
||||
static const double width = 152;
|
||||
static const double barWidth = 146;
|
||||
|
||||
static const Duration duration = Duration(milliseconds: 250);
|
||||
|
||||
@override
|
||||
Widget build(BuildContext context) {
|
||||
final double step = double.parse(currentStep.toString());
|
||||
final double dy = (step - 4) - (-(step - 4) * (horizontalSpacing / width));
|
||||
return Row(
|
||||
children: [
|
||||
Expanded(
|
||||
SizedBox(
|
||||
width: width,
|
||||
child: Column(
|
||||
children: [
|
||||
Text(
|
||||
"Confirm amount",
|
||||
style: STextStyles.desktopTextExtraExtraSmall(context).copyWith(
|
||||
color: getColor(context, 1),
|
||||
AnimatedCrossFade(
|
||||
firstChild: Text(
|
||||
"Confirm amount",
|
||||
style:
|
||||
STextStyles.desktopTextExtraExtraSmall(context).copyWith(
|
||||
color: Theme.of(context)
|
||||
.extension<StackColors>()!
|
||||
.accentColorBlue,
|
||||
),
|
||||
),
|
||||
secondChild: Text(
|
||||
"Confirm amount",
|
||||
style:
|
||||
STextStyles.desktopTextExtraExtraSmall(context).copyWith(
|
||||
color: Theme.of(context)
|
||||
.extension<StackColors>()!
|
||||
.accentColorBlue
|
||||
.withOpacity(0.5),
|
||||
),
|
||||
),
|
||||
crossFadeState: currentStep == 1
|
||||
? CrossFadeState.showFirst
|
||||
: CrossFadeState.showSecond,
|
||||
duration: duration,
|
||||
),
|
||||
const SizedBox(
|
||||
height: verticalSpacing,
|
||||
|
@ -53,14 +77,49 @@ class DesktopExchangeStepsIndicator extends StatelessWidget {
|
|||
const SizedBox(
|
||||
width: horizontalSpacing,
|
||||
),
|
||||
Expanded(
|
||||
SizedBox(
|
||||
width: width,
|
||||
child: Column(
|
||||
children: [
|
||||
Text(
|
||||
"Enter details",
|
||||
style: STextStyles.desktopTextExtraExtraSmall(context).copyWith(
|
||||
color: getColor(context, 2),
|
||||
AnimatedCrossFade(
|
||||
firstChild: Text(
|
||||
"Enter details",
|
||||
style:
|
||||
STextStyles.desktopTextExtraExtraSmall(context).copyWith(
|
||||
color: Theme.of(context)
|
||||
.extension<StackColors>()!
|
||||
.textSubtitle3,
|
||||
),
|
||||
),
|
||||
secondChild: AnimatedCrossFade(
|
||||
firstChild: Text(
|
||||
"Enter details",
|
||||
style: STextStyles.desktopTextExtraExtraSmall(context)
|
||||
.copyWith(
|
||||
color: Theme.of(context)
|
||||
.extension<StackColors>()!
|
||||
.accentColorBlue,
|
||||
),
|
||||
),
|
||||
secondChild: Text(
|
||||
"Enter details",
|
||||
style: STextStyles.desktopTextExtraExtraSmall(context)
|
||||
.copyWith(
|
||||
color: Theme.of(context)
|
||||
.extension<StackColors>()!
|
||||
.accentColorBlue
|
||||
.withOpacity(0.5),
|
||||
),
|
||||
),
|
||||
crossFadeState: currentStep == 2 && currentStep > 1
|
||||
? CrossFadeState.showFirst
|
||||
: CrossFadeState.showSecond,
|
||||
duration: duration,
|
||||
),
|
||||
crossFadeState: currentStep < 2
|
||||
? CrossFadeState.showFirst
|
||||
: CrossFadeState.showSecond,
|
||||
duration: duration,
|
||||
),
|
||||
const SizedBox(
|
||||
height: verticalSpacing,
|
||||
|
@ -76,14 +135,49 @@ class DesktopExchangeStepsIndicator extends StatelessWidget {
|
|||
const SizedBox(
|
||||
width: horizontalSpacing,
|
||||
),
|
||||
Expanded(
|
||||
SizedBox(
|
||||
width: width,
|
||||
child: Column(
|
||||
children: [
|
||||
Text(
|
||||
"Confirm details",
|
||||
style: STextStyles.desktopTextExtraExtraSmall(context).copyWith(
|
||||
color: getColor(context, 3),
|
||||
AnimatedCrossFade(
|
||||
firstChild: Text(
|
||||
"Confirm details",
|
||||
style:
|
||||
STextStyles.desktopTextExtraExtraSmall(context).copyWith(
|
||||
color: Theme.of(context)
|
||||
.extension<StackColors>()!
|
||||
.textSubtitle3,
|
||||
),
|
||||
),
|
||||
secondChild: AnimatedCrossFade(
|
||||
firstChild: Text(
|
||||
"Confirm details",
|
||||
style: STextStyles.desktopTextExtraExtraSmall(context)
|
||||
.copyWith(
|
||||
color: Theme.of(context)
|
||||
.extension<StackColors>()!
|
||||
.accentColorBlue,
|
||||
),
|
||||
),
|
||||
secondChild: Text(
|
||||
"Confirm details",
|
||||
style: STextStyles.desktopTextExtraExtraSmall(context)
|
||||
.copyWith(
|
||||
color: Theme.of(context)
|
||||
.extension<StackColors>()!
|
||||
.accentColorBlue
|
||||
.withOpacity(0.5),
|
||||
),
|
||||
),
|
||||
crossFadeState: currentStep == 3 && currentStep > 2
|
||||
? CrossFadeState.showFirst
|
||||
: CrossFadeState.showSecond,
|
||||
duration: duration,
|
||||
),
|
||||
crossFadeState: currentStep < 3
|
||||
? CrossFadeState.showFirst
|
||||
: CrossFadeState.showSecond,
|
||||
duration: duration,
|
||||
),
|
||||
const SizedBox(
|
||||
height: verticalSpacing,
|
||||
|
@ -99,22 +193,56 @@ class DesktopExchangeStepsIndicator extends StatelessWidget {
|
|||
const SizedBox(
|
||||
width: horizontalSpacing,
|
||||
),
|
||||
Expanded(
|
||||
SizedBox(
|
||||
width: width,
|
||||
child: Column(
|
||||
children: [
|
||||
Text(
|
||||
"Complete exchange",
|
||||
style: STextStyles.desktopTextExtraExtraSmall(context).copyWith(
|
||||
color: getColor(context, 4),
|
||||
AnimatedCrossFade(
|
||||
firstChild: Text(
|
||||
"Complete exchange",
|
||||
style:
|
||||
STextStyles.desktopTextExtraExtraSmall(context).copyWith(
|
||||
color: Theme.of(context)
|
||||
.extension<StackColors>()!
|
||||
.textSubtitle3,
|
||||
),
|
||||
),
|
||||
secondChild: Text(
|
||||
"Complete exchange",
|
||||
style:
|
||||
STextStyles.desktopTextExtraExtraSmall(context).copyWith(
|
||||
color: Theme.of(context)
|
||||
.extension<StackColors>()!
|
||||
.accentColorBlue,
|
||||
),
|
||||
),
|
||||
crossFadeState: currentStep < 4
|
||||
? CrossFadeState.showFirst
|
||||
: CrossFadeState.showSecond,
|
||||
duration: duration,
|
||||
),
|
||||
const SizedBox(
|
||||
height: verticalSpacing,
|
||||
),
|
||||
RoundedContainer(
|
||||
color: getColor(context, 4),
|
||||
height: barHeight,
|
||||
width: double.infinity,
|
||||
Stack(
|
||||
children: [
|
||||
RoundedContainer(
|
||||
color: getColor(context, 4),
|
||||
height: barHeight,
|
||||
width: double.infinity,
|
||||
),
|
||||
AnimatedSlide(
|
||||
offset: Offset(dy, 0),
|
||||
duration: duration,
|
||||
child: RoundedContainer(
|
||||
color: Theme.of(context)
|
||||
.extension<StackColors>()!
|
||||
.accentColorBlue,
|
||||
height: barHeight,
|
||||
width: double.infinity,
|
||||
),
|
||||
),
|
||||
],
|
||||
),
|
||||
],
|
||||
),
|
||||
|
|
|
@ -1,13 +1,13 @@
|
|||
import 'package:flutter/material.dart';
|
||||
import 'package:flutter_riverpod/flutter_riverpod.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/address_book_view/desktop_address_book.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/desktop_exchange/desktop_exchange_view.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/home/address_book_view/desktop_address_book.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/home/desktop_menu.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/home/desktop_settings_view.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/home/my_stack_view/my_stack_view.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/home/notifications/desktop_notifications_view.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/home/support_and_about_view/desktop_about_view.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/home/support_and_about_view/desktop_support_view.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/desktop_menu.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/my_stack_view/my_stack_view.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/notifications/desktop_notifications_view.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/settings/desktop_settings_view.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/settings/settings_menu/desktop_about_view.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/settings/settings_menu/desktop_support_view.dart';
|
||||
import 'package:stackwallet/providers/desktop/current_desktop_menu_item.dart';
|
||||
import 'package:stackwallet/providers/global/auto_swb_service_provider.dart';
|
||||
import 'package:stackwallet/providers/global/notifications_provider.dart';
|
||||
|
@ -32,13 +32,13 @@ class DesktopHomeView extends ConsumerStatefulWidget {
|
|||
}
|
||||
|
||||
class _DesktopHomeViewState extends ConsumerState<DesktopHomeView> {
|
||||
final GlobalKey key = GlobalKey<NavigatorState>();
|
||||
final GlobalKey myStackViewNavKey = GlobalKey<NavigatorState>();
|
||||
late final Navigator myStackViewNav;
|
||||
|
||||
@override
|
||||
void initState() {
|
||||
myStackViewNav = Navigator(
|
||||
key: key,
|
||||
key: myStackViewNavKey,
|
||||
onGenerateRoute: RouteGenerator.generateRoute,
|
||||
initialRoute: MyStackView.routeName,
|
||||
);
|
||||
|
@ -87,7 +87,7 @@ class _DesktopHomeViewState extends ConsumerState<DesktopHomeView> {
|
|||
|
||||
void onMenuSelectionWillChange(DesktopMenuItemId newKey) {
|
||||
if (prev == DesktopMenuItemId.myStack && prev == newKey) {
|
||||
Navigator.of(key.currentContext!)
|
||||
Navigator.of(myStackViewNavKey.currentContext!)
|
||||
.popUntil(ModalRoute.withName(MyStackView.routeName));
|
||||
if (ref.read(currentWalletIdProvider.state).state != null) {
|
||||
final managerProvider = ref
|
|
@ -3,7 +3,7 @@ import 'dart:io';
|
|||
import 'package:flutter/material.dart';
|
||||
import 'package:flutter_riverpod/flutter_riverpod.dart';
|
||||
import 'package:flutter_svg/flutter_svg.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/home/desktop_menu_item.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/desktop_menu_item.dart';
|
||||
import 'package:stackwallet/providers/desktop/current_desktop_menu_item.dart';
|
||||
import 'package:stackwallet/utilities/assets.dart';
|
||||
import 'package:stackwallet/utilities/text_styles.dart';
|
||||
|
@ -138,22 +138,7 @@ class _DesktopMenuState extends ConsumerState<DesktopMenu> {
|
|||
children: [
|
||||
DesktopMenuItem(
|
||||
duration: duration,
|
||||
icon: SvgPicture.asset(
|
||||
Assets.svg.walletDesktop,
|
||||
width: 20,
|
||||
height: 20,
|
||||
color: DesktopMenuItemId.myStack ==
|
||||
ref
|
||||
.watch(currentDesktopMenuItemProvider.state)
|
||||
.state
|
||||
? Theme.of(context)
|
||||
.extension<StackColors>()!
|
||||
.accentColorDark
|
||||
: Theme.of(context)
|
||||
.extension<StackColors>()!
|
||||
.accentColorDark
|
||||
.withOpacity(0.8),
|
||||
),
|
||||
icon: const DesktopMyStackIcon(),
|
||||
label: "My Stack",
|
||||
value: DesktopMenuItemId.myStack,
|
||||
onChanged: updateSelectedMenuItem,
|
||||
|
@ -164,22 +149,7 @@ class _DesktopMenuState extends ConsumerState<DesktopMenu> {
|
|||
),
|
||||
DesktopMenuItem(
|
||||
duration: duration,
|
||||
icon: SvgPicture.asset(
|
||||
Assets.svg.exchangeDesktop,
|
||||
width: 20,
|
||||
height: 20,
|
||||
color: DesktopMenuItemId.exchange ==
|
||||
ref
|
||||
.watch(currentDesktopMenuItemProvider.state)
|
||||
.state
|
||||
? Theme.of(context)
|
||||
.extension<StackColors>()!
|
||||
.accentColorDark
|
||||
: Theme.of(context)
|
||||
.extension<StackColors>()!
|
||||
.accentColorDark
|
||||
.withOpacity(0.8),
|
||||
),
|
||||
icon: const DesktopExchangeIcon(),
|
||||
label: "Exchange",
|
||||
value: DesktopMenuItemId.exchange,
|
||||
onChanged: updateSelectedMenuItem,
|
||||
|
@ -201,22 +171,7 @@ class _DesktopMenuState extends ConsumerState<DesktopMenu> {
|
|||
),
|
||||
DesktopMenuItem(
|
||||
duration: duration,
|
||||
icon: SvgPicture.asset(
|
||||
Assets.svg.addressBookDesktop,
|
||||
width: 20,
|
||||
height: 20,
|
||||
color: DesktopMenuItemId.addressBook ==
|
||||
ref
|
||||
.watch(currentDesktopMenuItemProvider.state)
|
||||
.state
|
||||
? Theme.of(context)
|
||||
.extension<StackColors>()!
|
||||
.accentColorDark
|
||||
: Theme.of(context)
|
||||
.extension<StackColors>()!
|
||||
.accentColorDark
|
||||
.withOpacity(0.8),
|
||||
),
|
||||
icon: const DesktopAddressBookIcon(),
|
||||
label: "Address Book",
|
||||
value: DesktopMenuItemId.addressBook,
|
||||
onChanged: updateSelectedMenuItem,
|
||||
|
@ -227,22 +182,7 @@ class _DesktopMenuState extends ConsumerState<DesktopMenu> {
|
|||
),
|
||||
DesktopMenuItem(
|
||||
duration: duration,
|
||||
icon: SvgPicture.asset(
|
||||
Assets.svg.gear,
|
||||
width: 20,
|
||||
height: 20,
|
||||
color: DesktopMenuItemId.settings ==
|
||||
ref
|
||||
.watch(currentDesktopMenuItemProvider.state)
|
||||
.state
|
||||
? Theme.of(context)
|
||||
.extension<StackColors>()!
|
||||
.accentColorDark
|
||||
: Theme.of(context)
|
||||
.extension<StackColors>()!
|
||||
.accentColorDark
|
||||
.withOpacity(0.8),
|
||||
),
|
||||
icon: const DesktopSettingsIcon(),
|
||||
label: "Settings",
|
||||
value: DesktopMenuItemId.settings,
|
||||
onChanged: updateSelectedMenuItem,
|
||||
|
@ -253,22 +193,7 @@ class _DesktopMenuState extends ConsumerState<DesktopMenu> {
|
|||
),
|
||||
DesktopMenuItem(
|
||||
duration: duration,
|
||||
icon: SvgPicture.asset(
|
||||
Assets.svg.messageQuestion,
|
||||
width: 20,
|
||||
height: 20,
|
||||
color: DesktopMenuItemId.support ==
|
||||
ref
|
||||
.watch(currentDesktopMenuItemProvider.state)
|
||||
.state
|
||||
? Theme.of(context)
|
||||
.extension<StackColors>()!
|
||||
.accentColorDark
|
||||
: Theme.of(context)
|
||||
.extension<StackColors>()!
|
||||
.accentColorDark
|
||||
.withOpacity(0.8),
|
||||
),
|
||||
icon: const DesktopSupportIcon(),
|
||||
label: "Support",
|
||||
value: DesktopMenuItemId.support,
|
||||
onChanged: updateSelectedMenuItem,
|
||||
|
@ -279,22 +204,7 @@ class _DesktopMenuState extends ConsumerState<DesktopMenu> {
|
|||
),
|
||||
DesktopMenuItem(
|
||||
duration: duration,
|
||||
icon: SvgPicture.asset(
|
||||
Assets.svg.aboutDesktop,
|
||||
width: 20,
|
||||
height: 20,
|
||||
color: DesktopMenuItemId.about ==
|
||||
ref
|
||||
.watch(currentDesktopMenuItemProvider.state)
|
||||
.state
|
||||
? Theme.of(context)
|
||||
.extension<StackColors>()!
|
||||
.accentColorDark
|
||||
: Theme.of(context)
|
||||
.extension<StackColors>()!
|
||||
.accentColorDark
|
||||
.withOpacity(0.8),
|
||||
),
|
||||
icon: const DesktopAboutIcon(),
|
||||
label: "About",
|
||||
value: DesktopMenuItemId.about,
|
||||
onChanged: updateSelectedMenuItem,
|
||||
|
@ -304,15 +214,7 @@ class _DesktopMenuState extends ConsumerState<DesktopMenu> {
|
|||
DesktopMenuItem(
|
||||
duration: duration,
|
||||
labelLength: 123,
|
||||
icon: SvgPicture.asset(
|
||||
Assets.svg.exitDesktop,
|
||||
width: 20,
|
||||
height: 20,
|
||||
color: Theme.of(context)
|
||||
.extension<StackColors>()!
|
||||
.accentColorDark
|
||||
.withOpacity(0.8),
|
||||
),
|
||||
icon: const DesktopExitIcon(),
|
||||
label: "Exit",
|
||||
value: 7,
|
||||
onChanged: (_) {
|
|
@ -1,7 +1,7 @@
|
|||
import 'package:flutter/material.dart';
|
||||
import 'package:flutter_riverpod/flutter_riverpod.dart';
|
||||
import 'package:flutter_svg/svg.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/home/desktop_menu.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/desktop_menu.dart';
|
||||
import 'package:stackwallet/providers/desktop/current_desktop_menu_item.dart';
|
||||
import 'package:stackwallet/providers/global/notifications_provider.dart';
|
||||
import 'package:stackwallet/utilities/assets.dart';
|
||||
|
@ -15,18 +15,51 @@ class DMIController {
|
|||
}
|
||||
}
|
||||
|
||||
class DesktopNotificationsIcon extends ConsumerStatefulWidget {
|
||||
class DesktopMyStackIcon extends ConsumerWidget {
|
||||
const DesktopMyStackIcon({Key? key}) : super(key: key);
|
||||
|
||||
@override
|
||||
Widget build(BuildContext context, WidgetRef ref) {
|
||||
return SvgPicture.asset(
|
||||
Assets.svg.walletDesktop,
|
||||
width: 20,
|
||||
height: 20,
|
||||
color: DesktopMenuItemId.myStack ==
|
||||
ref.watch(currentDesktopMenuItemProvider.state).state
|
||||
? Theme.of(context).extension<StackColors>()!.accentColorDark
|
||||
: Theme.of(context)
|
||||
.extension<StackColors>()!
|
||||
.accentColorDark
|
||||
.withOpacity(0.8),
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
class DesktopExchangeIcon extends ConsumerWidget {
|
||||
const DesktopExchangeIcon({Key? key}) : super(key: key);
|
||||
|
||||
@override
|
||||
Widget build(BuildContext context, WidgetRef ref) {
|
||||
return SvgPicture.asset(
|
||||
Assets.svg.exchangeDesktop,
|
||||
width: 20,
|
||||
height: 20,
|
||||
color: DesktopMenuItemId.exchange ==
|
||||
ref.watch(currentDesktopMenuItemProvider.state).state
|
||||
? Theme.of(context).extension<StackColors>()!.accentColorDark
|
||||
: Theme.of(context)
|
||||
.extension<StackColors>()!
|
||||
.accentColorDark
|
||||
.withOpacity(0.8),
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
class DesktopNotificationsIcon extends ConsumerWidget {
|
||||
const DesktopNotificationsIcon({Key? key}) : super(key: key);
|
||||
|
||||
@override
|
||||
ConsumerState<DesktopNotificationsIcon> createState() =>
|
||||
_DesktopNotificationsIconState();
|
||||
}
|
||||
|
||||
class _DesktopNotificationsIconState
|
||||
extends ConsumerState<DesktopNotificationsIcon> {
|
||||
@override
|
||||
Widget build(BuildContext context) {
|
||||
Widget build(BuildContext context, WidgetRef ref) {
|
||||
return SvgPicture.asset(
|
||||
ref.watch(notificationsProvider
|
||||
.select((value) => value.hasUnreadNotifications))
|
||||
|
@ -48,6 +81,103 @@ class _DesktopNotificationsIconState
|
|||
}
|
||||
}
|
||||
|
||||
class DesktopAddressBookIcon extends ConsumerWidget {
|
||||
const DesktopAddressBookIcon({Key? key}) : super(key: key);
|
||||
|
||||
@override
|
||||
Widget build(BuildContext context, WidgetRef ref) {
|
||||
return SvgPicture.asset(
|
||||
Assets.svg.addressBookDesktop,
|
||||
width: 20,
|
||||
height: 20,
|
||||
color: DesktopMenuItemId.addressBook ==
|
||||
ref.watch(currentDesktopMenuItemProvider.state).state
|
||||
? Theme.of(context).extension<StackColors>()!.accentColorDark
|
||||
: Theme.of(context)
|
||||
.extension<StackColors>()!
|
||||
.accentColorDark
|
||||
.withOpacity(0.8),
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
class DesktopSettingsIcon extends ConsumerWidget {
|
||||
const DesktopSettingsIcon({Key? key}) : super(key: key);
|
||||
|
||||
@override
|
||||
Widget build(BuildContext context, WidgetRef ref) {
|
||||
return SvgPicture.asset(
|
||||
Assets.svg.gear,
|
||||
width: 20,
|
||||
height: 20,
|
||||
color: DesktopMenuItemId.settings ==
|
||||
ref.watch(currentDesktopMenuItemProvider.state).state
|
||||
? Theme.of(context).extension<StackColors>()!.accentColorDark
|
||||
: Theme.of(context)
|
||||
.extension<StackColors>()!
|
||||
.accentColorDark
|
||||
.withOpacity(0.8),
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
class DesktopSupportIcon extends ConsumerWidget {
|
||||
const DesktopSupportIcon({Key? key}) : super(key: key);
|
||||
|
||||
@override
|
||||
Widget build(BuildContext context, WidgetRef ref) {
|
||||
return SvgPicture.asset(
|
||||
Assets.svg.messageQuestion,
|
||||
width: 20,
|
||||
height: 20,
|
||||
color: DesktopMenuItemId.support ==
|
||||
ref.watch(currentDesktopMenuItemProvider.state).state
|
||||
? Theme.of(context).extension<StackColors>()!.accentColorDark
|
||||
: Theme.of(context)
|
||||
.extension<StackColors>()!
|
||||
.accentColorDark
|
||||
.withOpacity(0.8),
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
class DesktopAboutIcon extends ConsumerWidget {
|
||||
const DesktopAboutIcon({Key? key}) : super(key: key);
|
||||
|
||||
@override
|
||||
Widget build(BuildContext context, WidgetRef ref) {
|
||||
return SvgPicture.asset(
|
||||
Assets.svg.aboutDesktop,
|
||||
width: 20,
|
||||
height: 20,
|
||||
color: DesktopMenuItemId.about ==
|
||||
ref.watch(currentDesktopMenuItemProvider.state).state
|
||||
? Theme.of(context).extension<StackColors>()!.accentColorDark
|
||||
: Theme.of(context)
|
||||
.extension<StackColors>()!
|
||||
.accentColorDark
|
||||
.withOpacity(0.8),
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
class DesktopExitIcon extends ConsumerWidget {
|
||||
const DesktopExitIcon({Key? key}) : super(key: key);
|
||||
|
||||
@override
|
||||
Widget build(BuildContext context, WidgetRef ref) {
|
||||
return SvgPicture.asset(
|
||||
Assets.svg.exitDesktop,
|
||||
width: 20,
|
||||
height: 20,
|
||||
color: Theme.of(context)
|
||||
.extension<StackColors>()!
|
||||
.accentColorDark
|
||||
.withOpacity(0.8),
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
class DesktopMenuItem<T> extends ConsumerStatefulWidget {
|
||||
const DesktopMenuItem({
|
||||
Key? key,
|
||||
|
@ -127,7 +257,7 @@ class _DesktopMenuItemState<T> extends ConsumerState<DesktopMenuItem<T>>
|
|||
@override
|
||||
Widget build(BuildContext context) {
|
||||
final group = ref.watch(currentDesktopMenuItemProvider.state).state;
|
||||
debugPrint("============ value:$value ============ group:$group");
|
||||
|
||||
return TextButton(
|
||||
style: value == group
|
||||
? Theme.of(context)
|
|
@ -1,136 +0,0 @@
|
|||
import 'package:flutter/material.dart';
|
||||
import 'package:stackwallet/utilities/text_styles.dart';
|
||||
import 'package:stackwallet/utilities/theme/stack_colors.dart';
|
||||
|
||||
class SendReceiveTabMenu extends StatefulWidget {
|
||||
const SendReceiveTabMenu({
|
||||
Key? key,
|
||||
this.initialIndex = 0,
|
||||
this.onChanged,
|
||||
}) : super(key: key);
|
||||
|
||||
final int initialIndex;
|
||||
final void Function(int)? onChanged;
|
||||
|
||||
@override
|
||||
State<SendReceiveTabMenu> createState() => _SendReceiveTabMenuState();
|
||||
}
|
||||
|
||||
class _SendReceiveTabMenuState extends State<SendReceiveTabMenu> {
|
||||
late int _selectedIndex;
|
||||
|
||||
void _onChanged(int newIndex) {
|
||||
if (_selectedIndex != newIndex) {
|
||||
setState(() {
|
||||
_selectedIndex = newIndex;
|
||||
});
|
||||
widget.onChanged?.call(_selectedIndex);
|
||||
}
|
||||
}
|
||||
|
||||
@override
|
||||
void initState() {
|
||||
_selectedIndex = widget.initialIndex;
|
||||
super.initState();
|
||||
}
|
||||
|
||||
@override
|
||||
Widget build(BuildContext context) {
|
||||
return Row(
|
||||
children: [
|
||||
Expanded(
|
||||
child: MouseRegion(
|
||||
cursor: SystemMouseCursors.click,
|
||||
child: GestureDetector(
|
||||
onTap: () => _onChanged(0),
|
||||
child: Container(
|
||||
color: Colors.transparent,
|
||||
child: Column(
|
||||
children: [
|
||||
const SizedBox(
|
||||
height: 16,
|
||||
),
|
||||
Text(
|
||||
"Send",
|
||||
style:
|
||||
STextStyles.desktopTextExtraSmall(context).copyWith(
|
||||
color: _selectedIndex == 0
|
||||
? Theme.of(context)
|
||||
.extension<StackColors>()!
|
||||
.accentColorBlue
|
||||
: Theme.of(context)
|
||||
.extension<StackColors>()!
|
||||
.textSubtitle1,
|
||||
),
|
||||
),
|
||||
const SizedBox(
|
||||
height: 19,
|
||||
),
|
||||
Container(
|
||||
height: 2,
|
||||
decoration: BoxDecoration(
|
||||
color: _selectedIndex == 0
|
||||
? Theme.of(context)
|
||||
.extension<StackColors>()!
|
||||
.accentColorBlue
|
||||
: Theme.of(context)
|
||||
.extension<StackColors>()!
|
||||
.background,
|
||||
),
|
||||
),
|
||||
],
|
||||
),
|
||||
),
|
||||
),
|
||||
),
|
||||
),
|
||||
Expanded(
|
||||
child: MouseRegion(
|
||||
cursor: SystemMouseCursors.click,
|
||||
child: GestureDetector(
|
||||
onTap: () => _onChanged(1),
|
||||
child: Container(
|
||||
color: Colors.transparent,
|
||||
child: Column(
|
||||
children: [
|
||||
const SizedBox(
|
||||
height: 16,
|
||||
),
|
||||
Text(
|
||||
"Receive",
|
||||
style:
|
||||
STextStyles.desktopTextExtraSmall(context).copyWith(
|
||||
color: _selectedIndex == 1
|
||||
? Theme.of(context)
|
||||
.extension<StackColors>()!
|
||||
.accentColorBlue
|
||||
: Theme.of(context)
|
||||
.extension<StackColors>()!
|
||||
.textSubtitle1,
|
||||
),
|
||||
),
|
||||
const SizedBox(
|
||||
height: 19,
|
||||
),
|
||||
Container(
|
||||
height: 2,
|
||||
decoration: BoxDecoration(
|
||||
color: _selectedIndex == 1
|
||||
? Theme.of(context)
|
||||
.extension<StackColors>()!
|
||||
.accentColorBlue
|
||||
: Theme.of(context)
|
||||
.extension<StackColors>()!
|
||||
.background,
|
||||
),
|
||||
),
|
||||
],
|
||||
),
|
||||
),
|
||||
),
|
||||
),
|
||||
),
|
||||
],
|
||||
);
|
||||
}
|
||||
}
|
|
@ -1,501 +0,0 @@
|
|||
import 'package:flutter/material.dart';
|
||||
import 'package:flutter_riverpod/flutter_riverpod.dart';
|
||||
import 'package:flutter_svg/svg.dart';
|
||||
import 'package:stackwallet/hive/db.dart';
|
||||
import 'package:stackwallet/providers/global/prefs_provider.dart';
|
||||
import 'package:stackwallet/providers/ui/color_theme_provider.dart';
|
||||
import 'package:stackwallet/utilities/assets.dart';
|
||||
import 'package:stackwallet/utilities/constants.dart';
|
||||
import 'package:stackwallet/utilities/text_styles.dart';
|
||||
import 'package:stackwallet/utilities/theme/color_theme.dart';
|
||||
import 'package:stackwallet/utilities/theme/dark_colors.dart';
|
||||
import 'package:stackwallet/utilities/theme/light_colors.dart';
|
||||
import 'package:stackwallet/utilities/theme/ocean_breeze_colors.dart';
|
||||
import 'package:stackwallet/utilities/theme/stack_colors.dart';
|
||||
import 'package:stackwallet/widgets/custom_buttons/draggable_switch_button.dart';
|
||||
import 'package:stackwallet/widgets/rounded_white_container.dart';
|
||||
|
||||
class AppearanceOptionSettings extends ConsumerStatefulWidget {
|
||||
const AppearanceOptionSettings({Key? key}) : super(key: key);
|
||||
|
||||
static const String routeName = "/settingsMenuAppearance";
|
||||
|
||||
@override
|
||||
ConsumerState<AppearanceOptionSettings> createState() =>
|
||||
_AppearanceOptionSettings();
|
||||
}
|
||||
|
||||
class _AppearanceOptionSettings
|
||||
extends ConsumerState<AppearanceOptionSettings> {
|
||||
// late bool isLight;
|
||||
|
||||
// @override
|
||||
// void initState() {
|
||||
//
|
||||
// super.initState();
|
||||
// }
|
||||
//
|
||||
// @override
|
||||
// void dispose() {
|
||||
// super.dispose();
|
||||
// }
|
||||
|
||||
@override
|
||||
Widget build(BuildContext context) {
|
||||
debugPrint("BUILD: $runtimeType");
|
||||
return Column(
|
||||
children: [
|
||||
Padding(
|
||||
padding: const EdgeInsets.only(
|
||||
right: 30,
|
||||
),
|
||||
child: RoundedWhiteContainer(
|
||||
radiusMultiplier: 2,
|
||||
child: Column(
|
||||
crossAxisAlignment: CrossAxisAlignment.start,
|
||||
children: [
|
||||
Padding(
|
||||
padding: const EdgeInsets.all(8.0),
|
||||
child: SvgPicture.asset(
|
||||
Assets.svg.circleSun,
|
||||
width: 48,
|
||||
height: 48,
|
||||
),
|
||||
),
|
||||
Column(
|
||||
crossAxisAlignment: CrossAxisAlignment.stretch,
|
||||
children: [
|
||||
Padding(
|
||||
padding: const EdgeInsets.all(10),
|
||||
child: RichText(
|
||||
textAlign: TextAlign.left,
|
||||
text: TextSpan(
|
||||
children: [
|
||||
TextSpan(
|
||||
text: "Appearances",
|
||||
style: STextStyles.desktopTextSmall(context),
|
||||
),
|
||||
TextSpan(
|
||||
text:
|
||||
"\n\nCustomize how your Stack Wallet looks according to your preferences.",
|
||||
style: STextStyles.desktopTextExtraExtraSmall(
|
||||
context),
|
||||
),
|
||||
],
|
||||
),
|
||||
),
|
||||
),
|
||||
],
|
||||
),
|
||||
const Padding(
|
||||
padding: EdgeInsets.all(10.0),
|
||||
child: Divider(
|
||||
thickness: 0.5,
|
||||
),
|
||||
),
|
||||
Padding(
|
||||
padding: const EdgeInsets.all(10.0),
|
||||
child: Row(
|
||||
mainAxisAlignment: MainAxisAlignment.spaceBetween,
|
||||
children: [
|
||||
Text(
|
||||
"Display favorite wallets",
|
||||
style: STextStyles.desktopTextExtraSmall(context)
|
||||
.copyWith(
|
||||
color: Theme.of(context)
|
||||
.extension<StackColors>()!
|
||||
.textDark),
|
||||
textAlign: TextAlign.left,
|
||||
),
|
||||
SizedBox(
|
||||
height: 20,
|
||||
width: 40,
|
||||
child: DraggableSwitchButton(
|
||||
isOn: ref.watch(
|
||||
prefsChangeNotifierProvider
|
||||
.select((value) => value.showFavoriteWallets),
|
||||
),
|
||||
onValueChanged: (newValue) {
|
||||
ref
|
||||
.read(prefsChangeNotifierProvider)
|
||||
.showFavoriteWallets = newValue;
|
||||
},
|
||||
),
|
||||
)
|
||||
],
|
||||
),
|
||||
),
|
||||
const Padding(
|
||||
padding: EdgeInsets.all(10.0),
|
||||
child: Divider(
|
||||
thickness: 0.5,
|
||||
),
|
||||
),
|
||||
Padding(
|
||||
padding: const EdgeInsets.all(10.0),
|
||||
child: Row(
|
||||
mainAxisAlignment: MainAxisAlignment.spaceBetween,
|
||||
children: [
|
||||
Text(
|
||||
"Choose theme",
|
||||
style: STextStyles.desktopTextExtraSmall(context)
|
||||
.copyWith(
|
||||
color: Theme.of(context)
|
||||
.extension<StackColors>()!
|
||||
.textDark),
|
||||
textAlign: TextAlign.left,
|
||||
),
|
||||
],
|
||||
),
|
||||
),
|
||||
const Padding(
|
||||
padding: EdgeInsets.all(10),
|
||||
child: ThemeToggle(),
|
||||
),
|
||||
],
|
||||
),
|
||||
),
|
||||
),
|
||||
],
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
class ThemeToggle extends ConsumerStatefulWidget {
|
||||
const ThemeToggle({
|
||||
Key? key,
|
||||
}) : super(key: key);
|
||||
|
||||
// final bool externalCallsEnabled;
|
||||
// final void Function(bool)? onChanged;
|
||||
|
||||
@override
|
||||
ConsumerState<ThemeToggle> createState() => _ThemeToggle();
|
||||
}
|
||||
|
||||
class _ThemeToggle extends ConsumerState<ThemeToggle> {
|
||||
// late bool externalCallsEnabled;
|
||||
|
||||
late String _selectedTheme;
|
||||
|
||||
@override
|
||||
void initState() {
|
||||
_selectedTheme =
|
||||
DB.instance.get<dynamic>(boxName: DB.boxNameTheme, key: "colorScheme")
|
||||
as String? ??
|
||||
"light";
|
||||
|
||||
super.initState();
|
||||
}
|
||||
|
||||
@override
|
||||
Widget build(BuildContext context) {
|
||||
return Row(
|
||||
children: [
|
||||
MaterialButton(
|
||||
splashColor: Colors.transparent,
|
||||
hoverColor: Colors.transparent,
|
||||
padding: const EdgeInsets.all(0),
|
||||
materialTapTargetSize: MaterialTapTargetSize.shrinkWrap,
|
||||
shape: RoundedRectangleBorder(
|
||||
borderRadius: BorderRadius.circular(
|
||||
Constants.size.circularBorderRadius,
|
||||
),
|
||||
),
|
||||
onPressed: () {
|
||||
DB.instance.put<dynamic>(
|
||||
boxName: DB.boxNameTheme,
|
||||
key: "colorScheme",
|
||||
value: ThemeType.light.name,
|
||||
);
|
||||
ref.read(colorThemeProvider.state).state =
|
||||
StackColors.fromStackColorTheme(
|
||||
LightColors(),
|
||||
);
|
||||
|
||||
setState(() {
|
||||
_selectedTheme = "light";
|
||||
});
|
||||
},
|
||||
child: SizedBox(
|
||||
width: 200,
|
||||
child: Column(
|
||||
mainAxisSize: MainAxisSize.min,
|
||||
children: [
|
||||
Container(
|
||||
decoration: BoxDecoration(
|
||||
border: Border.all(
|
||||
width: 2.5,
|
||||
color: _selectedTheme == "light"
|
||||
? Theme.of(context)
|
||||
.extension<StackColors>()!
|
||||
.infoItemIcons
|
||||
: Theme.of(context).extension<StackColors>()!.popupBG,
|
||||
),
|
||||
borderRadius: BorderRadius.circular(
|
||||
Constants.size.circularBorderRadius,
|
||||
),
|
||||
),
|
||||
child: SvgPicture.asset(
|
||||
Assets.svg.themeLight,
|
||||
),
|
||||
),
|
||||
const SizedBox(
|
||||
height: 12,
|
||||
),
|
||||
Row(
|
||||
children: [
|
||||
SizedBox(
|
||||
width: 20,
|
||||
height: 20,
|
||||
child: Radio(
|
||||
activeColor: Theme.of(context)
|
||||
.extension<StackColors>()!
|
||||
.radioButtonIconEnabled,
|
||||
value: "light",
|
||||
groupValue: _selectedTheme,
|
||||
onChanged: (newValue) {
|
||||
if (newValue is String && newValue == "light") {
|
||||
DB.instance.put<dynamic>(
|
||||
boxName: DB.boxNameTheme,
|
||||
key: "colorScheme",
|
||||
value: ThemeType.light.name,
|
||||
);
|
||||
ref.read(colorThemeProvider.state).state =
|
||||
StackColors.fromStackColorTheme(
|
||||
LightColors(),
|
||||
);
|
||||
|
||||
setState(() {
|
||||
_selectedTheme = "light";
|
||||
});
|
||||
}
|
||||
},
|
||||
),
|
||||
),
|
||||
const SizedBox(
|
||||
width: 14,
|
||||
),
|
||||
Text(
|
||||
"Light",
|
||||
style:
|
||||
STextStyles.desktopTextExtraSmall(context).copyWith(
|
||||
color: Theme.of(context)
|
||||
.extension<StackColors>()!
|
||||
.textDark,
|
||||
),
|
||||
),
|
||||
],
|
||||
),
|
||||
],
|
||||
),
|
||||
),
|
||||
),
|
||||
const SizedBox(
|
||||
width: 10,
|
||||
),
|
||||
MaterialButton(
|
||||
splashColor: Colors.transparent,
|
||||
hoverColor: Colors.transparent,
|
||||
padding: const EdgeInsets.all(0),
|
||||
materialTapTargetSize: MaterialTapTargetSize.shrinkWrap,
|
||||
shape: RoundedRectangleBorder(
|
||||
borderRadius: BorderRadius.circular(
|
||||
Constants.size.circularBorderRadius,
|
||||
),
|
||||
),
|
||||
onPressed: () {
|
||||
DB.instance.put<dynamic>(
|
||||
boxName: DB.boxNameTheme,
|
||||
key: "colorScheme",
|
||||
value: ThemeType.oceanBreeze.name,
|
||||
);
|
||||
ref.read(colorThemeProvider.state).state =
|
||||
StackColors.fromStackColorTheme(
|
||||
OceanBreezeColors(),
|
||||
);
|
||||
|
||||
setState(() {
|
||||
_selectedTheme = "oceanBreeze";
|
||||
});
|
||||
},
|
||||
child: SizedBox(
|
||||
width: 200,
|
||||
child: Column(
|
||||
mainAxisSize: MainAxisSize.min,
|
||||
children: [
|
||||
Container(
|
||||
decoration: BoxDecoration(
|
||||
border: Border.all(
|
||||
width: 2.5,
|
||||
color: _selectedTheme == "oceanBreeze"
|
||||
? Theme.of(context)
|
||||
.extension<StackColors>()!
|
||||
.infoItemIcons
|
||||
: Theme.of(context).extension<StackColors>()!.popupBG,
|
||||
),
|
||||
borderRadius: BorderRadius.circular(
|
||||
Constants.size.circularBorderRadius,
|
||||
),
|
||||
),
|
||||
child: SvgPicture.asset(
|
||||
Assets.svg.themeOcean,
|
||||
),
|
||||
),
|
||||
const SizedBox(
|
||||
height: 12,
|
||||
),
|
||||
Row(
|
||||
children: [
|
||||
SizedBox(
|
||||
width: 20,
|
||||
height: 20,
|
||||
child: Radio(
|
||||
activeColor: Theme.of(context)
|
||||
.extension<StackColors>()!
|
||||
.radioButtonIconEnabled,
|
||||
value: "oceanBreeze",
|
||||
groupValue: _selectedTheme,
|
||||
onChanged: (newValue) {
|
||||
if (newValue is String && newValue == "oceanBreeze") {
|
||||
DB.instance.put<dynamic>(
|
||||
boxName: DB.boxNameTheme,
|
||||
key: "colorScheme",
|
||||
value: ThemeType.oceanBreeze.name,
|
||||
);
|
||||
ref.read(colorThemeProvider.state).state =
|
||||
StackColors.fromStackColorTheme(
|
||||
OceanBreezeColors(),
|
||||
);
|
||||
|
||||
setState(() {
|
||||
_selectedTheme = "oceanBreeze";
|
||||
});
|
||||
}
|
||||
},
|
||||
),
|
||||
),
|
||||
const SizedBox(
|
||||
width: 14,
|
||||
),
|
||||
Text(
|
||||
"Ocean Breeze",
|
||||
style:
|
||||
STextStyles.desktopTextExtraSmall(context).copyWith(
|
||||
color: Theme.of(context)
|
||||
.extension<StackColors>()!
|
||||
.textDark,
|
||||
),
|
||||
),
|
||||
],
|
||||
),
|
||||
],
|
||||
),
|
||||
),
|
||||
),
|
||||
const SizedBox(
|
||||
width: 10,
|
||||
),
|
||||
MaterialButton(
|
||||
splashColor: Colors.transparent,
|
||||
hoverColor: Colors.transparent,
|
||||
padding: const EdgeInsets.all(0),
|
||||
materialTapTargetSize: MaterialTapTargetSize.shrinkWrap,
|
||||
shape: RoundedRectangleBorder(
|
||||
borderRadius: BorderRadius.circular(
|
||||
Constants.size.circularBorderRadius,
|
||||
),
|
||||
),
|
||||
onPressed: () {
|
||||
DB.instance.put<dynamic>(
|
||||
boxName: DB.boxNameTheme,
|
||||
key: "colorScheme",
|
||||
value: ThemeType.dark.name,
|
||||
);
|
||||
ref.read(colorThemeProvider.state).state =
|
||||
StackColors.fromStackColorTheme(
|
||||
DarkColors(),
|
||||
);
|
||||
|
||||
setState(() {
|
||||
_selectedTheme = "dark";
|
||||
});
|
||||
},
|
||||
child: SizedBox(
|
||||
width: 200,
|
||||
child: Column(
|
||||
mainAxisSize: MainAxisSize.min,
|
||||
children: [
|
||||
Container(
|
||||
decoration: BoxDecoration(
|
||||
border: Border.all(
|
||||
width: 2.5,
|
||||
color: _selectedTheme == "dark"
|
||||
? Theme.of(context)
|
||||
.extension<StackColors>()!
|
||||
.infoItemIcons
|
||||
: Theme.of(context).extension<StackColors>()!.popupBG,
|
||||
),
|
||||
borderRadius: BorderRadius.circular(
|
||||
Constants.size.circularBorderRadius,
|
||||
),
|
||||
),
|
||||
child: SvgPicture.asset(
|
||||
Assets.svg.themeDark,
|
||||
),
|
||||
),
|
||||
const SizedBox(
|
||||
height: 12,
|
||||
),
|
||||
Row(
|
||||
children: [
|
||||
SizedBox(
|
||||
width: 20,
|
||||
height: 20,
|
||||
child: Radio(
|
||||
activeColor: Theme.of(context)
|
||||
.extension<StackColors>()!
|
||||
.radioButtonIconEnabled,
|
||||
value: "dark",
|
||||
groupValue: _selectedTheme,
|
||||
onChanged: (newValue) {
|
||||
if (newValue is String && newValue == "dark") {
|
||||
DB.instance.put<dynamic>(
|
||||
boxName: DB.boxNameTheme,
|
||||
key: "colorScheme",
|
||||
value: ThemeType.dark.name,
|
||||
);
|
||||
ref.read(colorThemeProvider.state).state =
|
||||
StackColors.fromStackColorTheme(
|
||||
DarkColors(),
|
||||
);
|
||||
|
||||
setState(() {
|
||||
_selectedTheme = "dark";
|
||||
});
|
||||
}
|
||||
},
|
||||
),
|
||||
),
|
||||
const SizedBox(
|
||||
width: 14,
|
||||
),
|
||||
Text(
|
||||
"Dark",
|
||||
style:
|
||||
STextStyles.desktopTextExtraSmall(context).copyWith(
|
||||
color: Theme.of(context)
|
||||
.extension<StackColors>()!
|
||||
.textDark,
|
||||
),
|
||||
),
|
||||
],
|
||||
),
|
||||
],
|
||||
),
|
||||
),
|
||||
),
|
||||
],
|
||||
);
|
||||
}
|
||||
}
|
|
@ -1,200 +0,0 @@
|
|||
import 'package:flutter/material.dart';
|
||||
import 'package:flutter_riverpod/flutter_riverpod.dart';
|
||||
import 'package:flutter_svg/svg.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/home/settings_menu_item.dart';
|
||||
import 'package:stackwallet/utilities/assets.dart';
|
||||
import 'package:stackwallet/utilities/theme/stack_colors.dart';
|
||||
|
||||
class SettingsMenu extends ConsumerStatefulWidget {
|
||||
const SettingsMenu({
|
||||
Key? key,
|
||||
required this.onSelectionChanged,
|
||||
}) : super(key: key);
|
||||
|
||||
final void Function(int)?
|
||||
onSelectionChanged; //is a function that takes in an int and returns void/.;
|
||||
|
||||
static const String routeName = "/settingsMenu";
|
||||
|
||||
@override
|
||||
ConsumerState<ConsumerStatefulWidget> createState() => _SettingsMenuState();
|
||||
}
|
||||
|
||||
class _SettingsMenuState extends ConsumerState<SettingsMenu> {
|
||||
int selectedMenuItem = 0;
|
||||
|
||||
void updateSelectedMenuItem(int index) {
|
||||
setState(() {
|
||||
selectedMenuItem = index;
|
||||
});
|
||||
widget.onSelectionChanged?.call(index);
|
||||
}
|
||||
|
||||
@override
|
||||
Widget build(BuildContext context) {
|
||||
debugPrint("BUILD: $runtimeType");
|
||||
|
||||
return Column(
|
||||
crossAxisAlignment: CrossAxisAlignment.start,
|
||||
children: [
|
||||
Padding(
|
||||
padding: const EdgeInsets.only(left: 15),
|
||||
child: Column(
|
||||
crossAxisAlignment: CrossAxisAlignment.start,
|
||||
children: [
|
||||
SettingsMenuItem(
|
||||
icon: SvgPicture.asset(
|
||||
Assets.svg.polygon,
|
||||
width: 11,
|
||||
height: 11,
|
||||
color: selectedMenuItem == 0
|
||||
? Theme.of(context)
|
||||
.extension<StackColors>()!
|
||||
.accentColorBlue
|
||||
: Colors.transparent,
|
||||
),
|
||||
label: "Backup and restore",
|
||||
value: 0,
|
||||
group: selectedMenuItem,
|
||||
onChanged: updateSelectedMenuItem,
|
||||
),
|
||||
const SizedBox(
|
||||
height: 2,
|
||||
),
|
||||
SettingsMenuItem(
|
||||
icon: SvgPicture.asset(
|
||||
Assets.svg.polygon,
|
||||
width: 11,
|
||||
height: 11,
|
||||
color: selectedMenuItem == 1
|
||||
? Theme.of(context)
|
||||
.extension<StackColors>()!
|
||||
.accentColorBlue
|
||||
: Colors.transparent,
|
||||
),
|
||||
label: "Security",
|
||||
value: 1,
|
||||
group: selectedMenuItem,
|
||||
onChanged: updateSelectedMenuItem,
|
||||
),
|
||||
const SizedBox(
|
||||
height: 2,
|
||||
),
|
||||
SettingsMenuItem(
|
||||
icon: SvgPicture.asset(
|
||||
Assets.svg.polygon,
|
||||
width: 11,
|
||||
height: 11,
|
||||
color: selectedMenuItem == 2
|
||||
? Theme.of(context)
|
||||
.extension<StackColors>()!
|
||||
.accentColorBlue
|
||||
: Colors.transparent,
|
||||
),
|
||||
label: "Currency",
|
||||
value: 2,
|
||||
group: selectedMenuItem,
|
||||
onChanged: updateSelectedMenuItem,
|
||||
),
|
||||
const SizedBox(
|
||||
height: 2,
|
||||
),
|
||||
SettingsMenuItem(
|
||||
icon: SvgPicture.asset(
|
||||
Assets.svg.polygon,
|
||||
width: 11,
|
||||
height: 11,
|
||||
color: selectedMenuItem == 3
|
||||
? Theme.of(context)
|
||||
.extension<StackColors>()!
|
||||
.accentColorBlue
|
||||
: Colors.transparent,
|
||||
),
|
||||
label: "Language",
|
||||
value: 3,
|
||||
group: selectedMenuItem,
|
||||
onChanged: updateSelectedMenuItem,
|
||||
),
|
||||
const SizedBox(
|
||||
height: 2,
|
||||
),
|
||||
SettingsMenuItem(
|
||||
icon: SvgPicture.asset(
|
||||
Assets.svg.polygon,
|
||||
width: 11,
|
||||
height: 11,
|
||||
color: selectedMenuItem == 4
|
||||
? Theme.of(context)
|
||||
.extension<StackColors>()!
|
||||
.accentColorBlue
|
||||
: Colors.transparent,
|
||||
),
|
||||
label: "Nodes",
|
||||
value: 4,
|
||||
group: selectedMenuItem,
|
||||
onChanged: updateSelectedMenuItem,
|
||||
),
|
||||
const SizedBox(
|
||||
height: 2,
|
||||
),
|
||||
SettingsMenuItem(
|
||||
icon: SvgPicture.asset(
|
||||
Assets.svg.polygon,
|
||||
width: 11,
|
||||
height: 11,
|
||||
color: selectedMenuItem == 5
|
||||
? Theme.of(context)
|
||||
.extension<StackColors>()!
|
||||
.accentColorBlue
|
||||
: Colors.transparent,
|
||||
),
|
||||
label: "Syncing preferences",
|
||||
value: 5,
|
||||
group: selectedMenuItem,
|
||||
onChanged: updateSelectedMenuItem,
|
||||
),
|
||||
const SizedBox(
|
||||
height: 2,
|
||||
),
|
||||
SettingsMenuItem(
|
||||
icon: SvgPicture.asset(
|
||||
Assets.svg.polygon,
|
||||
width: 11,
|
||||
height: 11,
|
||||
color: selectedMenuItem == 6
|
||||
? Theme.of(context)
|
||||
.extension<StackColors>()!
|
||||
.accentColorBlue
|
||||
: Colors.transparent,
|
||||
),
|
||||
label: "Appearance",
|
||||
value: 6,
|
||||
group: selectedMenuItem,
|
||||
onChanged: updateSelectedMenuItem,
|
||||
),
|
||||
const SizedBox(
|
||||
height: 2,
|
||||
),
|
||||
SettingsMenuItem(
|
||||
icon: SvgPicture.asset(
|
||||
Assets.svg.polygon,
|
||||
width: 11,
|
||||
height: 11,
|
||||
color: selectedMenuItem == 7
|
||||
? Theme.of(context)
|
||||
.extension<StackColors>()!
|
||||
.accentColorBlue
|
||||
: Colors.transparent,
|
||||
),
|
||||
label: "Advanced",
|
||||
value: 7,
|
||||
group: selectedMenuItem,
|
||||
onChanged: updateSelectedMenuItem,
|
||||
),
|
||||
],
|
||||
),
|
||||
),
|
||||
],
|
||||
);
|
||||
}
|
||||
}
|
|
@ -1,8 +1,10 @@
|
|||
import 'package:flutter/material.dart';
|
||||
import 'package:flutter_riverpod/flutter_riverpod.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/home/desktop_home_view.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/home/my_stack_view/wallet_view/desktop_wallet_view.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/desktop_home_view.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/my_stack_view/wallet_view/desktop_wallet_view.dart';
|
||||
import 'package:stackwallet/providers/global/wallets_provider.dart';
|
||||
import 'package:stackwallet/utilities/constants.dart';
|
||||
import 'package:stackwallet/utilities/enums/coin_enum.dart';
|
||||
import 'package:stackwallet/utilities/theme/stack_colors.dart';
|
||||
import 'package:stackwallet/widgets/rounded_container.dart';
|
||||
import 'package:stackwallet/widgets/wallet_info_row/wallet_info_row.dart';
|
||||
|
@ -10,13 +12,16 @@ import 'package:stackwallet/widgets/wallet_info_row/wallet_info_row.dart';
|
|||
class CoinWalletsTable extends ConsumerWidget {
|
||||
const CoinWalletsTable({
|
||||
Key? key,
|
||||
required this.walletIds,
|
||||
required this.coin,
|
||||
}) : super(key: key);
|
||||
|
||||
final List<String> walletIds;
|
||||
final Coin coin;
|
||||
|
||||
@override
|
||||
Widget build(BuildContext context, WidgetRef ref) {
|
||||
final walletIds = ref.watch(walletsChangeNotifierProvider
|
||||
.select((value) => value.getWalletIdsFor(coin: coin)));
|
||||
|
||||
return Container(
|
||||
decoration: BoxDecoration(
|
||||
color: Theme.of(context).extension<StackColors>()!.popupBG,
|
||||
|
@ -38,7 +43,7 @@ class CoinWalletsTable extends ConsumerWidget {
|
|||
children: [
|
||||
if (i != 0)
|
||||
const SizedBox(
|
||||
height: 32,
|
||||
height: 8,
|
||||
),
|
||||
Stack(
|
||||
children: [
|
|
@ -1,5 +1,5 @@
|
|||
import 'package:flutter/material.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/home/desktop_home_view.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/desktop_home_view.dart';
|
||||
import 'package:stackwallet/utilities/text_styles.dart';
|
||||
import 'package:stackwallet/utilities/theme/stack_colors.dart';
|
||||
|
|
@ -2,7 +2,7 @@ import 'package:flutter/material.dart';
|
|||
import 'package:flutter_riverpod/flutter_riverpod.dart';
|
||||
import 'package:flutter_svg/flutter_svg.dart';
|
||||
import 'package:stackwallet/pages/wallets_view/sub_widgets/empty_wallets.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/home/my_stack_view/my_wallets.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/my_stack_view/my_wallets.dart';
|
||||
import 'package:stackwallet/providers/global/wallets_provider.dart';
|
||||
import 'package:stackwallet/utilities/assets.dart';
|
||||
import 'package:stackwallet/utilities/text_styles.dart';
|
||||
|
@ -27,29 +27,9 @@ class _MyStackViewState extends ConsumerState<MyStackView> {
|
|||
return Background(
|
||||
child: Column(
|
||||
children: [
|
||||
DesktopAppBar(
|
||||
const DesktopAppBar(
|
||||
isCompactHeight: true,
|
||||
leading: Row(
|
||||
children: [
|
||||
const SizedBox(
|
||||
width: 24,
|
||||
),
|
||||
SizedBox(
|
||||
width: 32,
|
||||
height: 32,
|
||||
child: SvgPicture.asset(
|
||||
Assets.svg.stackIcon(context),
|
||||
),
|
||||
),
|
||||
const SizedBox(
|
||||
width: 12,
|
||||
),
|
||||
Text(
|
||||
"My Stack",
|
||||
style: STextStyles.desktopH3(context),
|
||||
)
|
||||
],
|
||||
),
|
||||
leading: DesktopMyStackTitle(),
|
||||
),
|
||||
Expanded(
|
||||
child: hasWallets ? const MyWallets() : const EmptyWallets(),
|
||||
|
@ -59,3 +39,32 @@ class _MyStackViewState extends ConsumerState<MyStackView> {
|
|||
);
|
||||
}
|
||||
}
|
||||
|
||||
class DesktopMyStackTitle extends StatelessWidget {
|
||||
const DesktopMyStackTitle({Key? key}) : super(key: key);
|
||||
|
||||
@override
|
||||
Widget build(BuildContext context) {
|
||||
return Row(
|
||||
children: [
|
||||
const SizedBox(
|
||||
width: 24,
|
||||
),
|
||||
SizedBox(
|
||||
width: 32,
|
||||
height: 32,
|
||||
child: SvgPicture.asset(
|
||||
Assets.svg.stackIcon(context),
|
||||
),
|
||||
),
|
||||
const SizedBox(
|
||||
width: 12,
|
||||
),
|
||||
Text(
|
||||
"My Stack",
|
||||
style: STextStyles.desktopH3(context),
|
||||
)
|
||||
],
|
||||
);
|
||||
}
|
||||
}
|
|
@ -1,8 +1,8 @@
|
|||
import 'package:flutter/material.dart';
|
||||
import 'package:flutter_riverpod/flutter_riverpod.dart';
|
||||
import 'package:stackwallet/pages/add_wallet_views/add_wallet_view/add_wallet_view.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/home/my_stack_view/desktop_favorite_wallets.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/home/my_stack_view/wallet_summary_table.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/my_stack_view/desktop_favorite_wallets.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/my_stack_view/wallet_summary_table.dart';
|
||||
import 'package:stackwallet/providers/providers.dart';
|
||||
import 'package:stackwallet/utilities/text_styles.dart';
|
||||
import 'package:stackwallet/utilities/theme/stack_colors.dart';
|
|
@ -1,7 +1,7 @@
|
|||
import 'package:flutter/material.dart';
|
||||
import 'package:flutter_riverpod/flutter_riverpod.dart';
|
||||
import 'package:flutter_svg/svg.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/home/my_stack_view/coin_wallets_table.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/my_stack_view/coin_wallets_table.dart';
|
||||
import 'package:stackwallet/providers/providers.dart';
|
||||
import 'package:stackwallet/utilities/assets.dart';
|
||||
import 'package:stackwallet/utilities/constants.dart';
|
||||
|
@ -23,6 +23,7 @@ class WalletSummaryTable extends ConsumerStatefulWidget {
|
|||
class _WalletTableState extends ConsumerState<WalletSummaryTable> {
|
||||
@override
|
||||
Widget build(BuildContext context) {
|
||||
debugPrint("BUILD: $runtimeType");
|
||||
final providersByCoin = ref
|
||||
.watch(
|
||||
walletsChangeNotifierProvider.select(
|
||||
|
@ -35,72 +36,75 @@ class _WalletTableState extends ConsumerState<WalletSummaryTable> {
|
|||
return TableView(
|
||||
rows: [
|
||||
for (int i = 0; i < providersByCoin.length; i++)
|
||||
TableViewRow(
|
||||
padding: const EdgeInsets.symmetric(
|
||||
horizontal: 20,
|
||||
vertical: 16,
|
||||
),
|
||||
decoration: BoxDecoration(
|
||||
color: Theme.of(context).extension<StackColors>()!.popupBG,
|
||||
borderRadius: BorderRadius.circular(
|
||||
Constants.size.circularBorderRadius,
|
||||
),
|
||||
),
|
||||
cells: [
|
||||
TableViewCell(
|
||||
flex: 4,
|
||||
child: Row(
|
||||
children: [
|
||||
SvgPicture.asset(
|
||||
Assets.svg.iconFor(coin: providersByCoin[i].key),
|
||||
width: 28,
|
||||
height: 28,
|
||||
Builder(
|
||||
builder: (context) {
|
||||
final providers = ref.watch(walletsChangeNotifierProvider.select(
|
||||
(value) => value
|
||||
.getManagerProvidersForCoin(providersByCoin[i].key)));
|
||||
|
||||
return TableViewRow(
|
||||
padding: const EdgeInsets.symmetric(
|
||||
horizontal: 20,
|
||||
vertical: 16,
|
||||
),
|
||||
decoration: BoxDecoration(
|
||||
color: Theme.of(context).extension<StackColors>()!.popupBG,
|
||||
borderRadius: BorderRadius.circular(
|
||||
Constants.size.circularBorderRadius,
|
||||
),
|
||||
),
|
||||
cells: [
|
||||
TableViewCell(
|
||||
flex: 4,
|
||||
child: Row(
|
||||
children: [
|
||||
SvgPicture.asset(
|
||||
Assets.svg.iconFor(coin: providersByCoin[i].key),
|
||||
width: 28,
|
||||
height: 28,
|
||||
),
|
||||
const SizedBox(
|
||||
width: 10,
|
||||
),
|
||||
Text(
|
||||
providersByCoin[i].key.prettyName,
|
||||
style: STextStyles.desktopTextExtraSmall(context)
|
||||
.copyWith(
|
||||
color: Theme.of(context)
|
||||
.extension<StackColors>()!
|
||||
.textDark,
|
||||
),
|
||||
)
|
||||
],
|
||||
),
|
||||
const SizedBox(
|
||||
width: 10,
|
||||
),
|
||||
Text(
|
||||
providersByCoin[i].key.prettyName,
|
||||
),
|
||||
TableViewCell(
|
||||
flex: 4,
|
||||
child: Text(
|
||||
providers.length == 1
|
||||
? "${providers.length} wallet"
|
||||
: "${providers.length} wallets",
|
||||
style:
|
||||
STextStyles.desktopTextExtraSmall(context).copyWith(
|
||||
color: Theme.of(context)
|
||||
.extension<StackColors>()!
|
||||
.textDark,
|
||||
.textSubtitle1,
|
||||
),
|
||||
)
|
||||
],
|
||||
),
|
||||
),
|
||||
TableViewCell(
|
||||
flex: 4,
|
||||
child: Text(
|
||||
providersByCoin[i].value.length == 1
|
||||
? "${providersByCoin[i].value.length} wallet"
|
||||
: "${providersByCoin[i].value.length} wallets",
|
||||
style: STextStyles.desktopTextExtraSmall(context).copyWith(
|
||||
color: Theme.of(context)
|
||||
.extension<StackColors>()!
|
||||
.textSubtitle1,
|
||||
),
|
||||
),
|
||||
),
|
||||
),
|
||||
TableViewCell(
|
||||
flex: 6,
|
||||
child: TablePriceInfo(
|
||||
TableViewCell(
|
||||
flex: 6,
|
||||
child: TablePriceInfo(
|
||||
coin: providersByCoin[i].key,
|
||||
),
|
||||
),
|
||||
],
|
||||
expandingChild: CoinWalletsTable(
|
||||
coin: providersByCoin[i].key,
|
||||
),
|
||||
),
|
||||
],
|
||||
expandingChild: CoinWalletsTable(
|
||||
walletIds: ref.watch(
|
||||
walletsChangeNotifierProvider.select(
|
||||
(value) => value.getWalletIdsFor(
|
||||
coin: providersByCoin[i].key,
|
||||
),
|
||||
),
|
||||
),
|
||||
),
|
||||
)
|
||||
);
|
||||
},
|
||||
),
|
||||
],
|
||||
);
|
||||
}
|
|
@ -8,12 +8,12 @@ import 'package:flutter_svg/svg.dart';
|
|||
import 'package:stackwallet/notifications/show_flush_bar.dart';
|
||||
import 'package:stackwallet/pages/exchange_view/sub_widgets/exchange_rate_sheet.dart';
|
||||
import 'package:stackwallet/pages/exchange_view/wallet_initiated_exchange_view.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/home/my_stack_view/wallet_view/sub_widgets/delete_wallet_button.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/home/my_stack_view/wallet_view/sub_widgets/desktop_wallet_summary.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/home/my_stack_view/wallet_view/sub_widgets/my_wallet.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/home/my_stack_view/wallet_view/sub_widgets/network_info_button.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/home/my_stack_view/wallet_view/sub_widgets/recent_desktop_transactions.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/home/my_stack_view/wallet_view/sub_widgets/wallet_keys_button.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/my_stack_view/wallet_view/sub_widgets/delete_wallet_button.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/my_stack_view/wallet_view/sub_widgets/desktop_wallet_summary.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/my_stack_view/wallet_view/sub_widgets/my_wallet.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/my_stack_view/wallet_view/sub_widgets/network_info_button.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/my_stack_view/wallet_view/sub_widgets/recent_desktop_transactions.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/my_stack_view/wallet_view/sub_widgets/wallet_keys_button.dart';
|
||||
import 'package:stackwallet/providers/global/auto_swb_service_provider.dart';
|
||||
import 'package:stackwallet/providers/providers.dart';
|
||||
import 'package:stackwallet/providers/ui/transaction_filter_provider.dart';
|
||||
|
@ -25,7 +25,6 @@ import 'package:stackwallet/services/exchange/exchange_data_loading_service.dart
|
|||
import 'package:stackwallet/utilities/assets.dart';
|
||||
import 'package:stackwallet/utilities/enums/backup_frequency_type.dart';
|
||||
import 'package:stackwallet/utilities/enums/coin_enum.dart';
|
||||
import 'package:stackwallet/utilities/enums/flush_bar_type.dart';
|
||||
import 'package:stackwallet/utilities/logger.dart';
|
||||
import 'package:stackwallet/utilities/text_styles.dart';
|
||||
import 'package:stackwallet/utilities/theme/stack_colors.dart';
|
||||
|
@ -60,7 +59,6 @@ class DesktopWalletView extends ConsumerStatefulWidget {
|
|||
|
||||
class _DesktopWalletViewState extends ConsumerState<DesktopWalletView> {
|
||||
late final TextEditingController controller;
|
||||
late final String walletId;
|
||||
late final EventBus eventBus;
|
||||
|
||||
late final bool _shouldDisableAutoSyncOnLogOut;
|
||||
|
@ -75,8 +73,9 @@ class _DesktopWalletViewState extends ConsumerState<DesktopWalletView> {
|
|||
}
|
||||
|
||||
Future<void> _logout() async {
|
||||
final managerProvider =
|
||||
ref.read(walletsChangeNotifierProvider).getManagerProvider(walletId);
|
||||
final managerProvider = ref
|
||||
.read(walletsChangeNotifierProvider)
|
||||
.getManagerProvider(widget.walletId);
|
||||
if (_shouldDisableAutoSyncOnLogOut) {
|
||||
// disable auto sync if it was enabled only when loading wallet
|
||||
ref.read(managerProvider).shouldAutoSync = false;
|
||||
|
@ -96,7 +95,7 @@ class _DesktopWalletViewState extends ConsumerState<DesktopWalletView> {
|
|||
_cnLoadingService.loadAll(ref,
|
||||
coin: ref
|
||||
.read(walletsChangeNotifierProvider)
|
||||
.getManager(walletId)
|
||||
.getManager(widget.walletId)
|
||||
.coin);
|
||||
} else {
|
||||
Logging.instance.log("User does not want to use external calls",
|
||||
|
@ -105,8 +104,9 @@ class _DesktopWalletViewState extends ConsumerState<DesktopWalletView> {
|
|||
}
|
||||
|
||||
void _onExchangePressed(BuildContext context) async {
|
||||
final managerProvider =
|
||||
ref.read(walletsChangeNotifierProvider).getManagerProvider(walletId);
|
||||
final managerProvider = ref
|
||||
.read(walletsChangeNotifierProvider)
|
||||
.getManagerProvider(widget.walletId);
|
||||
unawaited(_cnLoadingService.loadAll(ref));
|
||||
|
||||
final coin = ref.read(managerProvider).coin;
|
||||
|
@ -128,7 +128,6 @@ class _DesktopWalletViewState extends ConsumerState<DesktopWalletView> {
|
|||
} else {
|
||||
ref.read(currentExchangeNameStateProvider.state).state =
|
||||
ChangeNowExchange.exchangeName;
|
||||
final walletId = ref.read(managerProvider).walletId;
|
||||
ref.read(prefsChangeNotifierProvider).exchangeRateType =
|
||||
ExchangeRateType.estimated;
|
||||
|
||||
|
@ -161,7 +160,7 @@ class _DesktopWalletViewState extends ConsumerState<DesktopWalletView> {
|
|||
Navigator.of(context).pushNamed(
|
||||
WalletInitiatedExchangeView.routeName,
|
||||
arguments: Tuple3(
|
||||
walletId,
|
||||
widget.walletId,
|
||||
coin,
|
||||
_loadCNData,
|
||||
),
|
||||
|
@ -172,8 +171,9 @@ class _DesktopWalletViewState extends ConsumerState<DesktopWalletView> {
|
|||
}
|
||||
|
||||
Future<void> attemptAnonymize() async {
|
||||
final managerProvider =
|
||||
ref.read(walletsChangeNotifierProvider).getManagerProvider(walletId);
|
||||
final managerProvider = ref
|
||||
.read(walletsChangeNotifierProvider)
|
||||
.getManagerProvider(widget.walletId);
|
||||
|
||||
bool shouldPop = false;
|
||||
unawaited(
|
||||
|
@ -284,9 +284,9 @@ class _DesktopWalletViewState extends ConsumerState<DesktopWalletView> {
|
|||
@override
|
||||
void initState() {
|
||||
controller = TextEditingController();
|
||||
walletId = widget.walletId;
|
||||
final managerProvider =
|
||||
ref.read(walletsChangeNotifierProvider).getManagerProvider(walletId);
|
||||
final managerProvider = ref
|
||||
.read(walletsChangeNotifierProvider)
|
||||
.getManagerProvider(widget.walletId);
|
||||
|
||||
controller.text = ref.read(managerProvider).walletName;
|
||||
|
||||
|
@ -307,13 +307,19 @@ class _DesktopWalletViewState extends ConsumerState<DesktopWalletView> {
|
|||
super.initState();
|
||||
}
|
||||
|
||||
@override
|
||||
void dispose() {
|
||||
controller.dispose();
|
||||
super.dispose();
|
||||
}
|
||||
|
||||
@override
|
||||
Widget build(BuildContext context) {
|
||||
final manager = ref.watch(walletsChangeNotifierProvider
|
||||
.select((value) => value.getManager(walletId)));
|
||||
.select((value) => value.getManager(widget.walletId)));
|
||||
final coin = manager.coin;
|
||||
final managerProvider = ref.watch(walletsChangeNotifierProvider
|
||||
.select((value) => value.getManagerProvider(walletId)));
|
||||
.select((value) => value.getManagerProvider(widget.walletId)));
|
||||
|
||||
return DesktopScaffold(
|
||||
appBar: DesktopAppBar(
|
||||
|
@ -356,47 +362,8 @@ class _DesktopWalletViewState extends ConsumerState<DesktopWalletView> {
|
|||
minWidth: 48,
|
||||
),
|
||||
child: IntrinsicWidth(
|
||||
child: HoverTextField(
|
||||
controller: controller,
|
||||
style: STextStyles.desktopH3(context),
|
||||
readOnly: true,
|
||||
onDone: () async {
|
||||
final currentWalletName =
|
||||
ref.read(managerProvider).walletName;
|
||||
final newName = controller.text;
|
||||
if (newName != currentWalletName) {
|
||||
final success = await ref
|
||||
.read(walletsServiceChangeNotifierProvider)
|
||||
.renameWallet(
|
||||
from: currentWalletName,
|
||||
to: newName,
|
||||
shouldNotifyListeners: true,
|
||||
);
|
||||
if (success) {
|
||||
ref
|
||||
.read(walletsChangeNotifierProvider)
|
||||
.getManager(walletId)
|
||||
.walletName = newName;
|
||||
unawaited(
|
||||
showFloatingFlushBar(
|
||||
type: FlushBarType.success,
|
||||
message: "Wallet renamed",
|
||||
context: context,
|
||||
),
|
||||
);
|
||||
} else {
|
||||
unawaited(
|
||||
showFloatingFlushBar(
|
||||
type: FlushBarType.warning,
|
||||
message:
|
||||
"Wallet named \"$newName\" already exists",
|
||||
context: context,
|
||||
),
|
||||
);
|
||||
controller.text = currentWalletName;
|
||||
}
|
||||
}
|
||||
},
|
||||
child: DesktopWalletNameField(
|
||||
walletId: widget.walletId,
|
||||
),
|
||||
),
|
||||
),
|
||||
|
@ -404,20 +371,20 @@ class _DesktopWalletViewState extends ConsumerState<DesktopWalletView> {
|
|||
Row(
|
||||
children: [
|
||||
NetworkInfoButton(
|
||||
walletId: walletId,
|
||||
walletId: widget.walletId,
|
||||
eventBus: eventBus,
|
||||
),
|
||||
const SizedBox(
|
||||
width: 2,
|
||||
),
|
||||
WalletKeysButton(
|
||||
walletId: walletId,
|
||||
walletId: widget.walletId,
|
||||
),
|
||||
const SizedBox(
|
||||
width: 2,
|
||||
),
|
||||
DeleteWalletButton(
|
||||
walletId: walletId,
|
||||
walletId: widget.walletId,
|
||||
),
|
||||
const SizedBox(
|
||||
width: 12,
|
||||
|
@ -447,7 +414,7 @@ class _DesktopWalletViewState extends ConsumerState<DesktopWalletView> {
|
|||
width: 10,
|
||||
),
|
||||
DesktopWalletSummary(
|
||||
walletId: walletId,
|
||||
walletId: widget.walletId,
|
||||
managerProvider: managerProvider,
|
||||
initialSyncStatus: ref.watch(managerProvider
|
||||
.select((value) => value.isRefreshing))
|
||||
|
@ -557,7 +524,7 @@ class _DesktopWalletViewState extends ConsumerState<DesktopWalletView> {
|
|||
SizedBox(
|
||||
width: 450,
|
||||
child: MyWallet(
|
||||
walletId: walletId,
|
||||
walletId: widget.walletId,
|
||||
),
|
||||
),
|
||||
const SizedBox(
|
||||
|
@ -565,7 +532,7 @@ class _DesktopWalletViewState extends ConsumerState<DesktopWalletView> {
|
|||
),
|
||||
Expanded(
|
||||
child: RecentDesktopTransactions(
|
||||
walletId: walletId,
|
||||
walletId: widget.walletId,
|
||||
),
|
||||
),
|
||||
],
|
|
@ -2,7 +2,7 @@ import 'package:flutter/material.dart';
|
|||
import 'package:flutter_riverpod/flutter_riverpod.dart';
|
||||
import 'package:flutter_svg/flutter_svg.dart';
|
||||
import 'package:stackwallet/models/contact.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/home/my_stack_view/wallet_view/sub_widgets/address_book_address_chooser/sub_widgets/contact_list_item.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/my_stack_view/wallet_view/sub_widgets/address_book_address_chooser/sub_widgets/contact_list_item.dart';
|
||||
import 'package:stackwallet/providers/global/address_book_service_provider.dart';
|
||||
import 'package:stackwallet/utilities/assets.dart';
|
||||
import 'package:stackwallet/utilities/constants.dart';
|
|
@ -1,7 +1,7 @@
|
|||
import 'package:flutter/material.dart';
|
||||
import 'package:flutter_riverpod/flutter_riverpod.dart';
|
||||
import 'package:flutter_svg/svg.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/home/my_stack_view/wallet_view/sub_widgets/desktop_delete_wallet_dialog.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/my_stack_view/wallet_view/sub_widgets/desktop_delete_wallet_dialog.dart';
|
||||
import 'package:stackwallet/route_generator.dart';
|
||||
import 'package:stackwallet/utilities/assets.dart';
|
||||
import 'package:stackwallet/utilities/constants.dart';
|
|
@ -1,6 +1,6 @@
|
|||
import 'package:flutter/material.dart';
|
||||
import 'package:flutter_riverpod/flutter_riverpod.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/home/my_stack_view/wallet_view/sub_widgets/delete_wallet_keys_popup.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/my_stack_view/wallet_view/sub_widgets/delete_wallet_keys_popup.dart';
|
||||
import 'package:stackwallet/providers/global/wallets_provider.dart';
|
||||
import 'package:stackwallet/utilities/text_styles.dart';
|
||||
import 'package:stackwallet/utilities/theme/stack_colors.dart';
|
|
@ -4,7 +4,7 @@ import 'package:flutter/material.dart';
|
|||
import 'package:flutter_riverpod/flutter_riverpod.dart';
|
||||
import 'package:flutter_svg/svg.dart';
|
||||
import 'package:stackwallet/notifications/show_flush_bar.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/home/my_stack_view/wallet_view/sub_widgets/desktop_attention_delete_wallet.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/my_stack_view/wallet_view/sub_widgets/desktop_attention_delete_wallet.dart';
|
||||
import 'package:stackwallet/providers/desktop/storage_crypto_handler_provider.dart';
|
||||
import 'package:stackwallet/utilities/assets.dart';
|
||||
import 'package:stackwallet/utilities/constants.dart';
|
|
@ -134,8 +134,10 @@ class _DesktopReceiveState extends ConsumerState<DesktopReceive> {
|
|||
child: Container(
|
||||
decoration: BoxDecoration(
|
||||
border: Border.all(
|
||||
color: Theme.of(context).extension<StackColors>()!.background,
|
||||
width: 2,
|
||||
color: Theme.of(context)
|
||||
.extension<StackColors>()!
|
||||
.backgroundAppBar,
|
||||
width: 1,
|
||||
),
|
||||
borderRadius: BorderRadius.circular(
|
||||
Constants.size.circularBorderRadius,
|
|
@ -11,9 +11,9 @@ import 'package:stackwallet/models/send_view_auto_fill_data.dart';
|
|||
import 'package:stackwallet/pages/send_view/confirm_transaction_view.dart';
|
||||
import 'package:stackwallet/pages/send_view/sub_widgets/building_transaction_dialog.dart';
|
||||
import 'package:stackwallet/pages/send_view/sub_widgets/transaction_fee_selection_sheet.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/home/desktop_home_view.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/home/my_stack_view/wallet_view/sub_widgets/address_book_address_chooser/address_book_address_chooser.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/home/my_stack_view/wallet_view/sub_widgets/desktop_fee_dropdown.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/desktop_home_view.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/my_stack_view/wallet_view/sub_widgets/address_book_address_chooser/address_book_address_chooser.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/my_stack_view/wallet_view/sub_widgets/desktop_fee_dropdown.dart';
|
||||
import 'package:stackwallet/providers/providers.dart';
|
||||
import 'package:stackwallet/providers/ui/fee_rate_type_state_provider.dart';
|
||||
import 'package:stackwallet/providers/ui/preview_tx_button_state_provider.dart';
|
||||
|
@ -71,16 +71,16 @@ class _DesktopSendState extends ConsumerState<DesktopSend> {
|
|||
late TextEditingController sendToController;
|
||||
late TextEditingController cryptoAmountController;
|
||||
late TextEditingController baseAmountController;
|
||||
late TextEditingController noteController;
|
||||
// late TextEditingController feeController;
|
||||
|
||||
late final SendViewAutoFillData? _data;
|
||||
|
||||
final _addressFocusNode = FocusNode();
|
||||
final _noteFocusNode = FocusNode();
|
||||
final _cryptoFocus = FocusNode();
|
||||
final _baseFocus = FocusNode();
|
||||
|
||||
String? _note;
|
||||
|
||||
Decimal? _amountToSend;
|
||||
Decimal? _cachedAmountToSend;
|
||||
String? _address;
|
||||
|
@ -255,7 +255,6 @@ class _DesktopSendState extends ConsumerState<DesktopSend> {
|
|||
sendToController.text = "";
|
||||
cryptoAmountController.text = "";
|
||||
baseAmountController.text = "";
|
||||
noteController.text = "";
|
||||
});
|
||||
},
|
||||
),
|
||||
|
@ -325,7 +324,7 @@ class _DesktopSendState extends ConsumerState<DesktopSend> {
|
|||
context,
|
||||
rootNavigator: true,
|
||||
).pop();
|
||||
txData["note"] = noteController.text;
|
||||
txData["note"] = _note;
|
||||
txData["address"] = _address;
|
||||
|
||||
unawaited(
|
||||
|
@ -633,9 +632,9 @@ class _DesktopSendState extends ConsumerState<DesktopSend> {
|
|||
|
||||
// autofill notes field
|
||||
if (results["message"] != null) {
|
||||
noteController.text = results["message"]!;
|
||||
_note = results["message"]!;
|
||||
} else if (results["label"] != null) {
|
||||
noteController.text = results["label"]!;
|
||||
_note = results["label"]!;
|
||||
}
|
||||
|
||||
// autofill amount field
|
||||
|
@ -783,7 +782,6 @@ class _DesktopSendState extends ConsumerState<DesktopSend> {
|
|||
sendToController = TextEditingController();
|
||||
cryptoAmountController = TextEditingController();
|
||||
baseAmountController = TextEditingController();
|
||||
noteController = TextEditingController();
|
||||
// feeController = TextEditingController();
|
||||
|
||||
onCryptoAmountChanged = _cryptoAmountChanged;
|
||||
|
@ -828,10 +826,8 @@ class _DesktopSendState extends ConsumerState<DesktopSend> {
|
|||
sendToController.dispose();
|
||||
cryptoAmountController.dispose();
|
||||
baseAmountController.dispose();
|
||||
noteController.dispose();
|
||||
// feeController.dispose();
|
||||
|
||||
_noteFocusNode.dispose();
|
||||
_addressFocusNode.dispose();
|
||||
_cryptoFocus.dispose();
|
||||
_baseFocus.dispose();
|
||||
|
@ -1298,73 +1294,73 @@ class _DesktopSendState extends ConsumerState<DesktopSend> {
|
|||
}
|
||||
},
|
||||
),
|
||||
const SizedBox(
|
||||
height: 20,
|
||||
),
|
||||
Text(
|
||||
"Note (optional)",
|
||||
style: STextStyles.desktopTextExtraSmall(context).copyWith(
|
||||
color: Theme.of(context)
|
||||
.extension<StackColors>()!
|
||||
.textFieldActiveSearchIconRight,
|
||||
),
|
||||
textAlign: TextAlign.left,
|
||||
),
|
||||
const SizedBox(
|
||||
height: 10,
|
||||
),
|
||||
ClipRRect(
|
||||
borderRadius: BorderRadius.circular(
|
||||
Constants.size.circularBorderRadius,
|
||||
),
|
||||
child: TextField(
|
||||
minLines: 1,
|
||||
maxLines: 5,
|
||||
autocorrect: Util.isDesktop ? false : true,
|
||||
enableSuggestions: Util.isDesktop ? false : true,
|
||||
controller: noteController,
|
||||
focusNode: _noteFocusNode,
|
||||
style: STextStyles.desktopTextExtraSmall(context).copyWith(
|
||||
color: Theme.of(context)
|
||||
.extension<StackColors>()!
|
||||
.textFieldActiveText,
|
||||
height: 1.8,
|
||||
),
|
||||
onChanged: (_) => setState(() {}),
|
||||
decoration: standardInputDecoration(
|
||||
"Type something...",
|
||||
_noteFocusNode,
|
||||
context,
|
||||
desktopMed: true,
|
||||
).copyWith(
|
||||
contentPadding: const EdgeInsets.only(
|
||||
left: 16,
|
||||
top: 11,
|
||||
bottom: 12,
|
||||
right: 5,
|
||||
),
|
||||
suffixIcon: noteController.text.isNotEmpty
|
||||
? Padding(
|
||||
padding: const EdgeInsets.only(right: 0),
|
||||
child: UnconstrainedBox(
|
||||
child: Row(
|
||||
children: [
|
||||
TextFieldIconButton(
|
||||
child: const XIcon(),
|
||||
onTap: () async {
|
||||
setState(() {
|
||||
noteController.text = "";
|
||||
});
|
||||
},
|
||||
),
|
||||
],
|
||||
),
|
||||
),
|
||||
)
|
||||
: null,
|
||||
),
|
||||
),
|
||||
),
|
||||
// const SizedBox(
|
||||
// height: 20,
|
||||
// ),
|
||||
// Text(
|
||||
// "Note (optional)",
|
||||
// style: STextStyles.desktopTextExtraSmall(context).copyWith(
|
||||
// color: Theme.of(context)
|
||||
// .extension<StackColors>()!
|
||||
// .textFieldActiveSearchIconRight,
|
||||
// ),
|
||||
// textAlign: TextAlign.left,
|
||||
// ),
|
||||
// const SizedBox(
|
||||
// height: 10,
|
||||
// ),
|
||||
// ClipRRect(
|
||||
// borderRadius: BorderRadius.circular(
|
||||
// Constants.size.circularBorderRadius,
|
||||
// ),
|
||||
// child: TextField(
|
||||
// minLines: 1,
|
||||
// maxLines: 5,
|
||||
// autocorrect: Util.isDesktop ? false : true,
|
||||
// enableSuggestions: Util.isDesktop ? false : true,
|
||||
// controller: noteController,
|
||||
// focusNode: _noteFocusNode,
|
||||
// style: STextStyles.desktopTextExtraSmall(context).copyWith(
|
||||
// color: Theme.of(context)
|
||||
// .extension<StackColors>()!
|
||||
// .textFieldActiveText,
|
||||
// height: 1.8,
|
||||
// ),
|
||||
// onChanged: (_) => setState(() {}),
|
||||
// decoration: standardInputDecoration(
|
||||
// "Type something...",
|
||||
// _noteFocusNode,
|
||||
// context,
|
||||
// desktopMed: true,
|
||||
// ).copyWith(
|
||||
// contentPadding: const EdgeInsets.only(
|
||||
// left: 16,
|
||||
// top: 11,
|
||||
// bottom: 12,
|
||||
// right: 5,
|
||||
// ),
|
||||
// suffixIcon: noteController.text.isNotEmpty
|
||||
// ? Padding(
|
||||
// padding: const EdgeInsets.only(right: 0),
|
||||
// child: UnconstrainedBox(
|
||||
// child: Row(
|
||||
// children: [
|
||||
// TextFieldIconButton(
|
||||
// child: const XIcon(),
|
||||
// onTap: () async {
|
||||
// setState(() {
|
||||
// noteController.text = "";
|
||||
// });
|
||||
// },
|
||||
// ),
|
||||
// ],
|
||||
// ),
|
||||
// ),
|
||||
// )
|
||||
// : null,
|
||||
// ),
|
||||
// ),
|
||||
// ),
|
||||
const SizedBox(
|
||||
height: 20,
|
||||
),
|
|
@ -2,7 +2,7 @@ import 'package:decimal/decimal.dart';
|
|||
import 'package:flutter/material.dart';
|
||||
import 'package:flutter_riverpod/flutter_riverpod.dart';
|
||||
import 'package:stackwallet/pages/wallet_view/sub_widgets/wallet_refresh_button.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/home/my_stack_view/wallet_view/sub_widgets/desktop_balance_toggle_button.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/my_stack_view/wallet_view/sub_widgets/desktop_balance_toggle_button.dart';
|
||||
import 'package:stackwallet/providers/providers.dart';
|
||||
import 'package:stackwallet/providers/wallet/wallet_balance_toggle_state_provider.dart';
|
||||
import 'package:stackwallet/services/coins/firo/firo_wallet.dart';
|
|
@ -1,7 +1,7 @@
|
|||
import 'package:flutter/material.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/home/my_stack_view/wallet_view/sub_widgets/desktop_receive.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/home/my_stack_view/wallet_view/sub_widgets/desktop_send.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/home/my_stack_view/wallet_view/sub_widgets/send_receive_tab_menu.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/my_stack_view/wallet_view/sub_widgets/desktop_receive.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/my_stack_view/wallet_view/sub_widgets/desktop_send.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/my_stack_view/wallet_view/sub_widgets/send_receive_tab_menu.dart';
|
||||
import 'package:stackwallet/utilities/constants.dart';
|
||||
import 'package:stackwallet/utilities/text_styles.dart';
|
||||
import 'package:stackwallet/utilities/theme/stack_colors.dart';
|
||||
|
@ -63,24 +63,25 @@ class _MyWalletState extends State<MyWallet> {
|
|||
),
|
||||
),
|
||||
),
|
||||
child: IndexedStack(
|
||||
index: _selectedIndex,
|
||||
children: [
|
||||
Padding(
|
||||
key: const Key("desktopSendViewPortKey"),
|
||||
padding: const EdgeInsets.all(20),
|
||||
child: DesktopSend(
|
||||
walletId: widget.walletId,
|
||||
),
|
||||
child: AnimatedCrossFade(
|
||||
firstChild: Padding(
|
||||
key: const Key("desktopSendViewPortKey"),
|
||||
padding: const EdgeInsets.all(20),
|
||||
child: DesktopSend(
|
||||
walletId: widget.walletId,
|
||||
),
|
||||
Padding(
|
||||
key: const Key("desktopReceiveViewPortKey"),
|
||||
padding: const EdgeInsets.all(20),
|
||||
child: DesktopReceive(
|
||||
walletId: widget.walletId,
|
||||
),
|
||||
),
|
||||
secondChild: Padding(
|
||||
key: const Key("desktopReceiveViewPortKey"),
|
||||
padding: const EdgeInsets.all(20),
|
||||
child: DesktopReceive(
|
||||
walletId: widget.walletId,
|
||||
),
|
||||
],
|
||||
),
|
||||
crossFadeState: _selectedIndex == 0
|
||||
? CrossFadeState.showFirst
|
||||
: CrossFadeState.showSecond,
|
||||
duration: const Duration(milliseconds: 250),
|
||||
),
|
||||
),
|
||||
],
|
|
@ -0,0 +1,165 @@
|
|||
import 'package:flutter/material.dart';
|
||||
import 'package:stackwallet/utilities/text_styles.dart';
|
||||
import 'package:stackwallet/utilities/theme/stack_colors.dart';
|
||||
|
||||
class SendReceiveTabMenu extends StatefulWidget {
|
||||
const SendReceiveTabMenu({
|
||||
Key? key,
|
||||
this.initialIndex = 0,
|
||||
this.onChanged,
|
||||
}) : super(key: key);
|
||||
|
||||
final int initialIndex;
|
||||
final void Function(int)? onChanged;
|
||||
|
||||
@override
|
||||
State<SendReceiveTabMenu> createState() => _SendReceiveTabMenuState();
|
||||
}
|
||||
|
||||
class _SendReceiveTabMenuState extends State<SendReceiveTabMenu> {
|
||||
late int _selectedIndex;
|
||||
|
||||
void _onChanged(int newIndex) {
|
||||
if (_selectedIndex != newIndex) {
|
||||
setState(() {
|
||||
_selectedIndex = newIndex;
|
||||
});
|
||||
widget.onChanged?.call(_selectedIndex);
|
||||
}
|
||||
}
|
||||
|
||||
@override
|
||||
void initState() {
|
||||
_selectedIndex = widget.initialIndex;
|
||||
super.initState();
|
||||
}
|
||||
|
||||
@override
|
||||
Widget build(BuildContext context) {
|
||||
return Row(
|
||||
children: [
|
||||
Expanded(
|
||||
child: MouseRegion(
|
||||
cursor: SystemMouseCursors.click,
|
||||
child: GestureDetector(
|
||||
onTap: () => _onChanged(0),
|
||||
child: Container(
|
||||
color: Colors.transparent,
|
||||
child: Column(
|
||||
children: [
|
||||
const SizedBox(
|
||||
height: 16,
|
||||
),
|
||||
AnimatedCrossFade(
|
||||
firstChild: Text(
|
||||
"Send",
|
||||
style:
|
||||
STextStyles.desktopTextExtraSmall(context).copyWith(
|
||||
color: Theme.of(context)
|
||||
.extension<StackColors>()!
|
||||
.accentColorBlue,
|
||||
),
|
||||
),
|
||||
secondChild: Text(
|
||||
"Send",
|
||||
style:
|
||||
STextStyles.desktopTextExtraSmall(context).copyWith(
|
||||
color: Theme.of(context)
|
||||
.extension<StackColors>()!
|
||||
.textSubtitle1,
|
||||
),
|
||||
),
|
||||
crossFadeState: _selectedIndex == 0
|
||||
? CrossFadeState.showFirst
|
||||
: CrossFadeState.showSecond,
|
||||
duration: const Duration(milliseconds: 250),
|
||||
),
|
||||
const SizedBox(
|
||||
height: 19,
|
||||
),
|
||||
Container(
|
||||
height: 2,
|
||||
decoration: BoxDecoration(
|
||||
color: Theme.of(context)
|
||||
.extension<StackColors>()!
|
||||
.backgroundAppBar,
|
||||
),
|
||||
),
|
||||
],
|
||||
),
|
||||
),
|
||||
),
|
||||
),
|
||||
),
|
||||
Expanded(
|
||||
child: MouseRegion(
|
||||
cursor: SystemMouseCursors.click,
|
||||
child: GestureDetector(
|
||||
onTap: () => _onChanged(1),
|
||||
child: Container(
|
||||
color: Colors.transparent,
|
||||
child: Column(
|
||||
children: [
|
||||
const SizedBox(
|
||||
height: 16,
|
||||
),
|
||||
AnimatedCrossFade(
|
||||
firstChild: Text(
|
||||
"Receive",
|
||||
style:
|
||||
STextStyles.desktopTextExtraSmall(context).copyWith(
|
||||
color: Theme.of(context)
|
||||
.extension<StackColors>()!
|
||||
.accentColorBlue,
|
||||
),
|
||||
),
|
||||
secondChild: Text(
|
||||
"Receive",
|
||||
style:
|
||||
STextStyles.desktopTextExtraSmall(context).copyWith(
|
||||
color: Theme.of(context)
|
||||
.extension<StackColors>()!
|
||||
.textSubtitle1,
|
||||
),
|
||||
),
|
||||
crossFadeState: _selectedIndex == 1
|
||||
? CrossFadeState.showFirst
|
||||
: CrossFadeState.showSecond,
|
||||
duration: const Duration(milliseconds: 250),
|
||||
),
|
||||
const SizedBox(
|
||||
height: 19,
|
||||
),
|
||||
Stack(
|
||||
children: [
|
||||
Container(
|
||||
height: 2,
|
||||
decoration: BoxDecoration(
|
||||
color: Theme.of(context)
|
||||
.extension<StackColors>()!
|
||||
.backgroundAppBar,
|
||||
),
|
||||
),
|
||||
AnimatedSlide(
|
||||
offset: Offset(_selectedIndex == 0 ? -1 : 0, 0),
|
||||
duration: const Duration(milliseconds: 250),
|
||||
child: Container(
|
||||
height: 2,
|
||||
decoration: BoxDecoration(
|
||||
color: Theme.of(context)
|
||||
.extension<StackColors>()!
|
||||
.accentColorBlue),
|
||||
),
|
||||
),
|
||||
],
|
||||
),
|
||||
],
|
||||
),
|
||||
),
|
||||
),
|
||||
),
|
||||
),
|
||||
],
|
||||
);
|
||||
}
|
||||
}
|
|
@ -4,12 +4,11 @@ import 'package:flutter/material.dart';
|
|||
import 'package:flutter_riverpod/flutter_riverpod.dart';
|
||||
import 'package:flutter_svg/svg.dart';
|
||||
import 'package:stackwallet/notifications/show_flush_bar.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/home/my_stack_view/wallet_view/sub_widgets/wallet_keys_desktop_popup.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/my_stack_view/wallet_view/sub_widgets/wallet_keys_desktop_popup.dart';
|
||||
import 'package:stackwallet/providers/desktop/storage_crypto_handler_provider.dart';
|
||||
import 'package:stackwallet/providers/providers.dart';
|
||||
import 'package:stackwallet/utilities/assets.dart';
|
||||
import 'package:stackwallet/utilities/constants.dart';
|
||||
import 'package:stackwallet/utilities/enums/flush_bar_type.dart';
|
||||
import 'package:stackwallet/utilities/text_styles.dart';
|
||||
import 'package:stackwallet/utilities/theme/stack_colors.dart';
|
||||
import 'package:stackwallet/widgets/desktop/desktop_dialog.dart';
|
|
@ -1,6 +1,6 @@
|
|||
import 'package:flutter/material.dart';
|
||||
import 'package:flutter_svg/svg.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/home/my_stack_view/wallet_view/sub_widgets/unlock_wallet_keys_desktop.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/my_stack_view/wallet_view/sub_widgets/unlock_wallet_keys_desktop.dart';
|
||||
import 'package:stackwallet/route_generator.dart';
|
||||
import 'package:stackwallet/utilities/assets.dart';
|
||||
import 'package:stackwallet/utilities/text_styles.dart';
|
|
@ -4,11 +4,10 @@ import 'package:flutter/material.dart';
|
|||
import 'package:flutter/services.dart';
|
||||
import 'package:stackwallet/notifications/show_flush_bar.dart';
|
||||
import 'package:stackwallet/pages/add_wallet_views/new_wallet_recovery_phrase_view/sub_widgets/mnemonic_table.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/home/my_stack_view/wallet_view/sub_widgets/qr_code_desktop_popup_content.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/my_stack_view/wallet_view/sub_widgets/qr_code_desktop_popup_content.dart';
|
||||
import 'package:stackwallet/utilities/address_utils.dart';
|
||||
import 'package:stackwallet/utilities/assets.dart';
|
||||
import 'package:stackwallet/utilities/clipboard_interface.dart';
|
||||
import 'package:stackwallet/utilities/enums/flush_bar_type.dart';
|
||||
import 'package:stackwallet/utilities/text_styles.dart';
|
||||
import 'package:stackwallet/utilities/theme/stack_colors.dart';
|
||||
import 'package:stackwallet/widgets/desktop/desktop_dialog.dart';
|
|
@ -4,7 +4,8 @@ import 'package:flutter/material.dart';
|
|||
import 'package:flutter_riverpod/flutter_riverpod.dart';
|
||||
import 'package:flutter_svg/svg.dart';
|
||||
import 'package:stackwallet/notifications/show_flush_bar.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/home/desktop_home_view.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/desktop_home_view.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/password/forgotten_passphrase_restore_from_swb.dart';
|
||||
import 'package:stackwallet/providers/desktop/storage_crypto_handler_provider.dart';
|
||||
import 'package:stackwallet/providers/global/secure_store_provider.dart';
|
||||
import 'package:stackwallet/providers/providers.dart';
|
||||
|
@ -23,9 +24,11 @@ import 'package:zxcvbn/zxcvbn.dart';
|
|||
class CreatePasswordView extends ConsumerStatefulWidget {
|
||||
const CreatePasswordView({
|
||||
Key? key,
|
||||
this.restoreFromSWB = false,
|
||||
}) : super(key: key);
|
||||
|
||||
static const String routeName = "/createPasswordDesktop";
|
||||
final bool restoreFromSWB;
|
||||
|
||||
@override
|
||||
ConsumerState<CreatePasswordView> createState() => _CreatePasswordViewState();
|
||||
|
@ -84,7 +87,9 @@ class _CreatePasswordViewState extends ConsumerState<CreatePasswordView> {
|
|||
|
||||
// load default nodes now as node service requires storage handler to exist
|
||||
|
||||
await ref.read(nodeServiceChangeNotifierProvider).updateDefaults();
|
||||
if (!widget.restoreFromSWB) {
|
||||
await ref.read(nodeServiceChangeNotifierProvider).updateDefaults();
|
||||
}
|
||||
} catch (e) {
|
||||
unawaited(showFloatingFlushBar(
|
||||
type: FlushBarType.warning,
|
||||
|
@ -95,15 +100,28 @@ class _CreatePasswordViewState extends ConsumerState<CreatePasswordView> {
|
|||
}
|
||||
|
||||
if (mounted) {
|
||||
unawaited(Navigator.of(context)
|
||||
.pushReplacementNamed(DesktopHomeView.routeName));
|
||||
if (widget.restoreFromSWB) {
|
||||
unawaited(
|
||||
Navigator.of(context).pushNamed(
|
||||
ForgottenPassphraseRestoreFromSWB.routeName,
|
||||
),
|
||||
);
|
||||
} else {
|
||||
unawaited(
|
||||
Navigator.of(context).pushReplacementNamed(
|
||||
DesktopHomeView.routeName,
|
||||
),
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
unawaited(showFloatingFlushBar(
|
||||
type: FlushBarType.success,
|
||||
message: "Your password is set up",
|
||||
context: context,
|
||||
));
|
||||
if (!widget.restoreFromSWB) {
|
||||
unawaited(showFloatingFlushBar(
|
||||
type: FlushBarType.success,
|
||||
message: "Your password is set up",
|
||||
context: context,
|
||||
));
|
||||
}
|
||||
}
|
||||
|
||||
@override
|
|
@ -0,0 +1,195 @@
|
|||
import 'dart:async';
|
||||
|
||||
import 'package:flutter/material.dart';
|
||||
import 'package:flutter_riverpod/flutter_riverpod.dart';
|
||||
import 'package:flutter_svg/svg.dart';
|
||||
import 'package:hive/hive.dart';
|
||||
import 'package:stackwallet/hive/db.dart';
|
||||
import 'package:stackwallet/notifications/show_flush_bar.dart';
|
||||
import 'package:stackwallet/pages/intro_view.dart';
|
||||
import 'package:stackwallet/utilities/assets.dart';
|
||||
import 'package:stackwallet/utilities/logger.dart';
|
||||
import 'package:stackwallet/utilities/stack_file_system.dart';
|
||||
import 'package:stackwallet/utilities/text_styles.dart';
|
||||
import 'package:stackwallet/widgets/custom_buttons/app_bar_icon_button.dart';
|
||||
import 'package:stackwallet/widgets/desktop/desktop_app_bar.dart';
|
||||
import 'package:stackwallet/widgets/desktop/desktop_scaffold.dart';
|
||||
import 'package:stackwallet/widgets/desktop/primary_button.dart';
|
||||
import 'package:stackwallet/widgets/desktop/secondary_button.dart';
|
||||
|
||||
class DeletePasswordWarningView extends ConsumerStatefulWidget {
|
||||
const DeletePasswordWarningView({
|
||||
Key? key,
|
||||
required this.shouldCreateNew,
|
||||
}) : super(key: key);
|
||||
|
||||
static const String routeName = "/deletePasswordWarning";
|
||||
|
||||
final bool shouldCreateNew;
|
||||
|
||||
@override
|
||||
ConsumerState<DeletePasswordWarningView> createState() =>
|
||||
_ForgotPasswordDesktopViewState();
|
||||
}
|
||||
|
||||
class _ForgotPasswordDesktopViewState
|
||||
extends ConsumerState<DeletePasswordWarningView> {
|
||||
bool _deleteInProgress = false;
|
||||
|
||||
Future<bool> _deleteStack() async {
|
||||
final appRoot = await StackFileSystem.applicationRootDirectory();
|
||||
|
||||
try {
|
||||
await Hive.close();
|
||||
await appRoot.delete(recursive: true);
|
||||
await DB.instance.init();
|
||||
} catch (e, s) {
|
||||
Logging.instance.log(
|
||||
"$e\n$s",
|
||||
level: LogLevel.Fatal,
|
||||
);
|
||||
return false;
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
@override
|
||||
Widget build(BuildContext context) {
|
||||
return DesktopScaffold(
|
||||
appBar: DesktopAppBar(
|
||||
leading: AppBarBackButton(
|
||||
onPressed: () async {
|
||||
if (mounted && !_deleteInProgress) {
|
||||
Navigator.of(context).pop();
|
||||
}
|
||||
},
|
||||
),
|
||||
isCompactHeight: false,
|
||||
),
|
||||
body: Column(
|
||||
mainAxisAlignment: MainAxisAlignment.center,
|
||||
crossAxisAlignment: CrossAxisAlignment.center,
|
||||
children: [
|
||||
SizedBox(
|
||||
width: 480,
|
||||
child: Column(
|
||||
mainAxisSize: MainAxisSize.min,
|
||||
children: [
|
||||
SvgPicture.asset(
|
||||
Assets.svg.stackIcon(context),
|
||||
width: 100,
|
||||
),
|
||||
const SizedBox(
|
||||
height: 42,
|
||||
),
|
||||
Text(
|
||||
"Warning!",
|
||||
style: STextStyles.desktopH1(context),
|
||||
),
|
||||
const SizedBox(
|
||||
height: 24,
|
||||
),
|
||||
SizedBox(
|
||||
width: 480,
|
||||
child: RichText(
|
||||
textAlign: TextAlign.center,
|
||||
text: TextSpan(
|
||||
children: [
|
||||
TextSpan(
|
||||
text: "To ",
|
||||
style: STextStyles.desktopTextSmall(context),
|
||||
),
|
||||
TextSpan(
|
||||
text: widget.shouldCreateNew
|
||||
? "create a new Stack"
|
||||
: "restore from backup",
|
||||
style: STextStyles.desktopTextSmallBold(context),
|
||||
),
|
||||
TextSpan(
|
||||
text: ", we need to ",
|
||||
style: STextStyles.desktopTextSmall(context),
|
||||
),
|
||||
TextSpan(
|
||||
text: "delete your old wallets",
|
||||
style: STextStyles.desktopTextSmallBold(context),
|
||||
),
|
||||
TextSpan(
|
||||
text:
|
||||
". All wallets will be lost. If you have not written down your recovery phrase for EACH wallet, you may be in danger of losing funds. Continue?",
|
||||
style: STextStyles.desktopTextSmall(context),
|
||||
),
|
||||
],
|
||||
),
|
||||
),
|
||||
),
|
||||
const SizedBox(
|
||||
height: 48,
|
||||
),
|
||||
PrimaryButton(
|
||||
label: "Delete and continue",
|
||||
enabled: !_deleteInProgress,
|
||||
onPressed: () async {
|
||||
final shouldDelete = !_deleteInProgress;
|
||||
setState(() {
|
||||
_deleteInProgress = true;
|
||||
});
|
||||
|
||||
if (shouldDelete) {
|
||||
unawaited(
|
||||
showFloatingFlushBar(
|
||||
type: FlushBarType.info,
|
||||
message: "Deleting wallet...",
|
||||
context: context,
|
||||
),
|
||||
);
|
||||
|
||||
final success = await _deleteStack();
|
||||
|
||||
if (success) {
|
||||
await showFloatingFlushBar(
|
||||
type: FlushBarType.success,
|
||||
message: "Wallet deleted",
|
||||
context: context,
|
||||
);
|
||||
if (mounted) {
|
||||
await Navigator.of(context).pushNamedAndRemoveUntil(
|
||||
IntroView.routeName,
|
||||
(_) => false,
|
||||
);
|
||||
}
|
||||
} else {
|
||||
await showFloatingFlushBar(
|
||||
type: FlushBarType.warning,
|
||||
message: "Something broke badly. Contact developer",
|
||||
context: context,
|
||||
);
|
||||
|
||||
setState(() {
|
||||
_deleteInProgress = false;
|
||||
});
|
||||
}
|
||||
}
|
||||
},
|
||||
),
|
||||
const SizedBox(
|
||||
height: 24,
|
||||
),
|
||||
SecondaryButton(
|
||||
label: "Take me back!",
|
||||
enabled: !_deleteInProgress,
|
||||
onPressed: () {
|
||||
Navigator.of(context).pop();
|
||||
},
|
||||
),
|
||||
const SizedBox(
|
||||
height: kDesktopAppBarHeight,
|
||||
),
|
||||
],
|
||||
),
|
||||
),
|
||||
],
|
||||
),
|
||||
);
|
||||
}
|
||||
}
|
|
@ -4,8 +4,8 @@ import 'package:flutter/material.dart';
|
|||
import 'package:flutter_riverpod/flutter_riverpod.dart';
|
||||
import 'package:flutter_svg/svg.dart';
|
||||
import 'package:stackwallet/notifications/show_flush_bar.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/forgot_password_desktop_view.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/home/desktop_home_view.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/desktop_home_view.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/password/forgot_password_desktop_view.dart';
|
||||
import 'package:stackwallet/providers/desktop/storage_crypto_handler_provider.dart';
|
||||
import 'package:stackwallet/providers/global/secure_store_provider.dart';
|
||||
import 'package:stackwallet/utilities/assets.dart';
|
|
@ -1,5 +1,6 @@
|
|||
import 'package:flutter/material.dart';
|
||||
import 'package:flutter_svg/svg.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/password/delete_password_warning_view.dart';
|
||||
import 'package:stackwallet/utilities/assets.dart';
|
||||
import 'package:stackwallet/utilities/text_styles.dart';
|
||||
import 'package:stackwallet/utilities/theme/stack_colors.dart';
|
||||
|
@ -74,18 +75,26 @@ class _ForgotPasswordDesktopViewState extends State<ForgotPasswordDesktopView> {
|
|||
height: 48,
|
||||
),
|
||||
PrimaryButton(
|
||||
label: "Create new wallet",
|
||||
label: "Create new Stack",
|
||||
onPressed: () {
|
||||
// // todo delete everything and start fresh?
|
||||
const shouldCreateNew = true;
|
||||
Navigator.of(context).pushNamed(
|
||||
DeletePasswordWarningView.routeName,
|
||||
arguments: shouldCreateNew,
|
||||
);
|
||||
},
|
||||
),
|
||||
const SizedBox(
|
||||
height: 24,
|
||||
),
|
||||
SecondaryButton(
|
||||
label: "Restore from backup",
|
||||
label: "Restore from Stack backup",
|
||||
onPressed: () {
|
||||
// todo SWB restore
|
||||
const shouldCreateNew = false;
|
||||
Navigator.of(context).pushNamed(
|
||||
DeletePasswordWarningView.routeName,
|
||||
arguments: shouldCreateNew,
|
||||
);
|
||||
},
|
||||
),
|
||||
const SizedBox(
|
|
@ -0,0 +1,406 @@
|
|||
import 'dart:async';
|
||||
import 'dart:io';
|
||||
|
||||
import 'package:flutter/foundation.dart';
|
||||
import 'package:flutter/material.dart';
|
||||
import 'package:flutter_riverpod/flutter_riverpod.dart';
|
||||
import 'package:flutter_svg/svg.dart';
|
||||
import 'package:hive_flutter/hive_flutter.dart';
|
||||
import 'package:stackwallet/hive/db.dart';
|
||||
import 'package:stackwallet/notifications/show_flush_bar.dart';
|
||||
import 'package:stackwallet/pages/settings_views/global_settings_view/stack_backup_views/helpers/restore_create_backup.dart';
|
||||
import 'package:stackwallet/pages/settings_views/global_settings_view/stack_backup_views/helpers/swb_file_system.dart';
|
||||
import 'package:stackwallet/pages/settings_views/global_settings_view/stack_backup_views/sub_views/stack_restore_progress_view.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/password/create_password_view.dart';
|
||||
import 'package:stackwallet/providers/desktop/storage_crypto_handler_provider.dart';
|
||||
import 'package:stackwallet/providers/global/secure_store_provider.dart';
|
||||
import 'package:stackwallet/providers/global/wallets_provider.dart';
|
||||
import 'package:stackwallet/utilities/assets.dart';
|
||||
import 'package:stackwallet/utilities/constants.dart';
|
||||
import 'package:stackwallet/utilities/flutter_secure_storage_interface.dart';
|
||||
import 'package:stackwallet/utilities/logger.dart';
|
||||
import 'package:stackwallet/utilities/text_styles.dart';
|
||||
import 'package:stackwallet/utilities/theme/stack_colors.dart';
|
||||
import 'package:stackwallet/widgets/custom_buttons/app_bar_icon_button.dart';
|
||||
import 'package:stackwallet/widgets/desktop/desktop_app_bar.dart';
|
||||
import 'package:stackwallet/widgets/desktop/desktop_dialog.dart';
|
||||
import 'package:stackwallet/widgets/desktop/desktop_scaffold.dart';
|
||||
import 'package:stackwallet/widgets/desktop/primary_button.dart';
|
||||
import 'package:stackwallet/widgets/loading_indicator.dart';
|
||||
import 'package:stackwallet/widgets/stack_text_field.dart';
|
||||
import 'package:tuple/tuple.dart';
|
||||
|
||||
class ForgottenPassphraseRestoreFromSWB extends ConsumerStatefulWidget {
|
||||
const ForgottenPassphraseRestoreFromSWB({Key? key}) : super(key: key);
|
||||
|
||||
static const String routeName = "/forgottenPassphraseRestoreFromSWB";
|
||||
|
||||
@override
|
||||
ConsumerState<ForgottenPassphraseRestoreFromSWB> createState() =>
|
||||
_ForgottenPassphraseRestoreFromSWBState();
|
||||
}
|
||||
|
||||
class _ForgottenPassphraseRestoreFromSWBState
|
||||
extends ConsumerState<ForgottenPassphraseRestoreFromSWB> {
|
||||
late final TextEditingController fileLocationController;
|
||||
late final TextEditingController passwordController;
|
||||
|
||||
late final FocusNode passwordFocusNode;
|
||||
|
||||
late final SWBFileSystem stackFileSystem;
|
||||
|
||||
bool hidePassword = true;
|
||||
|
||||
bool _enableButton = false;
|
||||
|
||||
Future<void> restore() async {
|
||||
final String fileToRestore = fileLocationController.text;
|
||||
final String passphrase = passwordController.text;
|
||||
|
||||
if (!(await File(fileToRestore).exists())) {
|
||||
await showFloatingFlushBar(
|
||||
type: FlushBarType.warning,
|
||||
message: "Backup file does not exist",
|
||||
context: context,
|
||||
);
|
||||
return;
|
||||
}
|
||||
|
||||
bool shouldPop = false;
|
||||
unawaited(
|
||||
showDialog<dynamic>(
|
||||
barrierDismissible: false,
|
||||
context: context,
|
||||
builder: (_) => WillPopScope(
|
||||
onWillPop: () async {
|
||||
return shouldPop;
|
||||
},
|
||||
child: Column(
|
||||
crossAxisAlignment: CrossAxisAlignment.stretch,
|
||||
mainAxisAlignment: MainAxisAlignment.center,
|
||||
children: [
|
||||
Material(
|
||||
color: Colors.transparent,
|
||||
child: Center(
|
||||
child: Text(
|
||||
"Decrypting Stack backup file",
|
||||
style: STextStyles.pageTitleH2(context).copyWith(
|
||||
color:
|
||||
Theme.of(context).extension<StackColors>()!.textWhite,
|
||||
),
|
||||
),
|
||||
),
|
||||
),
|
||||
const SizedBox(
|
||||
height: 64,
|
||||
),
|
||||
const Center(
|
||||
child: LoadingIndicator(
|
||||
width: 100,
|
||||
),
|
||||
),
|
||||
],
|
||||
),
|
||||
),
|
||||
),
|
||||
);
|
||||
|
||||
final String? jsonString = await compute(
|
||||
SWB.decryptStackWalletWithPassphrase,
|
||||
Tuple2(fileToRestore, passphrase),
|
||||
debugLabel: "stack wallet decryption compute",
|
||||
);
|
||||
|
||||
if (mounted) {
|
||||
// pop LoadingIndicator
|
||||
shouldPop = true;
|
||||
Navigator.of(context).pop();
|
||||
|
||||
passwordController.text = "";
|
||||
|
||||
if (jsonString == null) {
|
||||
await showFloatingFlushBar(
|
||||
type: FlushBarType.warning,
|
||||
message: "Failed to decrypt backup file",
|
||||
context: context,
|
||||
);
|
||||
return;
|
||||
}
|
||||
|
||||
ref.read(walletsChangeNotifierProvider);
|
||||
|
||||
await showDialog<void>(
|
||||
context: context,
|
||||
barrierDismissible: false,
|
||||
builder: (context) {
|
||||
return DesktopDialog(
|
||||
maxWidth: 580,
|
||||
maxHeight: double.infinity,
|
||||
child: Padding(
|
||||
padding: const EdgeInsets.all(32),
|
||||
child: Column(
|
||||
mainAxisSize: MainAxisSize.min,
|
||||
children: [
|
||||
Row(
|
||||
mainAxisAlignment: MainAxisAlignment.spaceBetween,
|
||||
children: [
|
||||
Text(
|
||||
"Restoring Stack wallet",
|
||||
style: STextStyles.desktopH3(context),
|
||||
),
|
||||
],
|
||||
),
|
||||
const SizedBox(
|
||||
height: 44,
|
||||
),
|
||||
StackRestoreProgressView(
|
||||
jsonString: jsonString,
|
||||
shouldPushToHome: true,
|
||||
),
|
||||
],
|
||||
),
|
||||
),
|
||||
);
|
||||
},
|
||||
);
|
||||
// await Navigator.of(context).push(
|
||||
// RouteGenerator.getRoute(
|
||||
// builder: (_) => StackRestoreProgressView(
|
||||
// jsonString: jsonString,
|
||||
// ),
|
||||
// ),
|
||||
// );
|
||||
}
|
||||
}
|
||||
|
||||
@override
|
||||
void initState() {
|
||||
stackFileSystem = SWBFileSystem();
|
||||
fileLocationController = TextEditingController();
|
||||
passwordController = TextEditingController();
|
||||
|
||||
passwordFocusNode = FocusNode();
|
||||
|
||||
super.initState();
|
||||
}
|
||||
|
||||
@override
|
||||
void dispose() {
|
||||
fileLocationController.dispose();
|
||||
passwordController.dispose();
|
||||
|
||||
passwordFocusNode.dispose();
|
||||
|
||||
super.dispose();
|
||||
}
|
||||
|
||||
@override
|
||||
Widget build(BuildContext context) {
|
||||
return DesktopScaffold(
|
||||
appBar: DesktopAppBar(
|
||||
leading: AppBarBackButton(
|
||||
onPressed: () async {
|
||||
await (ref.read(secureStoreProvider).store as DesktopSecureStore)
|
||||
.close();
|
||||
ref.refresh(secureStoreProvider);
|
||||
ref.refresh(storageCryptoHandlerProvider);
|
||||
await Hive.deleteBoxFromDisk(DB.boxNameDesktopData);
|
||||
await DB.instance.init();
|
||||
if (mounted) {
|
||||
Navigator.of(context)
|
||||
.popUntil(ModalRoute.withName(CreatePasswordView.routeName));
|
||||
Navigator.of(context).pop();
|
||||
}
|
||||
},
|
||||
),
|
||||
isCompactHeight: false,
|
||||
),
|
||||
body: Column(
|
||||
mainAxisAlignment: MainAxisAlignment.center,
|
||||
crossAxisAlignment: CrossAxisAlignment.center,
|
||||
children: [
|
||||
SizedBox(
|
||||
width: 480,
|
||||
child: Column(
|
||||
mainAxisSize: MainAxisSize.min,
|
||||
children: [
|
||||
Text(
|
||||
"Restore from backup",
|
||||
style: STextStyles.desktopH1(context),
|
||||
),
|
||||
const SizedBox(
|
||||
height: 32,
|
||||
),
|
||||
Text(
|
||||
"Use your Stack wallet backup file to restore your wallets, address book, and wallet preferences.",
|
||||
textAlign: TextAlign.center,
|
||||
style: STextStyles.desktopTextSmall(context).copyWith(
|
||||
color: Theme.of(context)
|
||||
.extension<StackColors>()!
|
||||
.textSubtitle1,
|
||||
),
|
||||
),
|
||||
const SizedBox(
|
||||
height: 40,
|
||||
),
|
||||
GestureDetector(
|
||||
onTap: () async {
|
||||
try {
|
||||
await stackFileSystem.prepareStorage();
|
||||
if (mounted) {
|
||||
await stackFileSystem.openFile(context);
|
||||
}
|
||||
|
||||
if (mounted) {
|
||||
setState(() {
|
||||
fileLocationController.text =
|
||||
stackFileSystem.filePath ?? "";
|
||||
});
|
||||
}
|
||||
} catch (e, s) {
|
||||
Logging.instance.log("$e\n$s", level: LogLevel.Error);
|
||||
}
|
||||
},
|
||||
child: MouseRegion(
|
||||
cursor: SystemMouseCursors.click,
|
||||
child: IgnorePointer(
|
||||
child: TextField(
|
||||
autocorrect: false,
|
||||
enableSuggestions: false,
|
||||
controller: fileLocationController,
|
||||
style: STextStyles.field(context),
|
||||
decoration: InputDecoration(
|
||||
hintText: "Choose file...",
|
||||
hintStyle: STextStyles.desktopTextFieldLabel(context),
|
||||
suffixIcon: SizedBox(
|
||||
height: 70,
|
||||
child: UnconstrainedBox(
|
||||
child: Row(
|
||||
children: [
|
||||
const SizedBox(
|
||||
width: 24,
|
||||
),
|
||||
SvgPicture.asset(
|
||||
Assets.svg.folder,
|
||||
color: Theme.of(context)
|
||||
.extension<StackColors>()!
|
||||
.textDark3,
|
||||
width: 24,
|
||||
height: 24,
|
||||
),
|
||||
const SizedBox(
|
||||
width: 12,
|
||||
),
|
||||
],
|
||||
),
|
||||
),
|
||||
),
|
||||
),
|
||||
key: const Key("restoreFromFileLocationTextFieldKey"),
|
||||
readOnly: true,
|
||||
toolbarOptions: const ToolbarOptions(
|
||||
copy: true,
|
||||
cut: false,
|
||||
paste: false,
|
||||
selectAll: false,
|
||||
),
|
||||
onChanged: (newValue) {
|
||||
setState(() {
|
||||
_enableButton =
|
||||
passwordController.text.isNotEmpty &&
|
||||
fileLocationController.text.isNotEmpty;
|
||||
});
|
||||
},
|
||||
),
|
||||
),
|
||||
),
|
||||
),
|
||||
const SizedBox(
|
||||
height: 16,
|
||||
),
|
||||
ClipRRect(
|
||||
borderRadius: BorderRadius.circular(
|
||||
Constants.size.circularBorderRadius,
|
||||
),
|
||||
child: TextField(
|
||||
key: const Key("restoreFromFilePasswordFieldKey"),
|
||||
focusNode: passwordFocusNode,
|
||||
controller: passwordController,
|
||||
style: STextStyles.desktopTextMedium(context).copyWith(
|
||||
height: 2,
|
||||
),
|
||||
obscureText: hidePassword,
|
||||
enableSuggestions: false,
|
||||
autocorrect: false,
|
||||
decoration: standardInputDecoration(
|
||||
"Enter passphrase",
|
||||
passwordFocusNode,
|
||||
context,
|
||||
).copyWith(
|
||||
suffixIcon: UnconstrainedBox(
|
||||
child: SizedBox(
|
||||
height: 70,
|
||||
child: Row(
|
||||
children: [
|
||||
const SizedBox(
|
||||
width: 24,
|
||||
),
|
||||
GestureDetector(
|
||||
key: const Key(
|
||||
"restoreFromFilePasswordFieldShowPasswordButtonKey"),
|
||||
onTap: () async {
|
||||
setState(() {
|
||||
hidePassword = !hidePassword;
|
||||
});
|
||||
},
|
||||
child: MouseRegion(
|
||||
cursor: SystemMouseCursors.click,
|
||||
child: SvgPicture.asset(
|
||||
hidePassword
|
||||
? Assets.svg.eye
|
||||
: Assets.svg.eyeSlash,
|
||||
color: Theme.of(context)
|
||||
.extension<StackColors>()!
|
||||
.textDark3,
|
||||
width: 24,
|
||||
height: 24,
|
||||
),
|
||||
),
|
||||
),
|
||||
const SizedBox(
|
||||
width: 12,
|
||||
),
|
||||
],
|
||||
),
|
||||
),
|
||||
),
|
||||
),
|
||||
onChanged: (newValue) {
|
||||
setState(() {
|
||||
_enableButton = passwordController.text.isNotEmpty &&
|
||||
fileLocationController.text.isNotEmpty;
|
||||
});
|
||||
},
|
||||
),
|
||||
),
|
||||
const SizedBox(
|
||||
height: 24,
|
||||
),
|
||||
PrimaryButton(
|
||||
label: "Restore",
|
||||
enabled: _enableButton,
|
||||
onPressed: () {
|
||||
restore();
|
||||
},
|
||||
),
|
||||
const SizedBox(
|
||||
height: kDesktopAppBarHeight,
|
||||
),
|
||||
],
|
||||
),
|
||||
),
|
||||
],
|
||||
),
|
||||
);
|
||||
}
|
||||
}
|
|
@ -1,14 +1,14 @@
|
|||
import 'package:flutter/material.dart';
|
||||
import 'package:flutter_riverpod/flutter_riverpod.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/home/settings_menu/advanced_settings/advanced_settings.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/home/settings_menu/appearance_settings.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/home/settings_menu/backup_and_restore/backup_and_restore_settings.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/home/settings_menu/currency_settings/currency_settings.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/home/settings_menu/language_settings/language_settings.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/home/settings_menu/nodes_settings.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/home/settings_menu/security_settings.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/home/settings_menu/settings_menu.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/home/settings_menu/syncing_preferences_settings.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/settings/settings_menu.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/settings/settings_menu/advanced_settings/advanced_settings.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/settings/settings_menu/appearance_settings.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/settings/settings_menu/backup_and_restore/backup_and_restore_settings.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/settings/settings_menu/currency_settings/currency_settings.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/settings/settings_menu/language_settings/language_settings.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/settings/settings_menu/nodes_settings.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/settings/settings_menu/security_settings.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/settings/settings_menu/syncing_preferences_settings.dart';
|
||||
import 'package:stackwallet/route_generator.dart';
|
||||
import 'package:stackwallet/utilities/text_styles.dart';
|
||||
import 'package:stackwallet/utilities/theme/stack_colors.dart';
|
||||
|
@ -26,7 +26,6 @@ class DesktopSettingsView extends ConsumerStatefulWidget {
|
|||
}
|
||||
|
||||
class _DesktopSettingsViewState extends ConsumerState<DesktopSettingsView> {
|
||||
int currentViewIndex = 0;
|
||||
final List<Widget> contentViews = [
|
||||
const Navigator(
|
||||
key: Key("settingsBackupRestoreDesktopKey"),
|
||||
|
@ -70,12 +69,6 @@ class _DesktopSettingsViewState extends ConsumerState<DesktopSettingsView> {
|
|||
), //advanced
|
||||
];
|
||||
|
||||
void onMenuSelectionChanged(int newIndex) {
|
||||
setState(() {
|
||||
currentViewIndex = newIndex;
|
||||
});
|
||||
}
|
||||
|
||||
@override
|
||||
Widget build(BuildContext context) {
|
||||
return DesktopScaffold(
|
||||
|
@ -83,28 +76,36 @@ class _DesktopSettingsViewState extends ConsumerState<DesktopSettingsView> {
|
|||
appBar: DesktopAppBar(
|
||||
isCompactHeight: true,
|
||||
leading: Row(
|
||||
children: [
|
||||
const SizedBox(
|
||||
children: const [
|
||||
SizedBox(
|
||||
width: 24,
|
||||
height: 24,
|
||||
),
|
||||
Text(
|
||||
"Settings",
|
||||
style: STextStyles.desktopH3(context),
|
||||
)
|
||||
DesktopSettingsTitle(),
|
||||
],
|
||||
),
|
||||
),
|
||||
body: Row(
|
||||
children: [
|
||||
SettingsMenu(
|
||||
onSelectionChanged: onMenuSelectionChanged,
|
||||
),
|
||||
const SettingsMenu(),
|
||||
Expanded(
|
||||
child: contentViews[currentViewIndex],
|
||||
child: contentViews[
|
||||
ref.watch(selectedSettingsMenuItemStateProvider.state).state],
|
||||
),
|
||||
],
|
||||
),
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
class DesktopSettingsTitle extends StatelessWidget {
|
||||
const DesktopSettingsTitle({Key? key}) : super(key: key);
|
||||
|
||||
@override
|
||||
Widget build(BuildContext context) {
|
||||
return Text(
|
||||
"Settings",
|
||||
style: STextStyles.desktopH3(context),
|
||||
);
|
||||
}
|
||||
}
|
233
lib/pages_desktop_specific/settings/settings_menu.dart
Normal file
233
lib/pages_desktop_specific/settings/settings_menu.dart
Normal file
|
@ -0,0 +1,233 @@
|
|||
import 'package:flutter/material.dart';
|
||||
import 'package:flutter_riverpod/flutter_riverpod.dart';
|
||||
import 'package:flutter_svg/svg.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/settings/settings_menu_item.dart';
|
||||
import 'package:stackwallet/utilities/assets.dart';
|
||||
import 'package:stackwallet/utilities/theme/stack_colors.dart';
|
||||
|
||||
final selectedSettingsMenuItemStateProvider = StateProvider<int>((_) => 0);
|
||||
|
||||
class SettingsMenu extends ConsumerStatefulWidget {
|
||||
const SettingsMenu({
|
||||
Key? key,
|
||||
}) : super(key: key);
|
||||
|
||||
@override
|
||||
ConsumerState<ConsumerStatefulWidget> createState() => _SettingsMenuState();
|
||||
}
|
||||
|
||||
class _SettingsMenuState extends ConsumerState<SettingsMenu> {
|
||||
final List<String> labels = [
|
||||
"Backup and restore",
|
||||
"Security",
|
||||
"Currency",
|
||||
"Language",
|
||||
"Nodes",
|
||||
"Syncing preferences",
|
||||
"Appearance",
|
||||
"Advanced",
|
||||
];
|
||||
|
||||
@override
|
||||
Widget build(BuildContext context) {
|
||||
debugPrint("BUILD: $runtimeType");
|
||||
|
||||
return Column(
|
||||
crossAxisAlignment: CrossAxisAlignment.start,
|
||||
children: [
|
||||
Padding(
|
||||
padding: const EdgeInsets.only(left: 15),
|
||||
child: Column(
|
||||
crossAxisAlignment: CrossAxisAlignment.start,
|
||||
children: [
|
||||
for (int i = 0; i < labels.length; i++)
|
||||
Column(
|
||||
mainAxisSize: MainAxisSize.min,
|
||||
children: [
|
||||
if (i > 0)
|
||||
const SizedBox(
|
||||
height: 2,
|
||||
),
|
||||
SettingsMenuItem<int>(
|
||||
icon: SvgPicture.asset(
|
||||
Assets.svg.polygon,
|
||||
width: 11,
|
||||
height: 11,
|
||||
color: ref
|
||||
.watch(selectedSettingsMenuItemStateProvider
|
||||
.state)
|
||||
.state ==
|
||||
i
|
||||
? Theme.of(context)
|
||||
.extension<StackColors>()!
|
||||
.accentColorBlue
|
||||
: Colors.transparent,
|
||||
),
|
||||
label: labels[i],
|
||||
value: i,
|
||||
group: ref
|
||||
.watch(selectedSettingsMenuItemStateProvider.state)
|
||||
.state,
|
||||
onChanged: (newValue) => ref
|
||||
.read(selectedSettingsMenuItemStateProvider.state)
|
||||
.state = newValue,
|
||||
),
|
||||
],
|
||||
)
|
||||
|
||||
// SettingsMenuItem(
|
||||
// icon: SvgPicture.asset(
|
||||
// Assets.svg.polygon,
|
||||
// width: 11,
|
||||
// height: 11,
|
||||
// color: selectedMenuItem == 0
|
||||
// ? Theme.of(context)
|
||||
// .extension<StackColors>()!
|
||||
// .accentColorBlue
|
||||
// : Colors.transparent,
|
||||
// ),
|
||||
// label: "Backup and restore",
|
||||
// value: 0,
|
||||
// group: selectedMenuItem,
|
||||
// onChanged: updateSelectedMenuItem,
|
||||
// ),
|
||||
// const SizedBox(
|
||||
// height: 2,
|
||||
// ),
|
||||
// SettingsMenuItem(
|
||||
// icon: SvgPicture.asset(
|
||||
// Assets.svg.polygon,
|
||||
// width: 11,
|
||||
// height: 11,
|
||||
// color: selectedMenuItem == 1
|
||||
// ? Theme.of(context)
|
||||
// .extension<StackColors>()!
|
||||
// .accentColorBlue
|
||||
// : Colors.transparent,
|
||||
// ),
|
||||
// label: "Security",
|
||||
// value: 1,
|
||||
// group: selectedMenuItem,
|
||||
// onChanged: updateSelectedMenuItem,
|
||||
// ),
|
||||
// const SizedBox(
|
||||
// height: 2,
|
||||
// ),
|
||||
// SettingsMenuItem(
|
||||
// icon: SvgPicture.asset(
|
||||
// Assets.svg.polygon,
|
||||
// width: 11,
|
||||
// height: 11,
|
||||
// color: selectedMenuItem == 2
|
||||
// ? Theme.of(context)
|
||||
// .extension<StackColors>()!
|
||||
// .accentColorBlue
|
||||
// : Colors.transparent,
|
||||
// ),
|
||||
// label: "Currency",
|
||||
// value: 2,
|
||||
// group: selectedMenuItem,
|
||||
// onChanged: updateSelectedMenuItem,
|
||||
// ),
|
||||
// const SizedBox(
|
||||
// height: 2,
|
||||
// ),
|
||||
// SettingsMenuItem(
|
||||
// icon: SvgPicture.asset(
|
||||
// Assets.svg.polygon,
|
||||
// width: 11,
|
||||
// height: 11,
|
||||
// color: selectedMenuItem == 3
|
||||
// ? Theme.of(context)
|
||||
// .extension<StackColors>()!
|
||||
// .accentColorBlue
|
||||
// : Colors.transparent,
|
||||
// ),
|
||||
// label: "Language",
|
||||
// value: 3,
|
||||
// group: selectedMenuItem,
|
||||
// onChanged: updateSelectedMenuItem,
|
||||
// ),
|
||||
// const SizedBox(
|
||||
// height: 2,
|
||||
// ),
|
||||
// SettingsMenuItem(
|
||||
// icon: SvgPicture.asset(
|
||||
// Assets.svg.polygon,
|
||||
// width: 11,
|
||||
// height: 11,
|
||||
// color: selectedMenuItem == 4
|
||||
// ? Theme.of(context)
|
||||
// .extension<StackColors>()!
|
||||
// .accentColorBlue
|
||||
// : Colors.transparent,
|
||||
// ),
|
||||
// label: "Nodes",
|
||||
// value: 4,
|
||||
// group: selectedMenuItem,
|
||||
// onChanged: updateSelectedMenuItem,
|
||||
// ),
|
||||
// const SizedBox(
|
||||
// height: 2,
|
||||
// ),
|
||||
// SettingsMenuItem(
|
||||
// icon: SvgPicture.asset(
|
||||
// Assets.svg.polygon,
|
||||
// width: 11,
|
||||
// height: 11,
|
||||
// color: selectedMenuItem == 5
|
||||
// ? Theme.of(context)
|
||||
// .extension<StackColors>()!
|
||||
// .accentColorBlue
|
||||
// : Colors.transparent,
|
||||
// ),
|
||||
// label: "Syncing preferences",
|
||||
// value: 5,
|
||||
// group: selectedMenuItem,
|
||||
// onChanged: updateSelectedMenuItem,
|
||||
// ),
|
||||
// const SizedBox(
|
||||
// height: 2,
|
||||
// ),
|
||||
// SettingsMenuItem(
|
||||
// icon: SvgPicture.asset(
|
||||
// Assets.svg.polygon,
|
||||
// width: 11,
|
||||
// height: 11,
|
||||
// color: selectedMenuItem == 6
|
||||
// ? Theme.of(context)
|
||||
// .extension<StackColors>()!
|
||||
// .accentColorBlue
|
||||
// : Colors.transparent,
|
||||
// ),
|
||||
// label: "Appearance",
|
||||
// value: 6,
|
||||
// group: selectedMenuItem,
|
||||
// onChanged: updateSelectedMenuItem,
|
||||
// ),
|
||||
// const SizedBox(
|
||||
// height: 2,
|
||||
// ),
|
||||
// SettingsMenuItem(
|
||||
// icon: SvgPicture.asset(
|
||||
// Assets.svg.polygon,
|
||||
// width: 11,
|
||||
// height: 11,
|
||||
// color: selectedMenuItem == 7
|
||||
// ? Theme.of(context)
|
||||
// .extension<StackColors>()!
|
||||
// .accentColorBlue
|
||||
// : Colors.transparent,
|
||||
// ),
|
||||
// label: "Advanced",
|
||||
// value: 7,
|
||||
// group: selectedMenuItem,
|
||||
// onChanged: updateSelectedMenuItem,
|
||||
// ),
|
||||
],
|
||||
),
|
||||
),
|
||||
],
|
||||
);
|
||||
}
|
||||
}
|
|
@ -1,8 +1,8 @@
|
|||
import 'package:flutter/material.dart';
|
||||
import 'package:flutter/src/widgets/framework.dart';
|
||||
import 'package:flutter_riverpod/flutter_riverpod.dart';
|
||||
import 'package:flutter_svg/svg.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/home/settings_menu/advanced_settings/stack_privacy_dialog.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/settings/settings_menu/advanced_settings/debug_info_dialog.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/settings/settings_menu/advanced_settings/stack_privacy_dialog.dart';
|
||||
import 'package:stackwallet/providers/global/prefs_provider.dart';
|
||||
import 'package:stackwallet/utilities/assets.dart';
|
||||
import 'package:stackwallet/utilities/text_styles.dart';
|
||||
|
@ -11,8 +11,6 @@ import 'package:stackwallet/widgets/custom_buttons/draggable_switch_button.dart'
|
|||
import 'package:stackwallet/widgets/desktop/primary_button.dart';
|
||||
import 'package:stackwallet/widgets/rounded_white_container.dart';
|
||||
|
||||
import 'debug_info_dialog.dart';
|
||||
|
||||
class AdvancedSettings extends ConsumerStatefulWidget {
|
||||
const AdvancedSettings({Key? key}) : super(key: key);
|
||||
|
|
@ -0,0 +1,271 @@
|
|||
import 'package:flutter/material.dart';
|
||||
import 'package:flutter_riverpod/flutter_riverpod.dart';
|
||||
import 'package:flutter_svg/svg.dart';
|
||||
import 'package:stackwallet/hive/db.dart';
|
||||
import 'package:stackwallet/providers/global/prefs_provider.dart';
|
||||
import 'package:stackwallet/providers/ui/color_theme_provider.dart';
|
||||
import 'package:stackwallet/utilities/assets.dart';
|
||||
import 'package:stackwallet/utilities/constants.dart';
|
||||
import 'package:stackwallet/utilities/text_styles.dart';
|
||||
import 'package:stackwallet/utilities/theme/color_theme.dart';
|
||||
import 'package:stackwallet/utilities/theme/stack_colors.dart';
|
||||
import 'package:stackwallet/widgets/custom_buttons/draggable_switch_button.dart';
|
||||
import 'package:stackwallet/widgets/rounded_white_container.dart';
|
||||
|
||||
class AppearanceOptionSettings extends ConsumerStatefulWidget {
|
||||
const AppearanceOptionSettings({Key? key}) : super(key: key);
|
||||
|
||||
static const String routeName = "/settingsMenuAppearance";
|
||||
|
||||
@override
|
||||
ConsumerState<AppearanceOptionSettings> createState() =>
|
||||
_AppearanceOptionSettings();
|
||||
}
|
||||
|
||||
class _AppearanceOptionSettings
|
||||
extends ConsumerState<AppearanceOptionSettings> {
|
||||
@override
|
||||
Widget build(BuildContext context) {
|
||||
debugPrint("BUILD: $runtimeType");
|
||||
return Column(
|
||||
children: [
|
||||
Padding(
|
||||
padding: const EdgeInsets.only(
|
||||
right: 30,
|
||||
),
|
||||
child: RoundedWhiteContainer(
|
||||
radiusMultiplier: 2,
|
||||
child: Column(
|
||||
crossAxisAlignment: CrossAxisAlignment.start,
|
||||
children: [
|
||||
Padding(
|
||||
padding: const EdgeInsets.all(8.0),
|
||||
child: SvgPicture.asset(
|
||||
Assets.svg.circleSun,
|
||||
width: 48,
|
||||
height: 48,
|
||||
),
|
||||
),
|
||||
Column(
|
||||
crossAxisAlignment: CrossAxisAlignment.stretch,
|
||||
children: [
|
||||
Padding(
|
||||
padding: const EdgeInsets.all(10),
|
||||
child: RichText(
|
||||
textAlign: TextAlign.left,
|
||||
text: TextSpan(
|
||||
children: [
|
||||
TextSpan(
|
||||
text: "Appearances",
|
||||
style: STextStyles.desktopTextSmall(context),
|
||||
),
|
||||
TextSpan(
|
||||
text:
|
||||
"\n\nCustomize how your Stack Wallet looks according to your preferences.",
|
||||
style: STextStyles.desktopTextExtraExtraSmall(
|
||||
context),
|
||||
),
|
||||
],
|
||||
),
|
||||
),
|
||||
),
|
||||
],
|
||||
),
|
||||
const Padding(
|
||||
padding: EdgeInsets.all(10.0),
|
||||
child: Divider(
|
||||
thickness: 0.5,
|
||||
),
|
||||
),
|
||||
Padding(
|
||||
padding: const EdgeInsets.all(10.0),
|
||||
child: Row(
|
||||
mainAxisAlignment: MainAxisAlignment.spaceBetween,
|
||||
children: [
|
||||
Text(
|
||||
"Display favorite wallets",
|
||||
style: STextStyles.desktopTextExtraSmall(context)
|
||||
.copyWith(
|
||||
color: Theme.of(context)
|
||||
.extension<StackColors>()!
|
||||
.textDark),
|
||||
textAlign: TextAlign.left,
|
||||
),
|
||||
SizedBox(
|
||||
height: 20,
|
||||
width: 40,
|
||||
child: DraggableSwitchButton(
|
||||
isOn: ref.watch(
|
||||
prefsChangeNotifierProvider
|
||||
.select((value) => value.showFavoriteWallets),
|
||||
),
|
||||
onValueChanged: (newValue) {
|
||||
ref
|
||||
.read(prefsChangeNotifierProvider)
|
||||
.showFavoriteWallets = newValue;
|
||||
},
|
||||
),
|
||||
)
|
||||
],
|
||||
),
|
||||
),
|
||||
const Padding(
|
||||
padding: EdgeInsets.all(10.0),
|
||||
child: Divider(
|
||||
thickness: 0.5,
|
||||
),
|
||||
),
|
||||
Padding(
|
||||
padding: const EdgeInsets.all(10.0),
|
||||
child: Row(
|
||||
mainAxisAlignment: MainAxisAlignment.spaceBetween,
|
||||
children: [
|
||||
Text(
|
||||
"Choose theme",
|
||||
style: STextStyles.desktopTextExtraSmall(context)
|
||||
.copyWith(
|
||||
color: Theme.of(context)
|
||||
.extension<StackColors>()!
|
||||
.textDark),
|
||||
textAlign: TextAlign.left,
|
||||
),
|
||||
],
|
||||
),
|
||||
),
|
||||
const Padding(
|
||||
padding: EdgeInsets.all(10),
|
||||
child: ThemeToggle(),
|
||||
),
|
||||
],
|
||||
),
|
||||
),
|
||||
),
|
||||
],
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
class ThemeToggle extends ConsumerStatefulWidget {
|
||||
const ThemeToggle({
|
||||
Key? key,
|
||||
}) : super(key: key);
|
||||
|
||||
@override
|
||||
ConsumerState<ThemeToggle> createState() => _ThemeToggle();
|
||||
}
|
||||
|
||||
class _ThemeToggle extends ConsumerState<ThemeToggle> {
|
||||
String assetNameFor(ThemeType type) {
|
||||
switch (type) {
|
||||
case ThemeType.light:
|
||||
return Assets.svg.themeLight;
|
||||
case ThemeType.dark:
|
||||
return Assets.svg.themeDark;
|
||||
case ThemeType.oceanBreeze:
|
||||
return Assets.svg.themeOcean;
|
||||
}
|
||||
}
|
||||
|
||||
@override
|
||||
Widget build(BuildContext context) {
|
||||
return Row(
|
||||
children: [
|
||||
for (int i = 0; i < ThemeType.values.length; i++)
|
||||
Row(
|
||||
mainAxisSize: MainAxisSize.min,
|
||||
children: [
|
||||
if (i > 0)
|
||||
const SizedBox(
|
||||
width: 10,
|
||||
),
|
||||
MouseRegion(
|
||||
cursor: SystemMouseCursors.click,
|
||||
child: GestureDetector(
|
||||
onTap: () {
|
||||
if (ref.read(colorThemeProvider.state).state.themeType !=
|
||||
ThemeType.values[i]) {
|
||||
DB.instance.put<dynamic>(
|
||||
boxName: DB.boxNameTheme,
|
||||
key: "colorScheme",
|
||||
value: ThemeType.values[i].name,
|
||||
);
|
||||
ref.read(colorThemeProvider.state).state =
|
||||
StackColors.fromStackColorTheme(
|
||||
ThemeType.values[i].colorTheme);
|
||||
}
|
||||
},
|
||||
child: Container(
|
||||
width: 200,
|
||||
color: Colors.transparent,
|
||||
child: Column(
|
||||
mainAxisSize: MainAxisSize.min,
|
||||
children: [
|
||||
Container(
|
||||
decoration: BoxDecoration(
|
||||
border: Border.all(
|
||||
width: 2.5,
|
||||
color: ref
|
||||
.read(colorThemeProvider.state)
|
||||
.state
|
||||
.themeType ==
|
||||
ThemeType.values[i]
|
||||
? Theme.of(context)
|
||||
.extension<StackColors>()!
|
||||
.infoItemIcons
|
||||
: Theme.of(context)
|
||||
.extension<StackColors>()!
|
||||
.popupBG,
|
||||
),
|
||||
borderRadius: BorderRadius.circular(
|
||||
Constants.size.circularBorderRadius,
|
||||
),
|
||||
),
|
||||
child: SvgPicture.asset(
|
||||
assetNameFor(ThemeType.values[i]),
|
||||
),
|
||||
),
|
||||
const SizedBox(
|
||||
height: 12,
|
||||
),
|
||||
Row(
|
||||
children: [
|
||||
SizedBox(
|
||||
width: 20,
|
||||
height: 20,
|
||||
child: Radio<ThemeType>(
|
||||
activeColor: Theme.of(context)
|
||||
.extension<StackColors>()!
|
||||
.radioButtonIconEnabled,
|
||||
value: ThemeType.values[i],
|
||||
groupValue: ref
|
||||
.read(colorThemeProvider.state)
|
||||
.state
|
||||
.themeType,
|
||||
onChanged: (_) {},
|
||||
),
|
||||
),
|
||||
const SizedBox(
|
||||
width: 14,
|
||||
),
|
||||
Text(
|
||||
ThemeType.values[i].prettyName,
|
||||
style: STextStyles.desktopTextExtraSmall(context)
|
||||
.copyWith(
|
||||
color: Theme.of(context)
|
||||
.extension<StackColors>()!
|
||||
.textDark,
|
||||
),
|
||||
),
|
||||
],
|
||||
),
|
||||
],
|
||||
),
|
||||
),
|
||||
),
|
||||
)
|
||||
],
|
||||
),
|
||||
],
|
||||
);
|
||||
}
|
||||
}
|
|
@ -6,8 +6,8 @@ import 'package:intl/intl.dart';
|
|||
import 'package:stackwallet/pages/settings_views/global_settings_view/stack_backup_views/create_backup_view.dart';
|
||||
import 'package:stackwallet/pages/settings_views/global_settings_view/stack_backup_views/edit_auto_backup_view.dart';
|
||||
import 'package:stackwallet/pages/settings_views/global_settings_view/stack_backup_views/restore_from_file_view.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/home/settings_menu/backup_and_restore/create_auto_backup.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/home/settings_menu/backup_and_restore/enable_backup_dialog.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/settings/settings_menu/backup_and_restore/create_auto_backup.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/settings/settings_menu/backup_and_restore/enable_backup_dialog.dart';
|
||||
import 'package:stackwallet/providers/global/auto_swb_service_provider.dart';
|
||||
import 'package:stackwallet/providers/global/locale_provider.dart';
|
||||
import 'package:stackwallet/providers/global/prefs_provider.dart';
|
|
@ -1,5 +1,5 @@
|
|||
import 'package:flutter/material.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/home/settings_menu/backup_and_restore/create_auto_backup.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/settings/settings_menu/backup_and_restore/create_auto_backup.dart';
|
||||
import 'package:stackwallet/utilities/text_styles.dart';
|
||||
import 'package:stackwallet/utilities/theme/stack_colors.dart';
|
||||
import 'package:stackwallet/widgets/desktop/desktop_dialog.dart';
|
|
@ -1,7 +1,7 @@
|
|||
import 'package:flutter/material.dart';
|
||||
import 'package:flutter_riverpod/flutter_riverpod.dart';
|
||||
import 'package:flutter_svg/svg.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/home/settings_menu/language_settings/language_dialog.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/settings/settings_menu/language_settings/language_dialog.dart';
|
||||
import 'package:stackwallet/utilities/assets.dart';
|
||||
import 'package:stackwallet/utilities/text_styles.dart';
|
||||
import 'package:stackwallet/widgets/desktop/primary_button.dart';
|
|
@ -33,7 +33,7 @@ class SettingsMenuItem<T> extends StatelessWidget {
|
|||
onChanged(value);
|
||||
},
|
||||
child: Padding(
|
||||
padding: EdgeInsets.symmetric(
|
||||
padding: const EdgeInsets.symmetric(
|
||||
vertical: 16,
|
||||
horizontal: 16,
|
||||
),
|
|
@ -1,5 +1,5 @@
|
|||
import 'package:flutter_riverpod/flutter_riverpod.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/home/desktop_menu.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/desktop_menu.dart';
|
||||
|
||||
final currentDesktopMenuItemProvider =
|
||||
StateProvider<DesktopMenuItemId>((ref) => DesktopMenuItemId.myStack);
|
||||
|
|
|
@ -84,33 +84,34 @@ import 'package:stackwallet/pages/wallet_view/transaction_views/transaction_deta
|
|||
import 'package:stackwallet/pages/wallet_view/transaction_views/transaction_search_filter_view.dart';
|
||||
import 'package:stackwallet/pages/wallet_view/wallet_view.dart';
|
||||
import 'package:stackwallet/pages/wallets_view/wallets_view.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/create_password/create_password_view.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/address_book_view/desktop_address_book.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/desktop_exchange/desktop_all_trades_view.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/desktop_exchange/desktop_exchange_view.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/forgot_password_desktop_view.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/home/address_book_view/desktop_address_book.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/home/desktop_home_view.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/home/desktop_settings_view.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/home/my_stack_view/my_stack_view.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/home/my_stack_view/wallet_view/desktop_wallet_view.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/home/my_stack_view/wallet_view/sub_widgets/delete_wallet_keys_popup.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/home/my_stack_view/wallet_view/sub_widgets/desktop_attention_delete_wallet.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/home/my_stack_view/wallet_view/sub_widgets/desktop_delete_wallet_dialog.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/home/my_stack_view/wallet_view/sub_widgets/qr_code_desktop_popup_content.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/home/my_stack_view/wallet_view/sub_widgets/unlock_wallet_keys_desktop.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/home/my_stack_view/wallet_view/sub_widgets/wallet_keys_desktop_popup.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/home/notifications/desktop_notifications_view.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/home/settings_menu/advanced_settings/advanced_settings.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/home/settings_menu/appearance_settings.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/home/settings_menu/backup_and_restore/backup_and_restore_settings.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/home/settings_menu/currency_settings/currency_settings.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/home/settings_menu/language_settings/language_settings.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/home/settings_menu/nodes_settings.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/home/settings_menu/security_settings.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/home/settings_menu/settings_menu.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/home/settings_menu/syncing_preferences_settings.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/home/support_and_about_view/desktop_about_view.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/home/support_and_about_view/desktop_support_view.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/desktop_home_view.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/my_stack_view/my_stack_view.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/my_stack_view/wallet_view/desktop_wallet_view.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/my_stack_view/wallet_view/sub_widgets/delete_wallet_keys_popup.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/my_stack_view/wallet_view/sub_widgets/desktop_attention_delete_wallet.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/my_stack_view/wallet_view/sub_widgets/desktop_delete_wallet_dialog.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/my_stack_view/wallet_view/sub_widgets/qr_code_desktop_popup_content.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/my_stack_view/wallet_view/sub_widgets/unlock_wallet_keys_desktop.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/my_stack_view/wallet_view/sub_widgets/wallet_keys_desktop_popup.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/notifications/desktop_notifications_view.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/password/create_password_view.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/password/delete_password_warning_view.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/password/forgot_password_desktop_view.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/password/forgotten_passphrase_restore_from_swb.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/settings/desktop_settings_view.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/settings/settings_menu/advanced_settings/advanced_settings.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/settings/settings_menu/appearance_settings.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/settings/settings_menu/backup_and_restore/backup_and_restore_settings.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/settings/settings_menu/currency_settings/currency_settings.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/settings/settings_menu/desktop_about_view.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/settings/settings_menu/desktop_support_view.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/settings/settings_menu/language_settings/language_settings.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/settings/settings_menu/nodes_settings.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/settings/settings_menu/security_settings.dart';
|
||||
import 'package:stackwallet/pages_desktop_specific/settings/settings_menu/syncing_preferences_settings.dart';
|
||||
import 'package:stackwallet/services/coins/manager.dart';
|
||||
import 'package:stackwallet/services/event_bus/events/global/node_connection_status_changed_event.dart';
|
||||
import 'package:stackwallet/services/event_bus/events/global/wallet_sync_status_changed_event.dart';
|
||||
|
@ -1000,6 +1001,17 @@ class RouteGenerator {
|
|||
|
||||
// == Desktop specific routes ============================================
|
||||
case CreatePasswordView.routeName:
|
||||
if (args is bool) {
|
||||
return getRoute(
|
||||
shouldUseMaterialRoute: useMaterialPageRoute,
|
||||
builder: (_) => CreatePasswordView(
|
||||
restoreFromSWB: args,
|
||||
),
|
||||
settings: RouteSettings(
|
||||
name: settings.name,
|
||||
),
|
||||
);
|
||||
}
|
||||
return getRoute(
|
||||
shouldUseMaterialRoute: useMaterialPageRoute,
|
||||
builder: (_) => const CreatePasswordView(),
|
||||
|
@ -1011,6 +1023,26 @@ class RouteGenerator {
|
|||
builder: (_) => const ForgotPasswordDesktopView(),
|
||||
settings: RouteSettings(name: settings.name));
|
||||
|
||||
case ForgottenPassphraseRestoreFromSWB.routeName:
|
||||
return getRoute(
|
||||
shouldUseMaterialRoute: useMaterialPageRoute,
|
||||
builder: (_) => const ForgottenPassphraseRestoreFromSWB(),
|
||||
settings: RouteSettings(name: settings.name));
|
||||
|
||||
case DeletePasswordWarningView.routeName:
|
||||
if (args is bool) {
|
||||
return getRoute(
|
||||
shouldUseMaterialRoute: useMaterialPageRoute,
|
||||
builder: (_) => DeletePasswordWarningView(
|
||||
shouldCreateNew: args,
|
||||
),
|
||||
settings: RouteSettings(
|
||||
name: settings.name,
|
||||
),
|
||||
);
|
||||
}
|
||||
return _routeError("${settings.name} invalid args: ${args.toString()}");
|
||||
|
||||
case DesktopHomeView.routeName:
|
||||
return getRoute(
|
||||
shouldUseMaterialRoute: useMaterialPageRoute,
|
||||
|
@ -1061,14 +1093,6 @@ class RouteGenerator {
|
|||
}
|
||||
return _routeError("${settings.name} invalid args: ${args.toString()}");
|
||||
|
||||
case SettingsMenu.routeName:
|
||||
return getRoute(
|
||||
shouldUseMaterialRoute: useMaterialPageRoute,
|
||||
builder: (_) => SettingsMenu(
|
||||
onSelectionChanged: (int) {},
|
||||
),
|
||||
settings: RouteSettings(name: settings.name));
|
||||
|
||||
case BackupRestoreSettings.routeName:
|
||||
return getRoute(
|
||||
shouldUseMaterialRoute: useMaterialPageRoute,
|
||||
|
|
|
@ -1519,22 +1519,28 @@ class BitcoinWallet extends CoinServiceAPI {
|
|||
Logging.instance
|
||||
.log("IS_INTEGRATION_TEST: $integrationTestFlag", level: LogLevel.Info);
|
||||
if (!integrationTestFlag) {
|
||||
final features = await electrumXClient.getServerFeatures();
|
||||
Logging.instance.log("features: $features", level: LogLevel.Info);
|
||||
switch (coin) {
|
||||
case Coin.bitcoin:
|
||||
if (features['genesis_hash'] != GENESIS_HASH_MAINNET) {
|
||||
throw Exception("genesis hash does not match main net!");
|
||||
}
|
||||
break;
|
||||
case Coin.bitcoinTestNet:
|
||||
if (features['genesis_hash'] != GENESIS_HASH_TESTNET) {
|
||||
throw Exception("genesis hash does not match test net!");
|
||||
}
|
||||
break;
|
||||
default:
|
||||
throw Exception(
|
||||
"Attempted to generate a BitcoinWallet using a non bitcoin coin type: ${coin.name}");
|
||||
try {
|
||||
final features = await electrumXClient
|
||||
.getServerFeatures()
|
||||
.timeout(const Duration(seconds: 3));
|
||||
Logging.instance.log("features: $features", level: LogLevel.Info);
|
||||
switch (coin) {
|
||||
case Coin.bitcoin:
|
||||
if (features['genesis_hash'] != GENESIS_HASH_MAINNET) {
|
||||
throw Exception("genesis hash does not match main net!");
|
||||
}
|
||||
break;
|
||||
case Coin.bitcoinTestNet:
|
||||
if (features['genesis_hash'] != GENESIS_HASH_TESTNET) {
|
||||
throw Exception("genesis hash does not match test net!");
|
||||
}
|
||||
break;
|
||||
default:
|
||||
throw Exception(
|
||||
"Attempted to generate a BitcoinWallet using a non bitcoin coin type: ${coin.name}");
|
||||
}
|
||||
} catch (e, s) {
|
||||
Logging.instance.log("$e/n$s", level: LogLevel.Info);
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
@ -1405,22 +1405,28 @@ class BitcoinCashWallet extends CoinServiceAPI {
|
|||
Logging.instance
|
||||
.log("IS_INTEGRATION_TEST: $integrationTestFlag", level: LogLevel.Info);
|
||||
if (!integrationTestFlag) {
|
||||
final features = await electrumXClient.getServerFeatures();
|
||||
Logging.instance.log("features: $features", level: LogLevel.Info);
|
||||
switch (coin) {
|
||||
case Coin.bitcoincash:
|
||||
if (features['genesis_hash'] != GENESIS_HASH_MAINNET) {
|
||||
throw Exception("genesis hash does not match main net!");
|
||||
}
|
||||
break;
|
||||
case Coin.bitcoincashTestnet:
|
||||
if (features['genesis_hash'] != GENESIS_HASH_TESTNET) {
|
||||
throw Exception("genesis hash does not match test net!");
|
||||
}
|
||||
break;
|
||||
default:
|
||||
throw Exception(
|
||||
"Attempted to generate a BitcoinWallet using a non bitcoin coin type: ${coin.name}");
|
||||
try {
|
||||
final features = await electrumXClient
|
||||
.getServerFeatures()
|
||||
.timeout(const Duration(seconds: 3));
|
||||
Logging.instance.log("features: $features", level: LogLevel.Info);
|
||||
switch (coin) {
|
||||
case Coin.bitcoincash:
|
||||
if (features['genesis_hash'] != GENESIS_HASH_MAINNET) {
|
||||
throw Exception("genesis hash does not match main net!");
|
||||
}
|
||||
break;
|
||||
case Coin.bitcoincashTestnet:
|
||||
if (features['genesis_hash'] != GENESIS_HASH_TESTNET) {
|
||||
throw Exception("genesis hash does not match test net!");
|
||||
}
|
||||
break;
|
||||
default:
|
||||
throw Exception(
|
||||
"Attempted to generate a BitcoinWallet using a non bitcoin coin type: ${coin.name}");
|
||||
}
|
||||
} catch (e, s) {
|
||||
Logging.instance.log("$e/n$s", level: LogLevel.Info);
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
@ -1268,22 +1268,28 @@ class DogecoinWallet extends CoinServiceAPI {
|
|||
Logging.instance
|
||||
.log("IS_INTEGRATION_TEST: $integrationTestFlag", level: LogLevel.Info);
|
||||
if (!integrationTestFlag) {
|
||||
final features = await electrumXClient.getServerFeatures();
|
||||
Logging.instance.log("features: $features", level: LogLevel.Info);
|
||||
switch (coin) {
|
||||
case Coin.dogecoin:
|
||||
if (features['genesis_hash'] != GENESIS_HASH_MAINNET) {
|
||||
throw Exception("genesis hash does not match main net!");
|
||||
}
|
||||
break;
|
||||
case Coin.dogecoinTestNet:
|
||||
if (features['genesis_hash'] != GENESIS_HASH_TESTNET) {
|
||||
throw Exception("genesis hash does not match test net!");
|
||||
}
|
||||
break;
|
||||
default:
|
||||
throw Exception(
|
||||
"Attempted to generate a BitcoinWallet using a non bitcoin coin type: ${coin.name}");
|
||||
try {
|
||||
final features = await electrumXClient
|
||||
.getServerFeatures()
|
||||
.timeout(const Duration(seconds: 3));
|
||||
Logging.instance.log("features: $features", level: LogLevel.Info);
|
||||
switch (coin) {
|
||||
case Coin.dogecoin:
|
||||
if (features['genesis_hash'] != GENESIS_HASH_MAINNET) {
|
||||
throw Exception("genesis hash does not match main net!");
|
||||
}
|
||||
break;
|
||||
case Coin.dogecoinTestNet:
|
||||
if (features['genesis_hash'] != GENESIS_HASH_TESTNET) {
|
||||
throw Exception("genesis hash does not match test net!");
|
||||
}
|
||||
break;
|
||||
default:
|
||||
throw Exception(
|
||||
"Attempted to generate a BitcoinWallet using a non bitcoin coin type: ${coin.name}");
|
||||
}
|
||||
} catch (e, s) {
|
||||
Logging.instance.log("$e/n$s", level: LogLevel.Info);
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
@ -2148,32 +2148,29 @@ class FiroWallet extends CoinServiceAPI {
|
|||
Logging.instance
|
||||
.log("IS_INTEGRATION_TEST: $integrationTestFlag", level: LogLevel.Info);
|
||||
if (!integrationTestFlag) {
|
||||
final features = await electrumXClient.getServerFeatures();
|
||||
Logging.instance.log("features: $features", level: LogLevel.Info);
|
||||
switch (coin) {
|
||||
case Coin.firo:
|
||||
if (features['genesis_hash'] != GENESIS_HASH_MAINNET) {
|
||||
throw Exception("genesis hash does not match main net!");
|
||||
}
|
||||
break;
|
||||
case Coin.firoTestNet:
|
||||
if (features['genesis_hash'] != GENESIS_HASH_TESTNET) {
|
||||
throw Exception("genesis hash does not match test net!");
|
||||
}
|
||||
break;
|
||||
default:
|
||||
throw Exception(
|
||||
"Attempted to generate a FiroWallet using a non firo coin type: ${coin.name}");
|
||||
try {
|
||||
final features = await electrumXClient
|
||||
.getServerFeatures()
|
||||
.timeout(const Duration(seconds: 3));
|
||||
Logging.instance.log("features: $features", level: LogLevel.Info);
|
||||
switch (coin) {
|
||||
case Coin.firo:
|
||||
if (features['genesis_hash'] != GENESIS_HASH_MAINNET) {
|
||||
throw Exception("genesis hash does not match main net!");
|
||||
}
|
||||
break;
|
||||
case Coin.firoTestNet:
|
||||
if (features['genesis_hash'] != GENESIS_HASH_TESTNET) {
|
||||
throw Exception("genesis hash does not match test net!");
|
||||
}
|
||||
break;
|
||||
default:
|
||||
throw Exception(
|
||||
"Attempted to generate a FiroWallet using a non firo coin type: ${coin.name}");
|
||||
}
|
||||
} catch (e, s) {
|
||||
Logging.instance.log("$e/n$s", level: LogLevel.Info);
|
||||
}
|
||||
// if (_networkType == BasicNetworkType.main) {
|
||||
// if (features['genesis_hash'] != GENESIS_HASH_MAINNET) {
|
||||
// throw Exception("genesis hash does not match!");
|
||||
// }
|
||||
// } else if (_networkType == BasicNetworkType.test) {
|
||||
// if (features['genesis_hash'] != GENESIS_HASH_TESTNET) {
|
||||
// throw Exception("genesis hash does not match!");
|
||||
// }
|
||||
// }
|
||||
}
|
||||
|
||||
// this should never fail as overwriting a mnemonic is big bad
|
||||
|
|
|
@ -1521,23 +1521,29 @@ class LitecoinWallet extends CoinServiceAPI {
|
|||
Logging.instance
|
||||
.log("IS_INTEGRATION_TEST: $integrationTestFlag", level: LogLevel.Info);
|
||||
if (!integrationTestFlag) {
|
||||
final features = await electrumXClient.getServerFeatures();
|
||||
Logging.instance.log("features: $features", level: LogLevel.Info);
|
||||
switch (coin) {
|
||||
case Coin.litecoin:
|
||||
if (features['genesis_hash'] != GENESIS_HASH_MAINNET) {
|
||||
print(features['genesis_hash']);
|
||||
throw Exception("genesis hash does not match main net!");
|
||||
}
|
||||
break;
|
||||
case Coin.litecoinTestNet:
|
||||
if (features['genesis_hash'] != GENESIS_HASH_TESTNET) {
|
||||
throw Exception("genesis hash does not match test net!");
|
||||
}
|
||||
break;
|
||||
default:
|
||||
throw Exception(
|
||||
"Attempted to generate a LitecoinWallet using a non litecoin coin type: ${coin.name}");
|
||||
try {
|
||||
final features = await electrumXClient
|
||||
.getServerFeatures()
|
||||
.timeout(const Duration(seconds: 3));
|
||||
Logging.instance.log("features: $features", level: LogLevel.Info);
|
||||
switch (coin) {
|
||||
case Coin.litecoin:
|
||||
if (features['genesis_hash'] != GENESIS_HASH_MAINNET) {
|
||||
print(features['genesis_hash']);
|
||||
throw Exception("genesis hash does not match main net!");
|
||||
}
|
||||
break;
|
||||
case Coin.litecoinTestNet:
|
||||
if (features['genesis_hash'] != GENESIS_HASH_TESTNET) {
|
||||
throw Exception("genesis hash does not match test net!");
|
||||
}
|
||||
break;
|
||||
default:
|
||||
throw Exception(
|
||||
"Attempted to generate a LitecoinWallet using a non litecoin coin type: ${coin.name}");
|
||||
}
|
||||
} catch (e, s) {
|
||||
Logging.instance.log("$e/n$s", level: LogLevel.Info);
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
@ -344,27 +344,24 @@ class NamecoinWallet extends CoinServiceAPI {
|
|||
Logging.instance.log("IS_INTEGRATION_TEST: $integrationTestFlag",
|
||||
level: LogLevel.Info);
|
||||
if (!integrationTestFlag) {
|
||||
final features = await electrumXClient.getServerFeatures();
|
||||
Logging.instance.log("features: $features", level: LogLevel.Info);
|
||||
switch (coin) {
|
||||
case Coin.namecoin:
|
||||
if (features['genesis_hash'] != GENESIS_HASH_MAINNET) {
|
||||
throw Exception("genesis hash does not match main net!");
|
||||
}
|
||||
break;
|
||||
default:
|
||||
throw Exception(
|
||||
"Attempted to generate a NamecoinWallet using a non namecoin coin type: ${coin.name}");
|
||||
try {
|
||||
final features = await electrumXClient
|
||||
.getServerFeatures()
|
||||
.timeout(const Duration(seconds: 3));
|
||||
Logging.instance.log("features: $features", level: LogLevel.Info);
|
||||
switch (coin) {
|
||||
case Coin.namecoin:
|
||||
if (features['genesis_hash'] != GENESIS_HASH_MAINNET) {
|
||||
throw Exception("genesis hash does not match main net!");
|
||||
}
|
||||
break;
|
||||
default:
|
||||
throw Exception(
|
||||
"Attempted to generate a NamecoinWallet using a non namecoin coin type: ${coin.name}");
|
||||
}
|
||||
} catch (e, s) {
|
||||
Logging.instance.log("$e/n$s", level: LogLevel.Info);
|
||||
}
|
||||
// if (_networkType == BasicNetworkType.main) {
|
||||
// if (features['genesis_hash'] != GENESIS_HASH_MAINNET) {
|
||||
// throw Exception("genesis hash does not match main net!");
|
||||
// }
|
||||
// } else if (_networkType == BasicNetworkType.test) {
|
||||
// if (features['genesis_hash'] != GENESIS_HASH_TESTNET) {
|
||||
// throw Exception("genesis hash does not match test net!");
|
||||
// }
|
||||
// }
|
||||
}
|
||||
// check to make sure we aren't overwriting a mnemonic
|
||||
// this should never fail
|
||||
|
|
|
@ -73,6 +73,17 @@ class Wallets extends ChangeNotifier {
|
|||
return result;
|
||||
}
|
||||
|
||||
List<ChangeNotifierProvider<Manager>> getManagerProvidersForCoin(Coin coin) {
|
||||
List<ChangeNotifierProvider<Manager>> result = [];
|
||||
for (final manager in _managerMap.values) {
|
||||
if (manager.coin == coin) {
|
||||
result.add(_managerProviderMap[manager.walletId]
|
||||
as ChangeNotifierProvider<Manager>);
|
||||
}
|
||||
}
|
||||
return result;
|
||||
}
|
||||
|
||||
ChangeNotifierProvider<Manager> getManagerProvider(String walletId) {
|
||||
return _managerProviderMap[walletId] as ChangeNotifierProvider<Manager>;
|
||||
}
|
||||
|
|
|
@ -37,6 +37,15 @@ abstract class SecureStorageInterface {
|
|||
MacOsOptions? mOptions,
|
||||
WindowsOptions? wOptions,
|
||||
});
|
||||
|
||||
Future<void> deleteAll({
|
||||
IOSOptions? iOptions,
|
||||
AndroidOptions? aOptions,
|
||||
LinuxOptions? lOptions,
|
||||
WebOptions? webOptions,
|
||||
MacOsOptions? mOptions,
|
||||
WindowsOptions? wOptions,
|
||||
});
|
||||
}
|
||||
|
||||
class DesktopSecureStore {
|
||||
|
@ -54,6 +63,10 @@ class DesktopSecureStore {
|
|||
);
|
||||
}
|
||||
|
||||
Future<void> close() async {
|
||||
await isar.close();
|
||||
}
|
||||
|
||||
Future<String?> read({
|
||||
required String key,
|
||||
}) async {
|
||||
|
@ -192,6 +205,30 @@ class SecureStorageWrapper implements SecureStorageInterface {
|
|||
);
|
||||
}
|
||||
}
|
||||
|
||||
@override
|
||||
Future<void> deleteAll({
|
||||
IOSOptions? iOptions,
|
||||
AndroidOptions? aOptions,
|
||||
LinuxOptions? lOptions,
|
||||
WebOptions? webOptions,
|
||||
MacOsOptions? mOptions,
|
||||
WindowsOptions? wOptions,
|
||||
}) async {
|
||||
if (_isDesktop) {
|
||||
// return (_store as DesktopSecureStore).deleteAll();
|
||||
throw UnimplementedError();
|
||||
} else {
|
||||
return await (_store as FlutterSecureStorage).deleteAll(
|
||||
iOptions: iOptions,
|
||||
aOptions: aOptions,
|
||||
lOptions: lOptions,
|
||||
webOptions: webOptions,
|
||||
mOptions: mOptions,
|
||||
wOptions: wOptions,
|
||||
);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// Mock class for testing purposes
|
||||
|
@ -252,6 +289,20 @@ class FakeSecureStorage implements SecureStorageInterface {
|
|||
_store.remove(key);
|
||||
}
|
||||
|
||||
@override
|
||||
Future<void> deleteAll({
|
||||
IOSOptions? iOptions,
|
||||
AndroidOptions? aOptions,
|
||||
LinuxOptions? lOptions,
|
||||
WebOptions? webOptions,
|
||||
MacOsOptions? mOptions,
|
||||
WindowsOptions? wOptions,
|
||||
}) async {
|
||||
_interactions++;
|
||||
_deletes++;
|
||||
_store.clear();
|
||||
}
|
||||
|
||||
@override
|
||||
dynamic get store => throw UnimplementedError();
|
||||
}
|
||||
|
|
Some files were not shown because too many files have changed in this diff Show more
Loading…
Reference in a new issue