import 'package:comwell_key_app/check_out/models/payment_method.dart';
import 'package:comwell_key_app/services/models/booking_dto.dart';
import 'package:comwell_key_app/check_out/pages/check_out_page.dart';
import 'package:equatable/equatable.dart';
class CheckoutState extends Equatable {
final Iterable<BookingAddonItem> _items;
final bool isTermsAccepted;
final bool applyClubPoints;
final int clubPoints;
final bool successfulCheckout;
final CheckoutPage page;
final CheckoutPaymentMethod? paymentMethod;
final bool showTermsError;
final num bookingBalance;
final bool isPaymentProcessingNeeded;
final bool isLoading;
final bool hasCheckoutError;
int get totalPriceBeforeDiscount => _sumOfList(_items);
int get totalPriceAfterDiscount => _sumOfList(items);
int get totalPrice => _sumOfList(_items);
Iterable<BookingAddonItem> get items {
if (applyClubPoints) {
return [
..._items,
BookingAddonItem("discount", "discount", clubPoints * -1, clubPoints * -1),
];
}
return _items;
}
int _sumOfList(Iterable<BookingAddonItem> list) {
if (list.isEmpty) return 0;
return list.map((item) => item.price).reduce((total, price) => total + price);
}
const CheckoutState({
required Iterable<BookingAddonItem> items,
required this.isTermsAccepted,
required this.page,
required this.showTermsError,
required this.clubPoints,
required this.applyClubPoints,
this.paymentMethod,
required this.bookingBalance,
required this.successfulCheckout,
required this.isPaymentProcessingNeeded,
required this.isLoading,
required this.hasCheckoutError,
}) : _items = items;
CheckoutState.initial(this.bookingBalance)
: _items = [],
isTermsAccepted = false,
page = CheckoutPage.confirmation,
showTermsError = false,
clubPoints = 0,
paymentMethod = CheckoutPaymentMethod.creditCard,
applyClubPoints = false,
successfulCheckout = false,
isLoading = false,
isPaymentProcessingNeeded = true,
hasCheckoutError = false;
CheckoutState itemsUpdated(Iterable<BookingAddonItem> items) {
final newItems = <BookingAddonItem>[];
for (var item in items) {
newItems.add(item.copyWith(price: item.price * item.quantity));
}
return _copyWith(items: newItems);
}
CheckoutState loading() => _copyWith(isLoading: true);
CheckoutState loaded() => _copyWith(isLoading: false);
CheckoutState termsAccepted() => _copyWith(termsAccepted: true, showTermsError: false);
CheckoutState termsDenied() => _copyWith(termsAccepted: false);
CheckoutState clubPointsApplied() => _copyWith(applyClubPoints: true);
CheckoutState clubPointsRemoved() => _copyWith(applyClubPoints: false);
CheckoutState paymentMethodChanged(CheckoutPaymentMethod payment) =>
_copyWith(paymentMethod: payment);
CheckoutState pageChanged(CheckoutPage page) => _copyWith(page: page);
CheckoutState clubPointsFetched(int clubPoints) => _copyWith(clubPoints: clubPoints);
CheckoutState showAcceptTermsError() => _copyWith(showTermsError: true);
CheckoutState checkoutSuccess() => _copyWith(successfulCheckout: true, hasCheckoutError: false);
CheckoutState checkoutError() => _copyWith(successfulCheckout: false, hasCheckoutError: true);
CheckoutState paymentProcessingNeeded() => _copyWith(isPaymentProcessingNeeded: true);
CheckoutState paymentProcessingNotNeeded() => _copyWith(isPaymentProcessingNeeded: false);
CheckoutState _copyWith({
Iterable<BookingAddonItem>? items,
bool? termsAccepted,
bool? applyClubPoints,
CheckoutPage? page,
CheckoutPaymentMethod? paymentMethod,
int? clubPoints,
bool? showTermsError,
num? bookingBalance,
bool? successfulCheckout,
bool? isPaymentProcessingNeeded,
bool? isLoading,
bool? hasCheckoutError,
}) {
return CheckoutState(
items: items ?? _items,
page: page ?? this.page,
clubPoints: clubPoints ?? this.clubPoints,
showTermsError: showTermsError ?? this.showTermsError,
isTermsAccepted: termsAccepted ?? isTermsAccepted,
applyClubPoints: applyClubPoints ?? this.applyClubPoints,
paymentMethod: paymentMethod ?? this.paymentMethod,
bookingBalance: bookingBalance ?? this.bookingBalance,
successfulCheckout: successfulCheckout ?? this.successfulCheckout,
isPaymentProcessingNeeded: isPaymentProcessingNeeded ?? this.isPaymentProcessingNeeded,
isLoading: isLoading ?? this.isLoading,
hasCheckoutError: hasCheckoutError ?? this.hasCheckoutError,
);
}
@override
List<Object?> get props => [
_items,
isTermsAccepted,
applyClubPoints,
page,
showTermsError,
paymentMethod,
totalPriceBeforeDiscount,
totalPriceAfterDiscount,
totalPrice,
successfulCheckout,
isPaymentProcessingNeeded,
isLoading,
hasCheckoutError,
];
}