Files
worker/lib/core/utils/localization_extension.dart
Phuoc Nguyen 628c81ce13 runable
2025-10-17 17:22:28 +07:00

137 lines
3.7 KiB
Dart

import 'package:flutter/widgets.dart';
import 'package:worker/generated/l10n/app_localizations.dart';
/// Extension on [BuildContext] for easy access to localizations
///
/// Usage:
/// ```dart
/// Text(context.l10n.login)
/// ```
///
/// This provides a shorter and more convenient way to access localized strings
/// compared to the verbose `AppLocalizations.of(context)!` syntax.
extension LocalizationExtension on BuildContext {
/// Get the current app localizations
///
/// Returns the [AppLocalizations] instance for the current context.
/// This will never be null because the app always has a default locale.
AppLocalizations get l10n => AppLocalizations.of(this);
}
/// Extension on [AppLocalizations] for additional formatting utilities
extension LocalizationUtilities on AppLocalizations {
/// Format currency in Vietnamese Dong
///
/// Example: 100000 -> "100.000 ₫"
String formatCurrency(double amount) {
final formatter = _getCurrencyFormatter();
return formatter.format(amount);
}
/// Format points display with formatted number
///
/// Example: 1500 -> "1.500 điểm" or "1,500 points"
String formatPointsDisplay(int points) {
// Use the generated method which already handles the formatting
return pointsBalance(points);
}
/// Format large numbers with thousand separators
///
/// Example: 1000000 -> "1.000.000"
String formatNumber(num number) {
return _formatNumber(number);
}
/// Get currency formatter based on locale
_CurrencyFormatter _getCurrencyFormatter() {
if (localeName.startsWith('vi')) {
return const _VietnameseCurrencyFormatter();
} else {
return const _EnglishCurrencyFormatter();
}
}
/// Format number with thousand separators
String _formatNumber(num number) {
final parts = number.toString().split('.');
final integerPart = parts[0];
final decimalPart = parts.length > 1 ? parts[1] : '';
// Add thousand separators
final buffer = StringBuffer();
final reversedInteger = integerPart.split('').reversed.join();
for (var i = 0; i < reversedInteger.length; i++) {
if (i > 0 && i % 3 == 0) {
buffer.write(localeName.startsWith('vi') ? '.' : ',');
}
buffer.write(reversedInteger[i]);
}
final formattedInteger = buffer.toString().split('').reversed.join();
if (decimalPart.isNotEmpty) {
return '$formattedInteger.$decimalPart';
}
return formattedInteger;
}
}
/// Abstract currency formatter
abstract class _CurrencyFormatter {
const _CurrencyFormatter();
String format(double amount);
}
/// Vietnamese currency formatter
///
/// Format: 100.000 ₫
class _VietnameseCurrencyFormatter extends _CurrencyFormatter {
const _VietnameseCurrencyFormatter();
@override
String format(double amount) {
final rounded = amount.round();
final parts = rounded.toString().split('').reversed.join();
final buffer = StringBuffer();
for (var i = 0; i < parts.length; i++) {
if (i > 0 && i % 3 == 0) {
buffer.write('.');
}
buffer.write(parts[i]);
}
final formatted = buffer.toString().split('').reversed.join();
return '$formatted';
}
}
/// English currency formatter
///
/// Format: ₫100,000
class _EnglishCurrencyFormatter extends _CurrencyFormatter {
const _EnglishCurrencyFormatter();
@override
String format(double amount) {
final rounded = amount.round();
final parts = rounded.toString().split('').reversed.join();
final buffer = StringBuffer();
for (var i = 0; i < parts.length; i++) {
if (i > 0 && i % 3 == 0) {
buffer.write(',');
}
buffer.write(parts[i]);
}
final formatted = buffer.toString().split('').reversed.join();
return '$formatted';
}
}