expense_apply_controller.dart 2.7 KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768697071727374757677787980818283848586878889909192939495969798
  1. import 'package:flutter_riverpod/flutter_riverpod.dart';
  2. import 'expense_model.dart';
  3. import 'expense_api.dart';
  4. class ExpenseApplyState {
  5. final ExpenseModel expense;
  6. final bool isSubmitting;
  7. const ExpenseApplyState({required this.expense, this.isSubmitting = false});
  8. ExpenseApplyState copyWith({ExpenseModel? expense, bool? isSubmitting}) {
  9. return ExpenseApplyState(
  10. expense: expense ?? this.expense,
  11. isSubmitting: isSubmitting ?? this.isSubmitting,
  12. );
  13. }
  14. }
  15. class ExpenseApplyController extends StateNotifier<ExpenseApplyState> {
  16. final ExpenseApi _api;
  17. ExpenseApplyController(this._api, {ExpenseModel? initial})
  18. : super(
  19. ExpenseApplyState(
  20. expense:
  21. initial ??
  22. ExpenseModel(
  23. id: '',
  24. reportNo: '',
  25. applicantId: '',
  26. applicantName: '',
  27. deptId: '',
  28. deptName: '',
  29. expenseType: '差旅费',
  30. totalAmount: 0.0,
  31. remark: '',
  32. createTime: DateTime.now(),
  33. updateTime: DateTime.now(),
  34. ),
  35. ),
  36. );
  37. void updateType(String type) {
  38. state = state.copyWith(expense: state.expense.copyWith(expenseType: type));
  39. }
  40. void updateRemark(String remark) {
  41. state = state.copyWith(expense: state.expense.copyWith(remark: remark));
  42. }
  43. void addDetail(ExpenseDetailModel detail) {
  44. final details = [...state.expense.details, detail];
  45. state = state.copyWith(expense: state.expense.copyWith(details: details));
  46. }
  47. void removeDetail(int index) {
  48. final details = [...state.expense.details]..removeAt(index);
  49. state = state.copyWith(expense: state.expense.copyWith(details: details));
  50. }
  51. void recalculateAmount() {
  52. final total = state.expense.details.fold<double>(
  53. 0,
  54. (sum, d) => sum + d.totalAmount,
  55. );
  56. state = state.copyWith(expense: state.expense.copyWith(totalAmount: total));
  57. }
  58. Future<bool> submit() async {
  59. state = state.copyWith(isSubmitting: true);
  60. try {
  61. await _api.submit(state.expense.copyWith(status: 'pending'));
  62. return true;
  63. } catch (_) {
  64. return false;
  65. } finally {
  66. state = state.copyWith(isSubmitting: false);
  67. }
  68. }
  69. Future<bool> saveDraft() async {
  70. state = state.copyWith(isSubmitting: true);
  71. try {
  72. await _api.saveDraft(state.expense);
  73. return true;
  74. } catch (_) {
  75. return false;
  76. } finally {
  77. state = state.copyWith(isSubmitting: false);
  78. }
  79. }
  80. }
  81. final expenseApplyProvider = StateNotifierProvider.autoDispose
  82. .family<ExpenseApplyController, ExpenseApplyState, String?>((ref, editId) {
  83. final api = ref.watch(expenseApiProvider);
  84. return ExpenseApplyController(api);
  85. });