format static method
String
format(
- dynamic amount,
- CurrencyFormat settings, {
- bool compact = false,
- int decimal = 2,
- dynamic showThousandSeparator = true,
- dynamic enforceDecimals = false,
Format amount using the settings of a currency.
If compact is true the compact form will be used. e.g. '$ 1.23K' instead of '$ 1,230'.
decimal is the number of decimal places used when rounding.
e.g. '$ 45.5' (1 decimal place), '$ 45.52' (2 decimal places).
If showThousandSeparator is set to false, the thousand separator won't be shown.
e.g. '$ 1200'instead of '$ 1,200'.
If enforceDecimals is set to true, decimals will be shown even if it is an integer.
e.g. '$ 5.00' instead of '$ 5'.
Implementation
static String format(
amount,
CurrencyFormat settings, {
bool compact = false,
int decimal = 2,
showThousandSeparator = true,
enforceDecimals = false,
}) {
double originalAmount = double.parse('$amount');
bool isNegative = originalAmount < 0;
double absAmount = originalAmount.abs();
String letter = '';
String formattedNumberString;
// Step 2: Perform numerical formatting on absAmount
if (compact) {
double compactCalcAmount = absAmount;
for (int i = 0; i < _letters.length; i++) {
if (compactCalcAmount >= _letters.keys.elementAt(i)) {
letter = _letters.values.elementAt(i);
compactCalcAmount /= _letters.keys.elementAt(i);
break;
}
}
formattedNumberString = compactCalcAmount.toStringAsPrecision(3);
} else {
formattedNumberString = absAmount.toStringAsFixed(decimal);
}
// Rounding for non-enforced decimals (only if not compact)
// This must use '.' for parsing, so it's done before replacing the decimal separator.
if (!enforceDecimals && !compact) {
double tempNum = double.parse(
formattedNumberString); // Assumes '.' as decimal separator
if (tempNum == tempNum.round()) {
formattedNumberString = tempNum.round().toString();
}
}
// Replace '.' with the settings-defined decimal separator
formattedNumberString =
formattedNumberString.replaceAll('.', settings.decimalSeparator);
// Apply thousand separator if needed
// This operates on the number string which is now purely numerical (absolute)
// and has the correct decimal separator.
if (showThousandSeparator) {
List<String> parts =
formattedNumberString.split(settings.decimalSeparator);
String integerPart = parts[0];
String decimalPart =
parts.length > 1 ? settings.decimalSeparator + parts[1] : '';
String newIntegerPart = '';
for (int i = 0; i < integerPart.length; i++) {
newIntegerPart =
integerPart[integerPart.length - i - 1] + newIntegerPart;
if ((i + 1) % 3 == 0 && i < integerPart.length - 1) {
newIntegerPart = settings.thousandSeparator + newIntegerPart;
}
}
formattedNumberString = newIntegerPart + decimalPart;
}
// Step 3 & 4: Sign handling and final assembly
String signComponent = '';
if (isNegative) {
if (settings.symbolSide == SymbolSide.left &&
settings.negativeSignPlacement ==
NegativeSignPlacement.beforeSymbol) {
signComponent = '-'; // Sign will go before the symbol
} else {
formattedNumberString =
'-$formattedNumberString'; // Sign will go with the number
}
}
// Step 5: Construct final string
switch (settings.symbolSide) {
case SymbolSide.left:
return '$signComponent${settings.symbol}${settings.symbolSeparator}$formattedNumberString$letter';
case SymbolSide.right:
return '$formattedNumberString$letter${settings.symbolSeparator}${settings.symbol}';
default: // SymbolSide.none
return '$formattedNumberString$letter';
}
}