enh: refactor Transacation in progress screen with uuid per transaction
This commit is contained in:
parent
8ca0b00a60
commit
007d62054b
|
@ -1,7 +1,6 @@
|
||||||
// ignore_for_file: use_build_context_synchronously, body_might_complete_normally_catch_error
|
// ignore_for_file: use_build_context_synchronously, body_might_complete_normally_catch_error
|
||||||
|
|
||||||
import 'dart:convert';
|
import 'dart:convert';
|
||||||
|
|
||||||
import 'package:easy_localization/easy_localization.dart';
|
import 'package:easy_localization/easy_localization.dart';
|
||||||
import 'package:fast_base58/fast_base58.dart';
|
import 'package:fast_base58/fast_base58.dart';
|
||||||
import 'package:flutter/foundation.dart';
|
import 'package:flutter/foundation.dart';
|
||||||
|
@ -26,6 +25,7 @@ import 'package:provider/provider.dart';
|
||||||
import 'package:truncate/truncate.dart';
|
import 'package:truncate/truncate.dart';
|
||||||
import 'package:pointycastle/pointycastle.dart' as pc;
|
import 'package:pointycastle/pointycastle.dart' as pc;
|
||||||
import "package:hex/hex.dart";
|
import "package:hex/hex.dart";
|
||||||
|
import 'package:uuid/uuid.dart' show Uuid;
|
||||||
|
|
||||||
class SubstrateSdk with ChangeNotifier {
|
class SubstrateSdk with ChangeNotifier {
|
||||||
final WalletSDK sdk = WalletSDK();
|
final WalletSDK sdk = WalletSDK();
|
||||||
|
@ -37,8 +37,8 @@ class SubstrateSdk with ChangeNotifier {
|
||||||
bool importIsLoading = false;
|
bool importIsLoading = false;
|
||||||
int blocNumber = 0;
|
int blocNumber = 0;
|
||||||
bool isLoadingEndpoint = false;
|
bool isLoadingEndpoint = false;
|
||||||
String? transactionStatus;
|
Map transactionStatus = {};
|
||||||
final int initSs58 = 42;
|
static const int initSs58 = 42;
|
||||||
Map<String, int> currencyParameters = {};
|
Map<String, int> currencyParameters = {};
|
||||||
final csSalt = TextEditingController();
|
final csSalt = TextEditingController();
|
||||||
final csPassword = TextEditingController();
|
final csPassword = TextEditingController();
|
||||||
|
@ -52,18 +52,23 @@ class SubstrateSdk with ChangeNotifier {
|
||||||
|
|
||||||
/////////////////////////////////////
|
/////////////////////////////////////
|
||||||
////////// 1: API METHODS ///////////
|
////////// 1: API METHODS ///////////
|
||||||
/////////////////////////////////////3
|
/////////////////////////////////////
|
||||||
|
|
||||||
Future<String> _executeCall(TxInfoData txInfo, txOptions, String password,
|
Future<String> _executeCall(String currentTransactionId, TxInfoData txInfo,
|
||||||
|
txOptions, String password,
|
||||||
[String? rawParams]) async {
|
[String? rawParams]) async {
|
||||||
final walletOptions =
|
final walletOptions =
|
||||||
Provider.of<WalletOptionsProvider>(homeContext, listen: false);
|
Provider.of<WalletOptionsProvider>(homeContext, listen: false);
|
||||||
final walletProfiles =
|
final walletProfiles =
|
||||||
Provider.of<WalletsProfilesProvider>(homeContext, listen: false);
|
Provider.of<WalletsProfilesProvider>(homeContext, listen: false);
|
||||||
|
transactionStatus.putIfAbsent(currentTransactionId, () => 'sending');
|
||||||
|
notifyListeners();
|
||||||
|
|
||||||
try {
|
try {
|
||||||
final hash = await sdk.api.tx.signAndSend(txInfo, txOptions, password,
|
final hash = await sdk.api.tx.signAndSend(txInfo, txOptions, password,
|
||||||
rawParam: rawParams, onStatusChange: (p0) {
|
rawParam: rawParams, onStatusChange: (p0) {
|
||||||
transactionStatus = p0;
|
transactionStatus.update(currentTransactionId, (_) => p0,
|
||||||
|
ifAbsent: () => p0);
|
||||||
notifyListeners();
|
notifyListeners();
|
||||||
}).timeout(
|
}).timeout(
|
||||||
const Duration(seconds: 18),
|
const Duration(seconds: 18),
|
||||||
|
@ -71,20 +76,23 @@ class SubstrateSdk with ChangeNotifier {
|
||||||
);
|
);
|
||||||
log.d(hash);
|
log.d(hash);
|
||||||
if (hash.isEmpty) {
|
if (hash.isEmpty) {
|
||||||
transactionStatus = 'Exception: timeout';
|
transactionStatus.update(
|
||||||
|
currentTransactionId, (_) => 'Exception: timeout');
|
||||||
notifyListeners();
|
notifyListeners();
|
||||||
|
|
||||||
return 'Exception: timeout';
|
return 'Exception: timeout';
|
||||||
} else {
|
} else {
|
||||||
// Success !
|
// Success !
|
||||||
transactionStatus = hash.toString();
|
transactionStatus.update(currentTransactionId, (_) => hash.toString(),
|
||||||
|
ifAbsent: () => hash.toString());
|
||||||
notifyListeners();
|
notifyListeners();
|
||||||
walletOptions.reload();
|
walletOptions.reload();
|
||||||
walletProfiles.reload();
|
walletProfiles.reload();
|
||||||
return hash.toString();
|
return hash.toString();
|
||||||
}
|
}
|
||||||
} catch (e) {
|
} catch (e) {
|
||||||
transactionStatus = e.toString();
|
transactionStatus.update(currentTransactionId, (_) => e.toString(),
|
||||||
|
ifAbsent: () => e.toString());
|
||||||
notifyListeners();
|
notifyListeners();
|
||||||
return e.toString();
|
return e.toString();
|
||||||
}
|
}
|
||||||
|
@ -909,8 +917,6 @@ class SubstrateSdk with ChangeNotifier {
|
||||||
required String destAddress,
|
required String destAddress,
|
||||||
required double amount,
|
required double amount,
|
||||||
required String password}) async {
|
required String password}) async {
|
||||||
transactionStatus = 'sending';
|
|
||||||
|
|
||||||
final sender = await _setSender(fromAddress);
|
final sender = await _setSender(fromAddress);
|
||||||
|
|
||||||
final globalBalance = await getBalance(fromAddress);
|
final globalBalance = await getBalance(fromAddress);
|
||||||
|
@ -956,13 +962,13 @@ class SubstrateSdk with ChangeNotifier {
|
||||||
rawParams = '[[$tx1, $tx2]]';
|
rawParams = '[[$tx1, $tx2]]';
|
||||||
}
|
}
|
||||||
|
|
||||||
return await _executeCall(txInfo, txOptions, password, rawParams);
|
final transactionId = const Uuid().v4();
|
||||||
|
_executeCall(transactionId, txInfo, txOptions, password, rawParams);
|
||||||
|
return transactionId;
|
||||||
}
|
}
|
||||||
|
|
||||||
Future<String> certify(
|
Future<String> certify(
|
||||||
String fromAddress, String destAddress, String password) async {
|
String fromAddress, String destAddress, String password) async {
|
||||||
transactionStatus = 'sending';
|
|
||||||
|
|
||||||
final statusList = await idtyStatus([fromAddress, destAddress]);
|
final statusList = await idtyStatus([fromAddress, destAddress]);
|
||||||
final myIdtyStatus = statusList[0];
|
final myIdtyStatus = statusList[0];
|
||||||
final toIdtyStatus = statusList[1];
|
final toIdtyStatus = statusList[1];
|
||||||
|
@ -973,8 +979,6 @@ class SubstrateSdk with ChangeNotifier {
|
||||||
final toIndex = idtyIndexList[1];
|
final toIndex = idtyIndexList[1];
|
||||||
|
|
||||||
if (myIdtyStatus != IdtyStatus.validated) {
|
if (myIdtyStatus != IdtyStatus.validated) {
|
||||||
transactionStatus = 'notMember';
|
|
||||||
notifyListeners();
|
|
||||||
return 'notMember';
|
return 'notMember';
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1022,18 +1026,17 @@ class SubstrateSdk with ChangeNotifier {
|
||||||
txOptions = [fromIndex, toIndex];
|
txOptions = [fromIndex, toIndex];
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
transactionStatus = 'cantBeCert';
|
|
||||||
notifyListeners();
|
|
||||||
return 'cantBeCert';
|
return 'cantBeCert';
|
||||||
}
|
}
|
||||||
|
|
||||||
log.d('Cert action: ${txInfo.call!}');
|
log.d('Cert action: ${txInfo.call!}');
|
||||||
return await _executeCall(txInfo, txOptions, password, rawParams);
|
final transactionId = const Uuid().v4();
|
||||||
|
_executeCall(transactionId, txInfo, txOptions, password, rawParams);
|
||||||
|
return transactionId;
|
||||||
}
|
}
|
||||||
|
|
||||||
Future<String> confirmIdentity(
|
Future<String> confirmIdentity(
|
||||||
String fromAddress, String name, String password) async {
|
String fromAddress, String name, String password) async {
|
||||||
transactionStatus = 'sending';
|
|
||||||
final sender = await _setSender(fromAddress);
|
final sender = await _setSender(fromAddress);
|
||||||
|
|
||||||
final txInfo = TxInfoData(
|
final txInfo = TxInfoData(
|
||||||
|
@ -1043,7 +1046,11 @@ class SubstrateSdk with ChangeNotifier {
|
||||||
);
|
);
|
||||||
final txOptions = [name];
|
final txOptions = [name];
|
||||||
|
|
||||||
return await _executeCall(txInfo, txOptions, password);
|
final transactionId = const Uuid().v4();
|
||||||
|
|
||||||
|
_executeCall(transactionId, txInfo, txOptions, password);
|
||||||
|
|
||||||
|
return transactionId;
|
||||||
}
|
}
|
||||||
|
|
||||||
Future<String> migrateIdentity(
|
Future<String> migrateIdentity(
|
||||||
|
@ -1053,7 +1060,6 @@ class SubstrateSdk with ChangeNotifier {
|
||||||
required String destPassword,
|
required String destPassword,
|
||||||
required Map fromBalance,
|
required Map fromBalance,
|
||||||
bool withBalance = false}) async {
|
bool withBalance = false}) async {
|
||||||
transactionStatus = 'sending';
|
|
||||||
final sender = await _setSender(fromAddress);
|
final sender = await _setSender(fromAddress);
|
||||||
|
|
||||||
TxInfoData txInfo;
|
TxInfoData txInfo;
|
||||||
|
@ -1111,7 +1117,9 @@ newKeySig: $newKeySigType""");
|
||||||
txOptions = [destAddress, newKeySigType];
|
txOptions = [destAddress, newKeySigType];
|
||||||
}
|
}
|
||||||
|
|
||||||
return await _executeCall(txInfo, txOptions, fromPassword, rawParams);
|
final transactionId = const Uuid().v4();
|
||||||
|
_executeCall(transactionId, txInfo, txOptions, fromPassword, rawParams);
|
||||||
|
return transactionId;
|
||||||
}
|
}
|
||||||
|
|
||||||
Future revokeIdentity(String address, String password) async {
|
Future revokeIdentity(String address, String password) async {
|
||||||
|
@ -1135,10 +1143,12 @@ newKeySig: $newKeySigType""");
|
||||||
);
|
);
|
||||||
|
|
||||||
final txOptions = [idtyIndex, address, revocationSigTyped];
|
final txOptions = [idtyIndex, address, revocationSigTyped];
|
||||||
return await _executeCall(txInfo, txOptions, password);
|
final transactionId = const Uuid().v4();
|
||||||
|
_executeCall(transactionId, txInfo, txOptions, password);
|
||||||
|
return transactionId;
|
||||||
}
|
}
|
||||||
|
|
||||||
Future migrateCsToV2(String salt, String password, String destAddress,
|
Future<String> migrateCsToV2(String salt, String password, String destAddress,
|
||||||
{required destPassword,
|
{required destPassword,
|
||||||
required Map balance,
|
required Map balance,
|
||||||
IdtyStatus idtyStatus = IdtyStatus.none}) async {
|
IdtyStatus idtyStatus = IdtyStatus.none}) async {
|
||||||
|
@ -1171,8 +1181,10 @@ newKeySig: $newKeySigType""");
|
||||||
password: password,
|
password: password,
|
||||||
);
|
);
|
||||||
|
|
||||||
|
late String transactionId;
|
||||||
|
|
||||||
if (idtyStatus != IdtyStatus.none) {
|
if (idtyStatus != IdtyStatus.none) {
|
||||||
await migrateIdentity(
|
transactionId = await migrateIdentity(
|
||||||
fromAddress: keypair.address!,
|
fromAddress: keypair.address!,
|
||||||
destAddress: destAddress,
|
destAddress: destAddress,
|
||||||
fromPassword: 'password',
|
fromPassword: 'password',
|
||||||
|
@ -1180,14 +1192,17 @@ newKeySig: $newKeySigType""");
|
||||||
withBalance: true,
|
withBalance: true,
|
||||||
fromBalance: balance);
|
fromBalance: balance);
|
||||||
} else if (balance['transferableBalance'] != 0) {
|
} else if (balance['transferableBalance'] != 0) {
|
||||||
await pay(
|
transactionId = await pay(
|
||||||
fromAddress: keypair.address!,
|
fromAddress: keypair.address!,
|
||||||
destAddress: destAddress,
|
destAddress: destAddress,
|
||||||
amount: -1,
|
amount: -1,
|
||||||
password: 'password');
|
password: 'password');
|
||||||
|
} else {
|
||||||
|
transactionId = '';
|
||||||
}
|
}
|
||||||
|
|
||||||
await sdk.api.keyring.deleteAccount(keyring, keypair);
|
await sdk.api.keyring.deleteAccount(keyring, keypair);
|
||||||
|
return transactionId;
|
||||||
}
|
}
|
||||||
|
|
||||||
Future spawnBlock([int number = 1, int until = 0]) async {
|
Future spawnBlock([int number = 1, int until = 0]) async {
|
||||||
|
@ -1204,6 +1219,10 @@ newKeySig: $newKeySigType""");
|
||||||
void reload() {
|
void reload() {
|
||||||
notifyListeners();
|
notifyListeners();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void resetTransactionStatus() {
|
||||||
|
transactionStatus.clear();
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
////////////////////////////////////////////
|
////////////////////////////////////////////
|
||||||
|
|
|
@ -217,14 +217,17 @@ class WalletOptionsProvider with ChangeNotifier {
|
||||||
final wallet = myWalletProvider
|
final wallet = myWalletProvider
|
||||||
.getWalletDataByAddress(address.text);
|
.getWalletDataByAddress(address.text);
|
||||||
await sub.setCurrentWallet(wallet!);
|
await sub.setCurrentWallet(wallet!);
|
||||||
sub.confirmIdentity(walletOptions.address.text,
|
final transactionId = await sub.confirmIdentity(
|
||||||
idtyName.text, myWalletProvider.pinCode);
|
walletOptions.address.text,
|
||||||
|
idtyName.text,
|
||||||
|
myWalletProvider.pinCode);
|
||||||
Navigator.pop(context);
|
Navigator.pop(context);
|
||||||
|
|
||||||
Navigator.push(
|
Navigator.push(
|
||||||
context,
|
context,
|
||||||
MaterialPageRoute(builder: (context) {
|
MaterialPageRoute(builder: (context) {
|
||||||
return TransactionInProgress(
|
return TransactionInProgress(
|
||||||
|
transactionId: transactionId,
|
||||||
transType: 'comfirmIdty',
|
transType: 'comfirmIdty',
|
||||||
fromAddress:
|
fromAddress:
|
||||||
getShortPubkey(wallet.address),
|
getShortPubkey(wallet.address),
|
||||||
|
|
|
@ -39,8 +39,9 @@ class DebugScreen extends StatelessWidget {
|
||||||
width: 250,
|
width: 250,
|
||||||
child: ElevatedButton(
|
child: ElevatedButton(
|
||||||
style: ElevatedButton.styleFrom(
|
style: ElevatedButton.styleFrom(
|
||||||
foregroundColor: Colors.white, elevation: 4,
|
foregroundColor: Colors.white,
|
||||||
backgroundColor: orangeC, // foreground
|
elevation: 4,
|
||||||
|
backgroundColor: orangeC,
|
||||||
),
|
),
|
||||||
onPressed: () async => await sub.spawnBlock(),
|
onPressed: () async => await sub.spawnBlock(),
|
||||||
child: const Text(
|
child: const Text(
|
||||||
|
|
|
@ -322,8 +322,9 @@ Widget welcomeHome(context) {
|
||||||
child: ElevatedButton(
|
child: ElevatedButton(
|
||||||
key: keyOnboardingNewChest,
|
key: keyOnboardingNewChest,
|
||||||
style: ElevatedButton.styleFrom(
|
style: ElevatedButton.styleFrom(
|
||||||
foregroundColor: Colors.white, elevation: 4,
|
foregroundColor: Colors.white,
|
||||||
backgroundColor: orangeC, // foreground
|
elevation: 4,
|
||||||
|
backgroundColor: orangeC,
|
||||||
),
|
),
|
||||||
onPressed: () {
|
onPressed: () {
|
||||||
Navigator.push(
|
Navigator.push(
|
||||||
|
|
|
@ -93,8 +93,9 @@ class _ChangePinScreenState extends State<ChangePinScreen> {
|
||||||
height: 50,
|
height: 50,
|
||||||
child: ElevatedButton(
|
child: ElevatedButton(
|
||||||
style: ElevatedButton.styleFrom(
|
style: ElevatedButton.styleFrom(
|
||||||
foregroundColor: Colors.black, elevation: 12,
|
foregroundColor: Colors.black,
|
||||||
backgroundColor: Colors.green[400], // foreground
|
elevation: 12,
|
||||||
|
backgroundColor: Colors.green[400],
|
||||||
),
|
),
|
||||||
onPressed: () async {
|
onPressed: () async {
|
||||||
WalletData defaultWallet =
|
WalletData defaultWallet =
|
||||||
|
|
|
@ -106,7 +106,7 @@ class _ChooseChestState extends State<ChooseChest> {
|
||||||
child: ElevatedButton(
|
child: ElevatedButton(
|
||||||
style: ElevatedButton.styleFrom(
|
style: ElevatedButton.styleFrom(
|
||||||
foregroundColor: Colors.black,
|
foregroundColor: Colors.black,
|
||||||
backgroundColor: orangeC, // foreground
|
backgroundColor: orangeC,
|
||||||
),
|
),
|
||||||
onPressed: () async {
|
onPressed: () async {
|
||||||
await configBox.put('currentChest', currentChest);
|
await configBox.put('currentChest', currentChest);
|
||||||
|
|
|
@ -22,6 +22,7 @@ import 'package:provider/provider.dart';
|
||||||
|
|
||||||
class ImportG1v1 extends StatelessWidget {
|
class ImportG1v1 extends StatelessWidget {
|
||||||
const ImportG1v1({Key? key}) : super(key: key);
|
const ImportG1v1({Key? key}) : super(key: key);
|
||||||
|
static const int debouneTime = 600;
|
||||||
|
|
||||||
@override
|
@override
|
||||||
Widget build(BuildContext context) {
|
Widget build(BuildContext context) {
|
||||||
|
@ -29,7 +30,6 @@ class ImportG1v1 extends StatelessWidget {
|
||||||
Provider.of<MyWalletsProvider>(context, listen: false);
|
Provider.of<MyWalletsProvider>(context, listen: false);
|
||||||
|
|
||||||
Timer? debounce;
|
Timer? debounce;
|
||||||
const int debouneTime = 600;
|
|
||||||
WalletData selectedWallet = myWalletProvider.getDefaultWallet();
|
WalletData selectedWallet = myWalletProvider.getDefaultWallet();
|
||||||
bool canValidate = false;
|
bool canValidate = false;
|
||||||
String validationStatus = '';
|
String validationStatus = '';
|
||||||
|
@ -297,8 +297,10 @@ class ImportG1v1 extends StatelessWidget {
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
sub.migrateCsToV2(sub.csSalt.text,
|
final transactionId = await sub.migrateCsToV2(
|
||||||
sub.csPassword.text, selectedWallet.address,
|
sub.csSalt.text,
|
||||||
|
sub.csPassword.text,
|
||||||
|
selectedWallet.address,
|
||||||
destPassword:
|
destPassword:
|
||||||
pin ?? myWalletProvider.pinCode,
|
pin ?? myWalletProvider.pinCode,
|
||||||
balance: balance,
|
balance: balance,
|
||||||
|
@ -308,6 +310,7 @@ class ImportG1v1 extends StatelessWidget {
|
||||||
context,
|
context,
|
||||||
MaterialPageRoute(builder: (context) {
|
MaterialPageRoute(builder: (context) {
|
||||||
return TransactionInProgress(
|
return TransactionInProgress(
|
||||||
|
transactionId: transactionId,
|
||||||
transType: 'identityMigration',
|
transType: 'identityMigration',
|
||||||
fromAddress:
|
fromAddress:
|
||||||
getShortPubkey(sub.g1V1NewAddress),
|
getShortPubkey(sub.g1V1NewAddress),
|
||||||
|
|
|
@ -109,38 +109,41 @@ class ManageMembership extends StatelessWidget {
|
||||||
'Êtes-vous certains de vouloir révoquer définitivement cette identité ?') ??
|
'Êtes-vous certains de vouloir révoquer définitivement cette identité ?') ??
|
||||||
false;
|
false;
|
||||||
|
|
||||||
if (answer) {
|
if (!answer) return;
|
||||||
final myWalletProvider =
|
final myWalletProvider =
|
||||||
Provider.of<MyWalletsProvider>(context, listen: false);
|
Provider.of<MyWalletsProvider>(context, listen: false);
|
||||||
final sub = Provider.of<SubstrateSdk>(context, listen: false);
|
final sub = Provider.of<SubstrateSdk>(context, listen: false);
|
||||||
|
|
||||||
WalletData? defaultWallet = myWalletProvider.getDefaultWallet();
|
WalletData? defaultWallet = myWalletProvider.getDefaultWallet();
|
||||||
String? pin;
|
String? pin;
|
||||||
if (myWalletProvider.pinCode == '') {
|
if (myWalletProvider.pinCode == '') {
|
||||||
pin = await Navigator.push(
|
pin = await Navigator.push(
|
||||||
context,
|
|
||||||
MaterialPageRoute(
|
|
||||||
builder: (homeContext) {
|
|
||||||
return UnlockingWallet(wallet: defaultWallet);
|
|
||||||
},
|
|
||||||
),
|
|
||||||
);
|
|
||||||
}
|
|
||||||
if (pin != null || myWalletProvider.pinCode != '') {
|
|
||||||
sub.revokeIdentity(address, myWalletProvider.pinCode);
|
|
||||||
}
|
|
||||||
Navigator.pop(context);
|
|
||||||
|
|
||||||
Navigator.push(
|
|
||||||
context,
|
context,
|
||||||
MaterialPageRoute(builder: (context) {
|
MaterialPageRoute(
|
||||||
return TransactionInProgress(
|
builder: (homeContext) {
|
||||||
transType: 'revokeIdty',
|
return UnlockingWallet(wallet: defaultWallet);
|
||||||
fromAddress: getShortPubkey(address),
|
},
|
||||||
toAddress: getShortPubkey(address));
|
),
|
||||||
}),
|
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (pin == null || myWalletProvider.pinCode == '') return;
|
||||||
|
|
||||||
|
final transactionId =
|
||||||
|
await sub.revokeIdentity(address, myWalletProvider.pinCode);
|
||||||
|
|
||||||
|
Navigator.pop(context);
|
||||||
|
|
||||||
|
Navigator.push(
|
||||||
|
context,
|
||||||
|
MaterialPageRoute(builder: (context) {
|
||||||
|
return TransactionInProgress(
|
||||||
|
transactionId: transactionId,
|
||||||
|
transType: 'revokeIdty',
|
||||||
|
fromAddress: getShortPubkey(address),
|
||||||
|
toAddress: getShortPubkey(address));
|
||||||
|
}),
|
||||||
|
);
|
||||||
},
|
},
|
||||||
child: ScaledSizedBox(
|
child: ScaledSizedBox(
|
||||||
height: 55,
|
height: 55,
|
||||||
|
|
|
@ -190,28 +190,25 @@ class MigrateIdentityScreen extends StatelessWidget {
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
if (myWalletProvider.pinCode != '') {
|
if (myWalletProvider.pinCode == '') return;
|
||||||
sub.migrateIdentity(
|
final transactionId = await sub.migrateIdentity(
|
||||||
fromAddress: fromAddress,
|
fromAddress: fromAddress,
|
||||||
destAddress: selectedWallet.address,
|
destAddress: selectedWallet.address,
|
||||||
fromPassword:
|
fromPassword: pin ?? myWalletProvider.pinCode,
|
||||||
pin ?? myWalletProvider.pinCode,
|
destPassword: pin ?? myWalletProvider.pinCode,
|
||||||
destPassword:
|
withBalance: true,
|
||||||
pin ?? myWalletProvider.pinCode,
|
fromBalance: balance);
|
||||||
withBalance: true,
|
Navigator.push(
|
||||||
fromBalance: balance);
|
context,
|
||||||
Navigator.push(
|
MaterialPageRoute(builder: (context) {
|
||||||
context,
|
return TransactionInProgress(
|
||||||
MaterialPageRoute(builder: (context) {
|
transactionId: transactionId,
|
||||||
return TransactionInProgress(
|
transType: 'identityMigration',
|
||||||
transType: 'identityMigration',
|
fromAddress: getShortPubkey(fromAddress),
|
||||||
fromAddress:
|
toAddress: getShortPubkey(
|
||||||
getShortPubkey(fromAddress),
|
selectedWallet.address));
|
||||||
toAddress: getShortPubkey(
|
}),
|
||||||
selectedWallet.address));
|
);
|
||||||
}),
|
|
||||||
);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
: null,
|
: null,
|
||||||
child: Text(
|
child: Text(
|
||||||
|
|
|
@ -84,8 +84,9 @@ class RestoreChest extends StatelessWidget {
|
||||||
child: ElevatedButton(
|
child: ElevatedButton(
|
||||||
key: keyGoNext,
|
key: keyGoNext,
|
||||||
style: ElevatedButton.styleFrom(
|
style: ElevatedButton.styleFrom(
|
||||||
foregroundColor: Colors.white, elevation: 4,
|
foregroundColor: Colors.white,
|
||||||
backgroundColor: orangeC, // foreground
|
elevation: 4,
|
||||||
|
backgroundColor: orangeC,
|
||||||
),
|
),
|
||||||
onPressed: () async {
|
onPressed: () async {
|
||||||
if (await sub
|
if (await sub
|
||||||
|
@ -125,8 +126,9 @@ class RestoreChest extends StatelessWidget {
|
||||||
child: ElevatedButton(
|
child: ElevatedButton(
|
||||||
key: keyPastMnemonic,
|
key: keyPastMnemonic,
|
||||||
style: ElevatedButton.styleFrom(
|
style: ElevatedButton.styleFrom(
|
||||||
foregroundColor: Colors.black, elevation: 4,
|
foregroundColor: Colors.black,
|
||||||
backgroundColor: yellowC, // foreground
|
elevation: 4,
|
||||||
|
backgroundColor: yellowC,
|
||||||
),
|
),
|
||||||
onPressed: () {
|
onPressed: () {
|
||||||
genW.pasteMnemonic(context);
|
genW.pasteMnemonic(context);
|
||||||
|
|
|
@ -239,9 +239,7 @@ class WalletOptions extends StatelessWidget {
|
||||||
if (!walletProvider.isDefaultWallet &&
|
if (!walletProvider.isDefaultWallet &&
|
||||||
!wallet.isMembre())
|
!wallet.isMembre())
|
||||||
deleteWallet(
|
deleteWallet(
|
||||||
context, walletProvider, currentChest)
|
context, walletProvider, currentChest),
|
||||||
else
|
|
||||||
ScaledSizedBox(),
|
|
||||||
if (wallet.isMembre())
|
if (wallet.isMembre())
|
||||||
const ManageMembershipButton()
|
const ManageMembershipButton()
|
||||||
])
|
])
|
||||||
|
@ -327,16 +325,10 @@ class WalletOptions extends StatelessWidget {
|
||||||
key: keyConfirmIdentity,
|
key: keyConfirmIdentity,
|
||||||
style: ElevatedButton.styleFrom(
|
style: ElevatedButton.styleFrom(
|
||||||
foregroundColor: Colors.white, elevation: 4,
|
foregroundColor: Colors.white, elevation: 4,
|
||||||
backgroundColor: orangeC, // foreground
|
backgroundColor: orangeC,
|
||||||
),
|
),
|
||||||
onPressed: () async {
|
onPressed: () {
|
||||||
walletProvider.confirmIdentityPopup(context);
|
walletProvider.confirmIdentityPopup(context);
|
||||||
// Navigator.push(
|
|
||||||
// context,
|
|
||||||
// MaterialPageRoute(builder: (context) {
|
|
||||||
// return const SearchResultScreen();
|
|
||||||
// }),
|
|
||||||
// );
|
|
||||||
},
|
},
|
||||||
child: Text(
|
child: Text(
|
||||||
'confirmMyIdentity'.tr(),
|
'confirmMyIdentity'.tr(),
|
||||||
|
|
|
@ -221,8 +221,9 @@ Widget nextButton(
|
||||||
child: ElevatedButton(
|
child: ElevatedButton(
|
||||||
key: keyGoNext,
|
key: keyGoNext,
|
||||||
style: ElevatedButton.styleFrom(
|
style: ElevatedButton.styleFrom(
|
||||||
foregroundColor: Colors.white, elevation: 4,
|
foregroundColor: Colors.white,
|
||||||
backgroundColor: orangeC, // foreground
|
elevation: 4,
|
||||||
|
backgroundColor: orangeC,
|
||||||
),
|
),
|
||||||
onPressed: () {
|
onPressed: () {
|
||||||
generateWalletProvider.nbrWord = generateWalletProvider.getRandomInt();
|
generateWalletProvider.nbrWord = generateWalletProvider.getRandomInt();
|
||||||
|
|
|
@ -148,8 +148,9 @@ Widget nextButton(BuildContext context, String text, nextScreen, bool isFast) {
|
||||||
child: ElevatedButton(
|
child: ElevatedButton(
|
||||||
key: keyGoNext,
|
key: keyGoNext,
|
||||||
style: ElevatedButton.styleFrom(
|
style: ElevatedButton.styleFrom(
|
||||||
foregroundColor: Colors.white, elevation: 4,
|
foregroundColor: Colors.white,
|
||||||
backgroundColor: orangeC, // foreground
|
elevation: 4,
|
||||||
|
backgroundColor: orangeC,
|
||||||
),
|
),
|
||||||
onPressed: () {
|
onPressed: () {
|
||||||
Navigator.push(
|
Navigator.push(
|
||||||
|
|
|
@ -81,8 +81,7 @@ class OnboardingStepNine extends StatelessWidget {
|
||||||
style: ElevatedButton.styleFrom(
|
style: ElevatedButton.styleFrom(
|
||||||
foregroundColor: Colors.black,
|
foregroundColor: Colors.black,
|
||||||
elevation: 4,
|
elevation: 4,
|
||||||
backgroundColor:
|
backgroundColor: const Color(0xffFFD58D),
|
||||||
const Color(0xffFFD58D), // foreground
|
|
||||||
),
|
),
|
||||||
onPressed: () {
|
onPressed: () {
|
||||||
generateWalletProvider.changePinCode(
|
generateWalletProvider.changePinCode(
|
||||||
|
|
|
@ -141,8 +141,9 @@ class _SearchScreenState extends State<SearchScreen> {
|
||||||
child: ElevatedButton(
|
child: ElevatedButton(
|
||||||
key: keyConfirmSearch,
|
key: keyConfirmSearch,
|
||||||
style: ElevatedButton.styleFrom(
|
style: ElevatedButton.styleFrom(
|
||||||
foregroundColor: Colors.white, elevation: 4,
|
foregroundColor: Colors.white,
|
||||||
backgroundColor: orangeC, // foreground
|
elevation: 4,
|
||||||
|
backgroundColor: orangeC,
|
||||||
),
|
),
|
||||||
onPressed: canValidate
|
onPressed: canValidate
|
||||||
? () {
|
? () {
|
||||||
|
|
|
@ -18,11 +18,11 @@ class SearchResultScreen extends StatelessWidget {
|
||||||
@override
|
@override
|
||||||
Widget build(BuildContext context) {
|
Widget build(BuildContext context) {
|
||||||
final searchProvider = Provider.of<SearchProvider>(context, listen: false);
|
final searchProvider = Provider.of<SearchProvider>(context, listen: false);
|
||||||
WalletsProfilesProvider walletsProfilesClass =
|
final walletsProfilesClass =
|
||||||
Provider.of<WalletsProfilesProvider>(context, listen: false);
|
Provider.of<WalletsProfilesProvider>(context, listen: false);
|
||||||
final duniterIndexer = Provider.of<DuniterIndexer>(context, listen: false);
|
final duniterIndexer = Provider.of<DuniterIndexer>(context, listen: false);
|
||||||
|
|
||||||
double avatarSize = scaleSize(37);
|
final avatarSize = scaleSize(37);
|
||||||
|
|
||||||
return Scaffold(
|
return Scaffold(
|
||||||
backgroundColor: backgroundColor,
|
backgroundColor: backgroundColor,
|
||||||
|
|
|
@ -1,95 +1,87 @@
|
||||||
import 'package:easy_localization/easy_localization.dart';
|
|
||||||
import 'package:gecko/globals.dart';
|
|
||||||
import 'package:flutter/material.dart';
|
import 'package:flutter/material.dart';
|
||||||
|
import 'package:gecko/globals.dart';
|
||||||
import 'package:gecko/models/scale_functions.dart';
|
import 'package:gecko/models/scale_functions.dart';
|
||||||
import 'package:gecko/models/widgets_keys.dart';
|
import 'package:gecko/models/widgets_keys.dart';
|
||||||
import 'package:gecko/providers/my_wallets.dart';
|
import 'package:gecko/providers/my_wallets.dart';
|
||||||
import 'package:gecko/providers/substrate_sdk.dart';
|
import 'package:gecko/providers/substrate_sdk.dart';
|
||||||
import 'package:gecko/providers/wallets_profiles.dart';
|
import 'package:gecko/providers/wallets_profiles.dart';
|
||||||
import 'package:provider/provider.dart';
|
import 'package:provider/provider.dart';
|
||||||
|
import 'package:easy_localization/easy_localization.dart';
|
||||||
|
|
||||||
class TransactionInProgress extends StatelessWidget {
|
class TransactionInProgress extends StatelessWidget {
|
||||||
const TransactionInProgress(
|
final String transactionId;
|
||||||
{Key? key,
|
|
||||||
this.transType = 'pay',
|
|
||||||
this.fromAddress,
|
|
||||||
this.toAddress,
|
|
||||||
this.toUsername})
|
|
||||||
: super(key: key);
|
|
||||||
final String transType;
|
final String transType;
|
||||||
final String? fromAddress;
|
final String? fromAddress, toAddress, toUsername;
|
||||||
final String? toAddress;
|
|
||||||
final String? toUsername;
|
const TransactionInProgress({
|
||||||
|
Key? key,
|
||||||
|
required this.transactionId,
|
||||||
|
this.transType = 'pay',
|
||||||
|
this.fromAddress,
|
||||||
|
this.toAddress,
|
||||||
|
this.toUsername,
|
||||||
|
}) : super(key: key);
|
||||||
|
|
||||||
@override
|
@override
|
||||||
Widget build(BuildContext context) {
|
Widget build(BuildContext context) {
|
||||||
final sub = Provider.of<SubstrateSdk>(context, listen: true);
|
final sub = Provider.of<SubstrateSdk>(context, listen: true);
|
||||||
final walletProfiles =
|
|
||||||
Provider.of<WalletsProfilesProvider>(context, listen: false);
|
|
||||||
final myWalletProvider =
|
|
||||||
Provider.of<MyWalletsProvider>(context, listen: false);
|
|
||||||
var txStatus = TransactionStatus.none;
|
|
||||||
final result = sub.transactionStatus;
|
|
||||||
|
|
||||||
final from = fromAddress ??
|
final transactionDetails = TransactionDetails(
|
||||||
g1WalletsBox
|
transactionId: transactionId,
|
||||||
.get(myWalletProvider.getDefaultWallet().address)
|
fromAddress: fromAddress,
|
||||||
?.username ??
|
toAddress: toAddress,
|
||||||
myWalletProvider.getDefaultWallet().name!;
|
toUsername: toUsername,
|
||||||
|
sub: sub,
|
||||||
|
transType: transType,
|
||||||
|
);
|
||||||
|
|
||||||
String to = toAddress ?? walletProfiles.address;
|
Widget getTransactionStatusIcon(TransactionDetails details) {
|
||||||
to =
|
switch (details.txStatus) {
|
||||||
myWalletProvider.getWalletDataByAddress(to)?.name ?? getShortPubkey(to);
|
case TransactionStatus.loading:
|
||||||
|
return ScaledSizedBox(
|
||||||
final amount = walletProfiles.payAmount.text;
|
height: 17,
|
||||||
final bool isUdUnit = configBox.get('isUdUnit') ?? false;
|
width: 17,
|
||||||
|
child: const CircularProgressIndicator(
|
||||||
final Map<String, String> actionMap = {
|
color: orangeC,
|
||||||
'pay': 'transaction'.tr(),
|
strokeWidth: 2,
|
||||||
'cert': 'certification'.tr(),
|
),
|
||||||
'comfirmIdty': 'identityConfirm'.tr(),
|
);
|
||||||
'revokeIdty': 'revokeAdhesion'.tr(),
|
case TransactionStatus.success:
|
||||||
'identityMigration': 'identityMigration'.tr(),
|
return Icon(
|
||||||
};
|
Icons.done_all,
|
||||||
|
size: scaleSize(32),
|
||||||
String resultText = '';
|
color: Colors.greenAccent,
|
||||||
final Map<String, String> resultMap = {
|
);
|
||||||
'sending': 'sending'.tr(),
|
case TransactionStatus.failed:
|
||||||
'Ready': 'propagating'.tr(),
|
return Icon(
|
||||||
'Broadcast': 'validating'.tr(),
|
Icons.close,
|
||||||
'cert.NotRespectCertPeriod': '24hbetweenCerts'.tr(),
|
size: scaleSize(32),
|
||||||
'identity.CreatorNotAllowedToCreateIdty': '24hbetweenCerts'.tr(),
|
color: Colors.redAccent,
|
||||||
'cert.CannotCertifySelf': 'canNotCertifySelf'.tr(),
|
);
|
||||||
'identity.IdtyNameAlreadyExist': 'nameAlreadyExist'.tr(),
|
case TransactionStatus.none:
|
||||||
'balances.KeepAlive': '2GDtoKeepAlive'.tr(),
|
default:
|
||||||
'1010: Invalid Transaction: Inability to pay some fees , e.g. account balance too low':
|
return const SizedBox.shrink();
|
||||||
'youHaveToFeedThisAccountBeforeUsing'.tr(),
|
}
|
||||||
'Token.FundsUnavailable': 'fundsUnavailable'.tr(),
|
|
||||||
'Exception: timeout': 'execTimeoutOver'.tr(),
|
|
||||||
};
|
|
||||||
|
|
||||||
if (result == null) {
|
|
||||||
txStatus = TransactionStatus.none;
|
|
||||||
} else if (result.contains('blockHash: ')) {
|
|
||||||
txStatus = TransactionStatus.success;
|
|
||||||
resultText = 'extrinsicValidated'
|
|
||||||
.tr(args: [actionMap[transType] ?? 'strangeTransaction'.tr()]);
|
|
||||||
} else if (result.contains('Exception: ')) {
|
|
||||||
txStatus = TransactionStatus.failed;
|
|
||||||
resultText = "${"anErrorOccurred".tr()}:\n";
|
|
||||||
final String exception = result.split('Exception: ')[1];
|
|
||||||
resultText = resultMap[exception] ?? "$resultText\n$exception";
|
|
||||||
log.e('Error: $exception');
|
|
||||||
} else {
|
|
||||||
txStatus = TransactionStatus.loading;
|
|
||||||
resultText = resultMap[result] ?? 'unknown status...';
|
|
||||||
}
|
}
|
||||||
|
|
||||||
log.d("$transType :: ${actionMap[transType]} :: $result");
|
Widget buildTransactionStatus(TransactionDetails details) {
|
||||||
|
return Column(
|
||||||
|
children: [
|
||||||
|
getTransactionStatusIcon(details),
|
||||||
|
ScaledSizedBox(height: 7),
|
||||||
|
if (details.txStatus != TransactionStatus.none)
|
||||||
|
Text(
|
||||||
|
transactionDetails.resultText,
|
||||||
|
textAlign: TextAlign.center,
|
||||||
|
style: scaledTextStyle(fontSize: 17),
|
||||||
|
)
|
||||||
|
],
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
return PopScope(
|
return PopScope(
|
||||||
onPopInvoked: (_) {
|
onPopInvoked: (_) {
|
||||||
sub.transactionStatus = null;
|
sub.resetTransactionStatus();
|
||||||
},
|
},
|
||||||
child: Scaffold(
|
child: Scaffold(
|
||||||
backgroundColor: backgroundColor,
|
backgroundColor: backgroundColor,
|
||||||
|
@ -102,138 +94,105 @@ class TransactionInProgress extends StatelessWidget {
|
||||||
children: <Widget>[
|
children: <Widget>[
|
||||||
Text(
|
Text(
|
||||||
'extrinsicInProgress'.tr(args: [
|
'extrinsicInProgress'.tr(args: [
|
||||||
actionMap[transType] ?? 'strangeTransaction'.tr()
|
transactionDetails.actionMap[transType] ??
|
||||||
|
'strangeTransaction'.tr()
|
||||||
]),
|
]),
|
||||||
style: scaledTextStyle(fontSize: 20),
|
style: scaledTextStyle(fontSize: 20),
|
||||||
)
|
)
|
||||||
])),
|
])),
|
||||||
body: SafeArea(
|
body: SafeArea(
|
||||||
child: Align(
|
child: Align(
|
||||||
alignment: FractionalOffset.bottomCenter,
|
alignment: FractionalOffset.bottomCenter,
|
||||||
child: Column(children: <Widget>[
|
child: Column(children: <Widget>[
|
||||||
Container(
|
Container(
|
||||||
width: double.infinity,
|
width: double.infinity,
|
||||||
decoration: const BoxDecoration(
|
decoration: const BoxDecoration(
|
||||||
gradient: LinearGradient(
|
gradient: LinearGradient(
|
||||||
begin: Alignment.topCenter,
|
begin: Alignment.topCenter,
|
||||||
end: Alignment.bottomCenter,
|
end: Alignment.bottomCenter,
|
||||||
colors: [
|
colors: [
|
||||||
yellowC,
|
yellowC,
|
||||||
backgroundColor,
|
backgroundColor,
|
||||||
],
|
],
|
||||||
)),
|
)),
|
||||||
child: Column(children: <Widget>[
|
child: Column(children: <Widget>[
|
||||||
ScaledSizedBox(height: 10),
|
ScaledSizedBox(height: 10),
|
||||||
if (transType == 'pay')
|
if (transType == 'pay')
|
||||||
Text(
|
|
||||||
isUdUnit
|
|
||||||
? 'ud'.tr(args: ['$amount '])
|
|
||||||
: '$amount $currencyName',
|
|
||||||
textAlign: TextAlign.center,
|
|
||||||
style: scaledTextStyle(
|
|
||||||
fontSize: 17, fontWeight: FontWeight.w500),
|
|
||||||
),
|
|
||||||
if (transType == 'pay') ScaledSizedBox(height: 10),
|
|
||||||
Text(
|
Text(
|
||||||
'fromMinus'.tr(),
|
transactionDetails.isUdUnit
|
||||||
textAlign: TextAlign.center,
|
? 'ud'.tr(args: ['${transactionDetails.amount} '])
|
||||||
style: scaledTextStyle(fontSize: 16),
|
: '${transactionDetails.amount} $currencyName',
|
||||||
),
|
|
||||||
Text(
|
|
||||||
from,
|
|
||||||
textAlign: TextAlign.center,
|
textAlign: TextAlign.center,
|
||||||
style: scaledTextStyle(
|
style: scaledTextStyle(
|
||||||
fontSize: 17, fontWeight: FontWeight.w500),
|
fontSize: 17, fontWeight: FontWeight.w500),
|
||||||
),
|
),
|
||||||
Visibility(
|
if (transType == 'pay') ScaledSizedBox(height: 10),
|
||||||
visible: from != to,
|
Text(
|
||||||
child: Column(
|
'fromMinus'.tr(),
|
||||||
children: [
|
textAlign: TextAlign.center,
|
||||||
ScaledSizedBox(height: 10),
|
style: scaledTextStyle(fontSize: 16),
|
||||||
Text(
|
),
|
||||||
'toMinus'.tr(),
|
Text(
|
||||||
textAlign: TextAlign.center,
|
transactionDetails.fromAddress!,
|
||||||
style: scaledTextStyle(fontSize: 16),
|
textAlign: TextAlign.center,
|
||||||
),
|
style: scaledTextStyle(
|
||||||
Text(
|
fontSize: 17, fontWeight: FontWeight.w500),
|
||||||
toUsername ?? to,
|
|
||||||
textAlign: TextAlign.center,
|
|
||||||
style: scaledTextStyle(
|
|
||||||
fontSize: 17, fontWeight: FontWeight.w500),
|
|
||||||
),
|
|
||||||
],
|
|
||||||
),
|
|
||||||
),
|
|
||||||
ScaledSizedBox(height: 20),
|
|
||||||
]),
|
|
||||||
),
|
|
||||||
const Spacer(),
|
|
||||||
Column(children: [
|
|
||||||
Visibility(
|
|
||||||
visible: txStatus == TransactionStatus.loading,
|
|
||||||
child: ScaledSizedBox(
|
|
||||||
height: 17,
|
|
||||||
width: 17,
|
|
||||||
child: const CircularProgressIndicator(
|
|
||||||
color: orangeC,
|
|
||||||
strokeWidth: 2,
|
|
||||||
),
|
|
||||||
),
|
|
||||||
),
|
),
|
||||||
Visibility(
|
Visibility(
|
||||||
visible: txStatus == TransactionStatus.success,
|
visible: transactionDetails.fromAddress !=
|
||||||
child: Icon(
|
transactionDetails.toAddress,
|
||||||
Icons.done_all,
|
child: Column(
|
||||||
size: scaleSize(32),
|
children: [
|
||||||
color: Colors.greenAccent,
|
ScaledSizedBox(height: 10),
|
||||||
),
|
Text(
|
||||||
),
|
'toMinus'.tr(),
|
||||||
Visibility(
|
textAlign: TextAlign.center,
|
||||||
visible: txStatus == TransactionStatus.failed,
|
style: scaledTextStyle(fontSize: 16),
|
||||||
child: Icon(
|
|
||||||
Icons.close,
|
|
||||||
size: scaleSize(32),
|
|
||||||
color: Colors.redAccent,
|
|
||||||
),
|
|
||||||
),
|
|
||||||
ScaledSizedBox(height: 10),
|
|
||||||
Visibility(
|
|
||||||
visible: txStatus != TransactionStatus.none,
|
|
||||||
child: Text(
|
|
||||||
resultText,
|
|
||||||
textAlign: TextAlign.center,
|
|
||||||
style: scaledTextStyle(fontSize: 17),
|
|
||||||
),
|
|
||||||
),
|
|
||||||
]),
|
|
||||||
const Spacer(),
|
|
||||||
Expanded(
|
|
||||||
child: Align(
|
|
||||||
alignment: Alignment.bottomCenter,
|
|
||||||
child: ScaledSizedBox(
|
|
||||||
width: 300,
|
|
||||||
height: 55,
|
|
||||||
child: ElevatedButton(
|
|
||||||
key: keyCloseTransactionScreen,
|
|
||||||
style: ElevatedButton.styleFrom(
|
|
||||||
foregroundColor: Colors.white, elevation: 4,
|
|
||||||
backgroundColor: orangeC, // foreground
|
|
||||||
),
|
),
|
||||||
onPressed: () {
|
Text(
|
||||||
sub.transactionStatus = null;
|
transactionDetails.toUsername!,
|
||||||
Navigator.pop(context);
|
textAlign: TextAlign.center,
|
||||||
},
|
|
||||||
child: Text(
|
|
||||||
'close'.tr(),
|
|
||||||
style: scaledTextStyle(
|
style: scaledTextStyle(
|
||||||
fontSize: 20, fontWeight: FontWeight.w600),
|
fontSize: 17, fontWeight: FontWeight.w500),
|
||||||
),
|
),
|
||||||
|
],
|
||||||
|
),
|
||||||
|
),
|
||||||
|
ScaledSizedBox(height: 20),
|
||||||
|
]),
|
||||||
|
),
|
||||||
|
const Spacer(),
|
||||||
|
buildTransactionStatus(transactionDetails),
|
||||||
|
const Spacer(),
|
||||||
|
Expanded(
|
||||||
|
child: Align(
|
||||||
|
alignment: Alignment.bottomCenter,
|
||||||
|
child: ScaledSizedBox(
|
||||||
|
width: 300,
|
||||||
|
height: 55,
|
||||||
|
child: ElevatedButton(
|
||||||
|
key: keyCloseTransactionScreen,
|
||||||
|
style: ElevatedButton.styleFrom(
|
||||||
|
foregroundColor: Colors.white,
|
||||||
|
elevation: 4,
|
||||||
|
backgroundColor: orangeC,
|
||||||
|
),
|
||||||
|
onPressed: () {
|
||||||
|
sub.resetTransactionStatus();
|
||||||
|
Navigator.pop(context);
|
||||||
|
},
|
||||||
|
child: Text(
|
||||||
|
'close'.tr(),
|
||||||
|
style: scaledTextStyle(
|
||||||
|
fontSize: 20, fontWeight: FontWeight.w600),
|
||||||
),
|
),
|
||||||
),
|
),
|
||||||
),
|
),
|
||||||
),
|
),
|
||||||
ScaledSizedBox(height: 80)
|
),
|
||||||
])),
|
ScaledSizedBox(height: 80)
|
||||||
|
]),
|
||||||
|
),
|
||||||
),
|
),
|
||||||
),
|
),
|
||||||
);
|
);
|
||||||
|
@ -241,3 +200,82 @@ class TransactionInProgress extends StatelessWidget {
|
||||||
}
|
}
|
||||||
|
|
||||||
enum TransactionStatus { loading, failed, success, none }
|
enum TransactionStatus { loading, failed, success, none }
|
||||||
|
|
||||||
|
class TransactionDetails {
|
||||||
|
String? fromAddress, toAddress, toUsername, amount;
|
||||||
|
bool isUdUnit = false;
|
||||||
|
String resultText = '';
|
||||||
|
TransactionStatus txStatus = TransactionStatus.none;
|
||||||
|
|
||||||
|
Map<String, String> actionMap = {
|
||||||
|
'pay': 'transaction'.tr(),
|
||||||
|
'cert': 'certification'.tr(),
|
||||||
|
'comfirmIdty': 'identityConfirm'.tr(),
|
||||||
|
'revokeIdty': 'revokeAdhesion'.tr(),
|
||||||
|
'identityMigration': 'identityMigration'.tr(),
|
||||||
|
};
|
||||||
|
|
||||||
|
Map<String, String> resultMap = {
|
||||||
|
'sending': 'sending'.tr(),
|
||||||
|
'Ready': 'propagating'.tr(),
|
||||||
|
'Broadcast': 'validating'.tr(),
|
||||||
|
'cert.NotRespectCertPeriod': '24hbetweenCerts'.tr(),
|
||||||
|
'identity.CreatorNotAllowedToCreateIdty': '24hbetweenCerts'.tr(),
|
||||||
|
'cert.CannotCertifySelf': 'canNotCertifySelf'.tr(),
|
||||||
|
'identity.IdtyNameAlreadyExist': 'nameAlreadyExist'.tr(),
|
||||||
|
'balances.KeepAlive': '2GDtoKeepAlive'.tr(),
|
||||||
|
'1010: Invalid Transaction: Inability to pay some fees , e.g. account balance too low':
|
||||||
|
'youHaveToFeedThisAccountBeforeUsing'.tr(),
|
||||||
|
'Token.FundsUnavailable': 'fundsUnavailable'.tr(),
|
||||||
|
'Exception: timeout': 'execTimeoutOver'.tr(),
|
||||||
|
};
|
||||||
|
|
||||||
|
TransactionDetails({
|
||||||
|
required transactionId,
|
||||||
|
required this.fromAddress,
|
||||||
|
required this.toAddress,
|
||||||
|
required this.toUsername,
|
||||||
|
required SubstrateSdk sub,
|
||||||
|
required String transType,
|
||||||
|
}) {
|
||||||
|
final walletProfiles =
|
||||||
|
Provider.of<WalletsProfilesProvider>(homeContext, listen: false);
|
||||||
|
final myWalletProvider =
|
||||||
|
Provider.of<MyWalletsProvider>(homeContext, listen: false);
|
||||||
|
String defaultWalletAddress = myWalletProvider.getDefaultWallet().address;
|
||||||
|
String defaultWalletName = myWalletProvider.getDefaultWallet().name!;
|
||||||
|
String? walletDataName =
|
||||||
|
myWalletProvider.getWalletDataByAddress(toAddress ?? '')?.name;
|
||||||
|
|
||||||
|
fromAddress = fromAddress ??
|
||||||
|
g1WalletsBox.get(defaultWalletAddress)?.username ??
|
||||||
|
defaultWalletName;
|
||||||
|
toAddress = toAddress ?? walletProfiles.address;
|
||||||
|
toUsername = toUsername ?? walletDataName ?? getShortPubkey(toAddress!);
|
||||||
|
|
||||||
|
amount = walletProfiles.payAmount.text;
|
||||||
|
isUdUnit = configBox.get('isUdUnit') ?? false;
|
||||||
|
|
||||||
|
if (sub.transactionStatus.containsKey(transactionId)) {
|
||||||
|
calculateTransactionStatus(
|
||||||
|
sub.transactionStatus[transactionId], transType);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void calculateTransactionStatus(String? result, String transType) {
|
||||||
|
if (result == null) {
|
||||||
|
txStatus = TransactionStatus.none;
|
||||||
|
} else if (result.contains('blockHash: ')) {
|
||||||
|
txStatus = TransactionStatus.success;
|
||||||
|
resultText = 'extrinsicValidated'
|
||||||
|
.tr(args: [actionMap[transType] ?? 'strangeTransaction']);
|
||||||
|
} else if (result.contains('Exception: ')) {
|
||||||
|
txStatus = TransactionStatus.failed;
|
||||||
|
String exception = result.split('Exception: ')[1];
|
||||||
|
resultText = resultMap[exception] ?? exception;
|
||||||
|
} else {
|
||||||
|
txStatus = TransactionStatus.loading;
|
||||||
|
resultText = resultMap[result] ?? 'Unknown status: $result';
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
|
@ -151,7 +151,7 @@ class WalletViewScreen extends StatelessWidget {
|
||||||
return FutureBuilder(
|
return FutureBuilder(
|
||||||
future: sub.certState(defaultWallet.address, address),
|
future: sub.certState(defaultWallet.address, address),
|
||||||
builder: (context, AsyncSnapshot<Map<String, int>> snapshot) {
|
builder: (context, AsyncSnapshot<Map<String, int>> snapshot) {
|
||||||
if (snapshot.data == null) return ScaledSizedBox();
|
if (snapshot.data == null) return const SizedBox.shrink();
|
||||||
String duration = '';
|
String duration = '';
|
||||||
|
|
||||||
if (snapshot.data!['certDelay'] != null ||
|
if (snapshot.data!['certDelay'] != null ||
|
||||||
|
@ -209,55 +209,53 @@ class WalletViewScreen extends StatelessWidget {
|
||||||
'assets/gecko_certify.png')),
|
'assets/gecko_certify.png')),
|
||||||
),
|
),
|
||||||
onTap: () async {
|
onTap: () async {
|
||||||
final bool? result =
|
final result =
|
||||||
await confirmPopupCertification(
|
await confirmPopupCertification(
|
||||||
context,
|
context,
|
||||||
'areYouSureYouWantToCertify1'
|
'areYouSureYouWantToCertify1'
|
||||||
.tr(),
|
.tr(),
|
||||||
duniterIndexer
|
duniterIndexer
|
||||||
.walletNameIndexer[
|
.walletNameIndexer[
|
||||||
address] ??
|
address] ??
|
||||||
"noIdentity".tr(),
|
"noIdentity".tr(),
|
||||||
'areYouSureYouWantToCertify2'
|
'areYouSureYouWantToCertify2'
|
||||||
.tr(),
|
.tr(),
|
||||||
getShortPubkey(address));
|
getShortPubkey(address)) ??
|
||||||
|
false;
|
||||||
|
|
||||||
if (result ?? false) {
|
if (!result) return;
|
||||||
String? pin;
|
if (myWalletProvider.pinCode == '') {
|
||||||
if (myWalletProvider.pinCode == '') {
|
await Navigator.push(
|
||||||
pin = await Navigator.push(
|
context,
|
||||||
context,
|
MaterialPageRoute(
|
||||||
MaterialPageRoute(
|
builder: (homeContext) {
|
||||||
builder: (homeContext) {
|
return UnlockingWallet(
|
||||||
return UnlockingWallet(
|
wallet: defaultWallet);
|
||||||
wallet: defaultWallet);
|
},
|
||||||
},
|
),
|
||||||
),
|
);
|
||||||
);
|
|
||||||
}
|
|
||||||
if (pin != null ||
|
|
||||||
myWalletProvider.pinCode != '') {
|
|
||||||
WalletsProfilesProvider
|
|
||||||
walletViewProvider = Provider
|
|
||||||
.of<WalletsProfilesProvider>(
|
|
||||||
context,
|
|
||||||
listen: false);
|
|
||||||
final acc = sub.getCurrentWallet();
|
|
||||||
sub.certify(
|
|
||||||
acc.address!,
|
|
||||||
walletViewProvider.address,
|
|
||||||
pin ??
|
|
||||||
myWalletProvider.pinCode);
|
|
||||||
Navigator.push(
|
|
||||||
context,
|
|
||||||
MaterialPageRoute(
|
|
||||||
builder: (context) {
|
|
||||||
return const TransactionInProgress(
|
|
||||||
transType: 'cert');
|
|
||||||
}),
|
|
||||||
);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
if (myWalletProvider.pinCode == '') {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
WalletsProfilesProvider
|
||||||
|
walletViewProvider = Provider.of<
|
||||||
|
WalletsProfilesProvider>(
|
||||||
|
context,
|
||||||
|
listen: false);
|
||||||
|
final acc = sub.getCurrentWallet();
|
||||||
|
final transactionId = await sub.certify(
|
||||||
|
acc.address!,
|
||||||
|
walletViewProvider.address,
|
||||||
|
myWalletProvider.pinCode);
|
||||||
|
Navigator.push(
|
||||||
|
context,
|
||||||
|
MaterialPageRoute(builder: (context) {
|
||||||
|
return TransactionInProgress(
|
||||||
|
transactionId: transactionId,
|
||||||
|
transType: 'cert');
|
||||||
|
}),
|
||||||
|
);
|
||||||
}),
|
}),
|
||||||
),
|
),
|
||||||
),
|
),
|
||||||
|
|
|
@ -24,8 +24,9 @@ class NextButton extends StatelessWidget {
|
||||||
child: ElevatedButton(
|
child: ElevatedButton(
|
||||||
key: keyGoNext,
|
key: keyGoNext,
|
||||||
style: ElevatedButton.styleFrom(
|
style: ElevatedButton.styleFrom(
|
||||||
foregroundColor: Colors.white, backgroundColor: orangeC,
|
foregroundColor: Colors.white,
|
||||||
elevation: 4, // foreground
|
backgroundColor: orangeC,
|
||||||
|
elevation: 4,
|
||||||
),
|
),
|
||||||
onPressed: () {
|
onPressed: () {
|
||||||
Navigator.push(
|
Navigator.push(
|
||||||
|
|
|
@ -33,9 +33,8 @@ void paymentPopup(BuildContext context, String toAddress, String? username) {
|
||||||
walletViewProvider.payAmount.text = '';
|
walletViewProvider.payAmount.text = '';
|
||||||
|
|
||||||
Future executeTransfert() async {
|
Future executeTransfert() async {
|
||||||
String? pin;
|
|
||||||
if (myWalletProvider.pinCode == '') {
|
if (myWalletProvider.pinCode == '') {
|
||||||
pin = await Navigator.push(
|
await Navigator.push(
|
||||||
context,
|
context,
|
||||||
MaterialPageRoute(
|
MaterialPageRoute(
|
||||||
builder: (homeContext) {
|
builder: (homeContext) {
|
||||||
|
@ -44,25 +43,26 @@ void paymentPopup(BuildContext context, String toAddress, String? username) {
|
||||||
),
|
),
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
if (pin != null || myWalletProvider.pinCode != '') {
|
if (myWalletProvider.pinCode == '') return;
|
||||||
// Payment workflow !
|
// Payment workflow !
|
||||||
final sub = Provider.of<SubstrateSdk>(context, listen: false);
|
final sub = Provider.of<SubstrateSdk>(context, listen: false);
|
||||||
final acc = sub.getCurrentWallet();
|
final acc = sub.getCurrentWallet();
|
||||||
log.d(
|
log.d(
|
||||||
"fromAddress: ${acc.address!},destAddress: $toAddress, amount: ${double.parse(walletViewProvider.payAmount.text)}");
|
"fromAddress: ${acc.address!},destAddress: $toAddress, amount: ${double.parse(walletViewProvider.payAmount.text)}");
|
||||||
sub.pay(
|
final transactionId = await sub.pay(
|
||||||
fromAddress: acc.address!,
|
fromAddress: acc.address!,
|
||||||
destAddress: toAddress,
|
destAddress: toAddress,
|
||||||
amount: double.parse(walletViewProvider.payAmount.text),
|
amount: double.parse(walletViewProvider.payAmount.text),
|
||||||
password: pin ?? myWalletProvider.pinCode);
|
password: myWalletProvider.pinCode);
|
||||||
Navigator.push(
|
Navigator.push(
|
||||||
context,
|
context,
|
||||||
MaterialPageRoute(builder: (context) {
|
MaterialPageRoute(builder: (context) {
|
||||||
return TransactionInProgress(
|
return TransactionInProgress(
|
||||||
toAddress: toAddress, toUsername: username);
|
transactionId: transactionId,
|
||||||
}),
|
toAddress: toAddress,
|
||||||
);
|
toUsername: username);
|
||||||
}
|
}),
|
||||||
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
myWalletProvider.readAllWallets().then((value) => myWalletProvider.listWallets
|
myWalletProvider.readAllWallets().then((value) => myWalletProvider.listWallets
|
||||||
|
|
|
@ -1660,7 +1660,7 @@ packages:
|
||||||
source: hosted
|
source: hosted
|
||||||
version: "3.1.0"
|
version: "3.1.0"
|
||||||
uuid:
|
uuid:
|
||||||
dependency: transitive
|
dependency: "direct main"
|
||||||
description:
|
description:
|
||||||
name: uuid
|
name: uuid
|
||||||
sha256: "648e103079f7c64a36dc7d39369cabb358d377078a051d6ae2ad3aa539519313"
|
sha256: "648e103079f7c64a36dc7d39369cabb358d377078a051d6ae2ad3aa539519313"
|
||||||
|
|
|
@ -61,6 +61,7 @@ dependencies:
|
||||||
url_launcher: ^6.1.11
|
url_launcher: ^6.1.11
|
||||||
crypto: ^3.0.3
|
crypto: ^3.0.3
|
||||||
screen_brightness: ^0.2.2+1
|
screen_brightness: ^0.2.2+1
|
||||||
|
uuid: ^3.0.7
|
||||||
|
|
||||||
dev_dependencies:
|
dev_dependencies:
|
||||||
# flutter_launcher_icons: ^0.9.2
|
# flutter_launcher_icons: ^0.9.2
|
||||||
|
|
Loading…
Reference in New Issue