mirror of
https://github.com/cake-tech/cake_wallet.git
synced 2025-06-28 12:29:51 +00:00
CW-1069-implement-deuro-dapp-support (#2304)
* feat: started dEuro Savings integration * fix: merge conflict regarding theming * feat: Add dEuro Savings Screen * feat: Change DEuro Savings UI * feat: Complete DEuro Savings integration with UI enhancements and transaction support * style: remove forgotten print statements * feat: localize dEuro subtitle * feat: add approval flow and priority handling to DEuro Savings integration - Introduced approval flow for DEuro Savings to enable token approvals. - Added priority handling for deposit and withdrawal operations. - Updated UI to support approval state and interactions. - Localized new strings for multiple languages. - Enhanced transaction handling with separate approval and commit actions. * feat: add support for ERC20 token approval transactions - Introduced `signApprovalTransaction` and `createApprovalTransaction` methods. - Added handling for infinite approvals. - Implemented encoding for approval transaction data. - Enhanced transaction creation flow with approval-specific functionality. * Update UI * feat: enhance DEuro Savings logic and UI with computed property and fix gradient background * feat: localize transaction confirmation content for DEuro Savings * feat: enable interest collection for DEuro Savings with localized support * fix reformatting [skip ci] --------- Co-authored-by: tuxsudo <tuxsudo@tux.pizza> Co-authored-by: OmarHatem <omarh.ismail1@gmail.com>
This commit is contained in:
parent
150becb679
commit
edaf485993
49 changed files with 2081 additions and 66 deletions
|
@ -76,7 +76,7 @@ abstract class EVMChainClient {
|
|||
Future<int> getGasUnitPrice() async {
|
||||
try {
|
||||
final gasPrice = await _client!.getGasPrice();
|
||||
|
||||
|
||||
return gasPrice.getInWei.toInt();
|
||||
} catch (_) {
|
||||
return 0;
|
||||
|
@ -101,6 +101,7 @@ abstract class EVMChainClient {
|
|||
String? contractAddress,
|
||||
EtherAmount? gasPrice,
|
||||
EtherAmount? maxFeePerGas,
|
||||
Uint8List? data,
|
||||
}) async {
|
||||
try {
|
||||
if (contractAddress == null) {
|
||||
|
@ -124,7 +125,7 @@ abstract class EVMChainClient {
|
|||
final gasEstimate = await _client!.estimateGas(
|
||||
sender: senderAddress,
|
||||
to: EthereumAddress.fromHex(contractAddress),
|
||||
data: transfer.encodeCall([
|
||||
data: data ?? transfer.encodeCall([
|
||||
toAddress,
|
||||
value.getInWei,
|
||||
]),
|
||||
|
@ -137,6 +138,21 @@ abstract class EVMChainClient {
|
|||
}
|
||||
}
|
||||
|
||||
Uint8List getEncodedDataForApprovalTransaction({
|
||||
required EthereumAddress toAddress,
|
||||
required EtherAmount value,
|
||||
required EthereumAddress contractAddress,
|
||||
}) {
|
||||
final contract = DeployedContract(ethereumContractAbi, contractAddress);
|
||||
|
||||
final approve = contract.function('approve');
|
||||
|
||||
return approve.encodeCall([
|
||||
toAddress,
|
||||
value.getInWei,
|
||||
]);
|
||||
}
|
||||
|
||||
Future<PendingEVMChainTransaction> signTransaction({
|
||||
required Credentials privateKey,
|
||||
required String toAddress,
|
||||
|
@ -198,6 +214,50 @@ abstract class EVMChainClient {
|
|||
);
|
||||
}
|
||||
|
||||
Future<PendingEVMChainTransaction> signApprovalTransaction({
|
||||
required Credentials privateKey,
|
||||
required String spender,
|
||||
required BigInt amount,
|
||||
required BigInt gasFee,
|
||||
required int estimatedGasUnits,
|
||||
required int maxFeePerGas,
|
||||
required EVMChainTransactionPriority priority,
|
||||
required int exponent,
|
||||
required String contractAddress,
|
||||
}) async {
|
||||
|
||||
final Transaction transaction = createTransaction(
|
||||
from: privateKey.address,
|
||||
to: EthereumAddress.fromHex(contractAddress),
|
||||
maxPriorityFeePerGas: EtherAmount.fromInt(EtherUnit.gwei, priority.tip),
|
||||
amount: EtherAmount.zero(),
|
||||
maxGas: estimatedGasUnits,
|
||||
maxFeePerGas: EtherAmount.fromInt(EtherUnit.wei, maxFeePerGas),
|
||||
);
|
||||
|
||||
final erc20 = ERC20(
|
||||
client: _client!,
|
||||
address: EthereumAddress.fromHex(contractAddress),
|
||||
chainId: chainId,
|
||||
);
|
||||
|
||||
final signedTransaction = await erc20.approve(
|
||||
EthereumAddress.fromHex(spender),
|
||||
amount,
|
||||
credentials: privateKey,
|
||||
transaction: transaction,
|
||||
);
|
||||
|
||||
return PendingEVMChainTransaction(
|
||||
signedTransaction: prepareSignedTransactionForSending(signedTransaction),
|
||||
amount: amount.toString(),
|
||||
fee: gasFee,
|
||||
sendTransaction: () => sendTransaction(signedTransaction),
|
||||
exponent: exponent,
|
||||
isInfiniteApproval: amount.toRadixString(16) == 'ffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff',
|
||||
);
|
||||
}
|
||||
|
||||
Transaction createTransaction({
|
||||
required EthereumAddress from,
|
||||
required EthereumAddress to,
|
||||
|
|
|
@ -2,6 +2,7 @@ import 'dart:async';
|
|||
import 'dart:convert';
|
||||
import 'dart:io';
|
||||
import 'dart:math';
|
||||
import 'dart:typed_data';
|
||||
|
||||
import 'package:bip32/bip32.dart' as bip32;
|
||||
import 'package:bip39/bip39.dart' as bip39;
|
||||
|
@ -255,6 +256,7 @@ abstract class EVMChainWalletBase
|
|||
required String? contractAddress,
|
||||
required String receivingAddressHex,
|
||||
required TransactionPriority priority,
|
||||
Uint8List? data,
|
||||
}) async {
|
||||
try {
|
||||
if (priority is EVMChainTransactionPriority) {
|
||||
|
@ -276,6 +278,7 @@ abstract class EVMChainWalletBase
|
|||
gasPrice: EtherAmount.fromInt(EtherUnit.wei, gasPrice),
|
||||
toAddress: EthereumAddress.fromHex(receivingAddressHex),
|
||||
maxFeePerGas: EtherAmount.fromInt(EtherUnit.wei, maxFeePerGas),
|
||||
data: data,
|
||||
);
|
||||
|
||||
final totalGasFee = estimatedGas * maxFeePerGas;
|
||||
|
@ -478,6 +481,43 @@ abstract class EVMChainWalletBase
|
|||
return pendingEVMChainTransaction;
|
||||
}
|
||||
|
||||
Future<PendingTransaction> createApprovalTransaction(
|
||||
BigInt amount,
|
||||
String spender,
|
||||
CryptoCurrency token,
|
||||
EVMChainTransactionPriority priority) async {
|
||||
final CryptoCurrency transactionCurrency =
|
||||
balance.keys.firstWhere((element) => element.title == token.title);
|
||||
assert(transactionCurrency is Erc20Token);
|
||||
|
||||
final data = _client.getEncodedDataForApprovalTransaction(
|
||||
contractAddress: EthereumAddress.fromHex(
|
||||
(transactionCurrency as Erc20Token).contractAddress),
|
||||
value: EtherAmount.fromBigInt(EtherUnit.wei, amount),
|
||||
toAddress: EthereumAddress.fromHex(spender),
|
||||
);
|
||||
|
||||
final gasFeesModel = await calculateActualEstimatedFeeForCreateTransaction(
|
||||
amount: amount,
|
||||
receivingAddressHex: spender,
|
||||
priority: priority,
|
||||
contractAddress: transactionCurrency.contractAddress,
|
||||
data: data,
|
||||
);
|
||||
|
||||
return _client.signApprovalTransaction(
|
||||
privateKey: _evmChainPrivateKey,
|
||||
spender: spender,
|
||||
amount: amount,
|
||||
priority: priority,
|
||||
gasFee: BigInt.from(gasFeesModel.estimatedGasFee),
|
||||
maxFeePerGas: gasFeesModel.maxFeePerGas,
|
||||
estimatedGasUnits: gasFeesModel.estimatedGasUnits,
|
||||
exponent: transactionCurrency.decimal,
|
||||
contractAddress: transactionCurrency.contractAddress,
|
||||
);
|
||||
}
|
||||
|
||||
Future<void> _updateTransactions() async {
|
||||
try {
|
||||
if (_isTransactionUpdating) {
|
||||
|
|
|
@ -11,6 +11,7 @@ class PendingEVMChainTransaction with PendingTransaction {
|
|||
final BigInt fee;
|
||||
final String amount;
|
||||
final int exponent;
|
||||
final bool isInfiniteApproval;
|
||||
|
||||
PendingEVMChainTransaction({
|
||||
required this.sendTransaction,
|
||||
|
@ -18,10 +19,12 @@ class PendingEVMChainTransaction with PendingTransaction {
|
|||
required this.fee,
|
||||
required this.amount,
|
||||
required this.exponent,
|
||||
this.isInfiniteApproval = false,
|
||||
});
|
||||
|
||||
@override
|
||||
String get amountFormatted {
|
||||
if (isInfiniteApproval) return "∞";
|
||||
final _amount = (BigInt.parse(amount) / BigInt.from(pow(10, exponent))).toString();
|
||||
return _amount.substring(0, min(10, _amount.length));
|
||||
}
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue