feat: Add logger service and improve expense dialog with enhanced receipt management and calculation logic.
This commit is contained in:
@@ -4,107 +4,114 @@ import 'package:flutter/material.dart';
|
||||
import 'expense_split.dart';
|
||||
|
||||
/// Enumeration of supported currencies for expenses.
|
||||
///
|
||||
///
|
||||
/// Each currency includes both a display symbol and standard currency code.
|
||||
enum ExpenseCurrency {
|
||||
/// Euro currency
|
||||
eur('€', 'EUR'),
|
||||
/// US Dollar currency
|
||||
|
||||
/// US Dollar currency
|
||||
usd('\$', 'USD'),
|
||||
|
||||
/// British Pound currency
|
||||
gbp('£', 'GBP');
|
||||
|
||||
const ExpenseCurrency(this.symbol, this.code);
|
||||
|
||||
|
||||
/// Currency symbol for display (e.g., €, $, £)
|
||||
final String symbol;
|
||||
|
||||
|
||||
/// Standard currency code (e.g., EUR, USD, GBP)
|
||||
final String code;
|
||||
}
|
||||
|
||||
/// Enumeration of expense categories with display names and icons.
|
||||
///
|
||||
///
|
||||
/// Provides predefined categories for organizing travel expenses.
|
||||
enum ExpenseCategory {
|
||||
/// Restaurant and food expenses
|
||||
restaurant('Restaurant', Icons.restaurant),
|
||||
|
||||
/// Transportation expenses
|
||||
transport('Transport', Icons.directions_car),
|
||||
|
||||
/// Accommodation and lodging expenses
|
||||
accommodation('Accommodation', Icons.hotel),
|
||||
|
||||
/// Entertainment and activity expenses
|
||||
entertainment('Entertainment', Icons.local_activity),
|
||||
|
||||
/// Shopping expenses
|
||||
shopping('Shopping', Icons.shopping_bag),
|
||||
|
||||
/// Other miscellaneous expenses
|
||||
other('Other', Icons.category);
|
||||
|
||||
const ExpenseCategory(this.displayName, this.icon);
|
||||
|
||||
|
||||
/// Human-readable display name for the category
|
||||
final String displayName;
|
||||
|
||||
|
||||
/// Icon representing the category
|
||||
final IconData icon;
|
||||
}
|
||||
|
||||
/// Model representing a travel expense.
|
||||
///
|
||||
///
|
||||
/// This class encapsulates all information about an expense including
|
||||
/// amount, currency, category, who paid, how it's split among participants,
|
||||
/// and receipt information. It extends [Equatable] for value comparison.
|
||||
class Expense extends Equatable {
|
||||
/// Unique identifier for the expense
|
||||
final String id;
|
||||
|
||||
|
||||
/// ID of the group this expense belongs to
|
||||
final String groupId;
|
||||
|
||||
|
||||
/// Description of the expense
|
||||
final String description;
|
||||
|
||||
|
||||
/// Amount of the expense in the original currency
|
||||
final double amount;
|
||||
|
||||
|
||||
/// Currency of the expense
|
||||
final ExpenseCurrency currency;
|
||||
|
||||
|
||||
/// Amount converted to EUR for standardized calculations
|
||||
final double amountInEur;
|
||||
|
||||
|
||||
/// Category of the expense
|
||||
final ExpenseCategory category;
|
||||
|
||||
|
||||
/// ID of the user who paid for this expense
|
||||
final String paidById;
|
||||
|
||||
|
||||
/// Name of the user who paid for this expense
|
||||
final String paidByName;
|
||||
|
||||
|
||||
/// Date when the expense occurred
|
||||
final DateTime date;
|
||||
|
||||
|
||||
/// Timestamp when the expense was created
|
||||
final DateTime createdAt;
|
||||
|
||||
|
||||
/// Timestamp when the expense was last edited (null if never edited)
|
||||
final DateTime? editedAt;
|
||||
|
||||
|
||||
/// Whether this expense has been edited after creation
|
||||
final bool isEdited;
|
||||
|
||||
|
||||
/// Whether this expense has been archived
|
||||
final bool isArchived;
|
||||
|
||||
|
||||
/// URL to the receipt image (optional)
|
||||
final String? receiptUrl;
|
||||
|
||||
|
||||
/// List of expense splits showing how the cost is divided
|
||||
final List<ExpenseSplit> splits;
|
||||
|
||||
/// Creates a new [Expense] instance.
|
||||
///
|
||||
///
|
||||
/// All parameters except [editedAt] and [receiptUrl] are required.
|
||||
const Expense({
|
||||
required this.id,
|
||||
@@ -144,13 +151,17 @@ class Expense extends Equatable {
|
||||
paidByName: map['paidByName'] ?? '',
|
||||
date: _parseDateTime(map['date']),
|
||||
createdAt: _parseDateTime(map['createdAt']),
|
||||
editedAt: map['editedAt'] != null ? _parseDateTime(map['editedAt']) : null,
|
||||
editedAt: map['editedAt'] != null
|
||||
? _parseDateTime(map['editedAt'])
|
||||
: null,
|
||||
isEdited: map['isEdited'] ?? false,
|
||||
isArchived: map['isArchived'] ?? false,
|
||||
receiptUrl: map['receiptUrl'],
|
||||
splits: (map['splits'] as List?)
|
||||
?.map((s) => ExpenseSplit.fromMap(s))
|
||||
.toList() ?? [],
|
||||
splits:
|
||||
(map['splits'] as List?)
|
||||
?.map((s) => ExpenseSplit.fromMap(s))
|
||||
.toList() ??
|
||||
[],
|
||||
);
|
||||
}
|
||||
|
||||
@@ -243,25 +254,36 @@ class Expense extends Equatable {
|
||||
|
||||
// Marquer comme archivé
|
||||
Expense copyWithArchived() {
|
||||
return copyWith(
|
||||
isArchived: true,
|
||||
);
|
||||
return copyWith(isArchived: true);
|
||||
}
|
||||
|
||||
// Ajouter/mettre à jour l'URL du reçu
|
||||
Expense copyWithReceipt(String receiptUrl) {
|
||||
return copyWith(
|
||||
receiptUrl: receiptUrl,
|
||||
);
|
||||
return copyWith(receiptUrl: receiptUrl);
|
||||
}
|
||||
|
||||
// Mettre à jour les splits
|
||||
Expense copyWithSplits(List<ExpenseSplit> newSplits) {
|
||||
return copyWith(
|
||||
splits: newSplits,
|
||||
);
|
||||
return copyWith(splits: newSplits);
|
||||
}
|
||||
|
||||
@override
|
||||
List<Object?> get props => [id];
|
||||
}
|
||||
List<Object?> get props => [
|
||||
id,
|
||||
groupId,
|
||||
description,
|
||||
amount,
|
||||
currency,
|
||||
amountInEur,
|
||||
category,
|
||||
paidById,
|
||||
paidByName,
|
||||
date,
|
||||
createdAt,
|
||||
editedAt,
|
||||
isEdited,
|
||||
isArchived,
|
||||
receiptUrl,
|
||||
splits,
|
||||
];
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user