125 lines
4.2 KiB
Dart
125 lines
4.2 KiB
Dart
import 'package:flutter/material.dart';
|
|
|
|
import 'package:provider/provider.dart';
|
|
|
|
import 'package:pshared/controllers/balance_mask/ledger_accounts.dart';
|
|
import 'package:pshared/models/ledger/account.dart';
|
|
import 'package:pshared/utils/currency.dart';
|
|
import 'package:pshared/utils/money.dart';
|
|
|
|
import 'package:pweb/pages/dashboard/buttons/balance/config.dart';
|
|
import 'package:pweb/pages/dashboard/buttons/balance/header.dart';
|
|
import 'package:pweb/widgets/refresh_balance/ledger.dart';
|
|
|
|
import 'package:pweb/generated/i18n/app_localizations.dart';
|
|
|
|
|
|
class LedgerAccountCard extends StatelessWidget {
|
|
final LedgerAccount account;
|
|
|
|
const LedgerAccountCard({super.key, required this.account});
|
|
|
|
String _formatBalance() {
|
|
final money = account.balance?.balance;
|
|
if (money == null) return '--';
|
|
|
|
final amount = parseMoneyAmount(money.amount, fallback: double.nan);
|
|
if (amount.isNaN) {
|
|
return '${money.amount} ${money.currency}';
|
|
}
|
|
|
|
try {
|
|
final currency = currencyStringToCode(money.currency);
|
|
final symbol = currencyCodeToSymbol(currency);
|
|
if (symbol.trim().isEmpty) {
|
|
return '${amountToString(amount)} ${money.currency}';
|
|
}
|
|
return '${amountToString(amount)} $symbol';
|
|
} catch (_) {
|
|
return '${amountToString(amount)} ${money.currency}';
|
|
}
|
|
}
|
|
|
|
String _formatMaskedBalance() {
|
|
final currency = account.currency.trim();
|
|
if (currency.isEmpty) return '••••';
|
|
try {
|
|
final symbol = currencyCodeToSymbol(currencyStringToCode(currency));
|
|
if (symbol.trim().isEmpty) {
|
|
return '•••• $currency';
|
|
}
|
|
return '•••• $symbol';
|
|
} catch (_) {
|
|
return '•••• $currency';
|
|
}
|
|
}
|
|
|
|
@override
|
|
Widget build(BuildContext context) {
|
|
final textTheme = Theme.of(context).textTheme;
|
|
final colorScheme = Theme.of(context).colorScheme;
|
|
final loc = AppLocalizations.of(context)!;
|
|
final accountName = account.name.trim();
|
|
final accountCode = account.accountCode.trim();
|
|
final title = accountName.isNotEmpty ? accountName : loc.paymentTypeLedger;
|
|
final subtitle = accountCode.isNotEmpty ? accountCode : null;
|
|
final badge = account.currency.trim().isEmpty
|
|
? null
|
|
: account.currency.toUpperCase();
|
|
|
|
return Card(
|
|
color: colorScheme.onSecondary,
|
|
elevation: WalletCardConfig.elevation,
|
|
shape: RoundedRectangleBorder(
|
|
borderRadius: BorderRadius.circular(WalletCardConfig.borderRadius),
|
|
),
|
|
child: Padding(
|
|
padding: WalletCardConfig.contentPadding,
|
|
child: Column(
|
|
crossAxisAlignment: CrossAxisAlignment.start,
|
|
children: [
|
|
BalanceHeader(title: title, subtitle: subtitle, badge: badge),
|
|
Row(
|
|
children: [
|
|
Consumer<LedgerBalanceMaskController>(
|
|
builder: (context, controller, _) {
|
|
final isMasked = controller.isBalanceMasked(
|
|
account.ledgerAccountRef,
|
|
);
|
|
return Row(
|
|
children: [
|
|
Text(
|
|
isMasked ? _formatMaskedBalance() : _formatBalance(),
|
|
style: textTheme.headlineSmall?.copyWith(
|
|
fontWeight: FontWeight.bold,
|
|
color: colorScheme.onSurface,
|
|
),
|
|
),
|
|
const SizedBox(width: 12),
|
|
GestureDetector(
|
|
onTap: () => controller.toggleBalanceMask(
|
|
account.ledgerAccountRef,
|
|
),
|
|
child: Icon(
|
|
isMasked ? Icons.visibility_off : Icons.visibility,
|
|
size: 24,
|
|
color: colorScheme.onSurface,
|
|
),
|
|
),
|
|
],
|
|
);
|
|
},
|
|
),
|
|
const SizedBox(width: 12),
|
|
LedgerBalanceRefreshButton(
|
|
ledgerAccountRef: account.ledgerAccountRef,
|
|
),
|
|
],
|
|
),
|
|
],
|
|
),
|
|
),
|
|
);
|
|
}
|
|
}
|