refactor: remove `toDouble` method and reverted other changes (#3531)

Konstantin Ullrich committed Aug 18, 2026 at 15:12 UTC 1f0f51fec5aad9ffd3e73aeb6a38c652e168f208
4 files changed +45 -32
cw_core/lib/amount/money.dart
-4
@@ -202,10 +202,6 @@ class Money implements Comparable<Money> {
202 @override
203 int get hashCode => amount.hashCode ^ currency.hashCode;
204
205 - // Added this to reduce the hops we do to convert Money to double
206 - // for fiat conversion and display
207 - double toDouble() => amount / multiplierOf(currency.decimals);
208 -
205 @override
206 String toString() => formatFixed(amount, currency.decimals);
207
cw_core/lib/format_fixed.dart
+22 -9
@@ -4,31 +4,44 @@ String formatFixed(BigInt value, int? decimals, {int? fractionalDigits, bool tri
4 decimals ??= 0;
5 fractionalDigits ??= decimals;
6
7 - final multiplier = multiplierOf(decimals);
8 - var negative = value.isNegative;
9 - if (negative) value = -value;
7 + final multiplier = getMultiplier(decimals);
8 + // Make sure wei is a big number (convert as necessary)
9 + final negative = value.isNegative;
10 + if (negative) {
11 + value = -value;
12 + }
13
11 - var fraction = (value % multiplier).toString().padLeft(decimals, "0");
14 + var fraction =
15 + value.modPow(BigInt.one, BigInt.parse(multiplier)).toString().padLeft(decimals, "0");
16
13 - if (fractionalDigits < 0) fractionalDigits = 0;
14 - if (fractionalDigits > decimals) fractionalDigits = decimals;
17 + if (fractionalDigits < 0) {
18 + fractionalDigits = 0;
19 + }
20 + if (fractionalDigits > decimals) {
21 + fractionalDigits = decimals;
22 + }
23 fraction = fraction.substring(0, fractionalDigits);
24
25 if (trimZeros) {
26 fraction = removeTrailing("0", fraction);
27 }
28
21 - final whole = value ~/ multiplier;
29 + final whole = value ~/ BigInt.parse(multiplier);
30
31 final valString = fraction.isEmpty ? "$whole" : "$whole.$fraction";
32
25 - if (negative) return "-$valString";
33 + if (negative) {
34 + return "-$valString";
35 + }
36
37 return valString;
38 }
39
40 String removeTrailing(String pattern, String from) {
31 - if (pattern.isEmpty) return from;
41 + if (pattern.isEmpty) {
42 + return from;
43 + }
44 +
45 var i = from.length;
46 while (i > 0 && from.startsWith(pattern, i - pattern.length)) {
47 i -= pattern.length;
cw_core/lib/parse_fixed.dart
+17 -13
@@ -37,40 +37,44 @@ BigInt parseFixed(String value, int decimals) {
37 }
38
39 final negative = value.startsWith("-");
40 - if (negative) value = value.substring(1);
40 + if (negative) {
41 + value = value.substring(1);
42 + }
43
42 - if (value == ".") throw FormatException("missing value, value, $value");
44 + if (value == ".") {
45 + throw FormatException("missing value, value, $value");
46 + }
47
44 - if (value.startsWith(".")) value = "0$value";
48 + if (value.startsWith(".")) {
49 + value = "0$value";
50 + }
51
52 final comps = value.split(".");
53 if (comps.length > 2) {
54 throw FormatException("too many decimal points, value, $value");
55 }
56
51 - var whole = comps.isNotEmpty ? comps[0] : "0";
52 - var fraction = (comps.length == 2 ? comps[1] : "0").padRight(decimals, "0");
57 + final whole = comps.isNotEmpty ? comps[0] : "0";
58 + final fraction = (comps.length == 2 ? comps[1] : "0").padRight(decimals, "0");
59
60 if (fraction.length > multiplier.length - 1) {
61 throw FormatException(
56 - "fractional component(${fraction.length}) exceeds decimals(${decimals}), underflow, parseFixed");
62 + "fractional component(${fraction.length}) exceeds decimals(${decimals}), underflow, parseFixed",
63 + );
64 }
65
66 final wholeValue = BigInt.parse(whole);
67 final fractionValue = BigInt.parse(fraction);
61 - final multiplierValue = multiplierOf(decimals);
68 + final multiplierValue = BigInt.parse(multiplier);
69
70 var wei = (wholeValue * multiplierValue) + fractionValue;
71
65 - if (negative) wei *= BigInt.from(-1);
72 + if (negative) {
73 + wei *= BigInt.from(-1);
74 + }
75
76 return wei;
77 }
78
79 // Returns a string "1" followed by decimal "0"s
80 String getMultiplier(int decimals) => "1".padRight(decimals + 1, "0");
72 -
73 -final _multipliers = <int, BigInt>{};
74 -
75 -// this is more direct and faster than having it as string then parsing everytime to get the number
76 -BigInt multiplierOf(int decimals) => _multipliers[decimals] ??= BigInt.from(10).pow(decimals);
lib/view_model/dashboard/transaction_list_item.dart
+6 -6
@@ -203,7 +203,7 @@ class TransactionListItem extends ActionListItem with Keyable {
203 case WalletType.decred:
204 case WalletType.zcash:
205 amount = calculateFiatAmountRaw(
206 - cryptoAmount: transaction.amount.toDouble(),
206 + cryptoAmount: double.parse(transaction.amount.toString()),
207 price: price,
208 ).withLocalSeperator(_appStore.settingsStore.languageCode);
209 case WalletType.ethereum:
@@ -214,15 +214,15 @@ class TransactionListItem extends ActionListItem with Keyable {
214 final asset = assetOfTransaction;
215 final price = balanceViewModel.fiatConversionStore.prices[asset];
216 amount = calculateFiatAmountRaw(
217 - cryptoAmount: transaction.amount.toDouble(),
217 + cryptoAmount: double.parse(transaction.amount.toString()),
218 price: price,
219 ).withLocalSeperator(_appStore.settingsStore.languageCode);
220 break;
221 case WalletType.solana:
222 - final asset = assetOfTransaction;
222 + final asset = solana!.assetOfTransaction(balanceViewModel.wallet, transaction);
223 final price = balanceViewModel.fiatConversionStore.prices[asset];
224 amount = calculateFiatAmountRaw(
225 - cryptoAmount: transaction.amount.toDouble(),
225 + cryptoAmount: double.parse(transaction.amount.toString()),
226 price: price,
227 ).withLocalSeperator(_appStore.settingsStore.languageCode);
228 break;
@@ -230,7 +230,7 @@ class TransactionListItem extends ActionListItem with Keyable {
230 final asset = tron!.assetOfTransaction(balanceViewModel.wallet, transaction);
231 final price = balanceViewModel.fiatConversionStore.prices[asset];
232 amount = calculateFiatAmountRaw(
233 - cryptoAmount: transaction.amount.toDouble(),
233 + cryptoAmount: double.parse(transaction.amount.toString()),
234 price: price,
235 ).withLocalSeperator(_appStore.settingsStore.languageCode);
236 break;
@@ -242,7 +242,7 @@ class TransactionListItem extends ActionListItem with Keyable {
242 }
243 final price = balanceViewModel.fiatConversionStore.prices[asset];
244 amount = calculateFiatAmountRaw(
245 - cryptoAmount: transaction.amount.toDouble(),
245 + cryptoAmount: double.parse(transaction.amount.toString()),
246 price: price,
247 ).withLocalSeperator(_appStore.settingsStore.languageCode);
248 break;