import 'package:flutter/material.dart'; import 'package:freezed_annotation/freezed_annotation.dart'; import 'package:qpay/http/http.dart'; import 'package:qpay/models/pageable_model.dart'; part 'home_controller.freezed.dart'; part 'home_controller.g.dart'; class HomeScreenModel { List> transactions = []; List categories = []; List providers = []; List filterableProviders = []; List accounts = []; BillProvider? selectedProvider; dynamic selectedCategory; dynamic account = {}; dynamic profile = {}; bool isLoading = false; bool isLoggedIn = false; String? errorMessage; } class Account { late String name; late String description; late String image; late String currency; late String balance; late String availableBalance; late String accountNumber; late String accountType; late String accountHolderName; Account({ required this.name, required this.description, required this.image, required this.currency, required this.balance, }); } @freezed abstract class Category with _$Category { const factory Category({ required String name, required String description, required String? image, required String label, }) = _Category; factory Category.fromJson(Map json) => _$CategoryFromJson(json); } @freezed abstract class BillProvider with _$BillProvider { const factory BillProvider({ required String clientId, required String name, required String description, required bool requiresAccount, required bool requiresAmount, required bool requiresAmountFromMerchant, required bool requiresPhone, required bool requiresReversal, required String? additionalDataString, required String processorType, required String uid, required String image, required String label, required String category, required String? accountFieldName, }) = _BillProvider; factory BillProvider.fromJson(Map json) => _$BillProviderFromJson(json); } class HomeController extends ChangeNotifier { final HomeScreenModel model = HomeScreenModel(); final Http http = Http(); BuildContext context; HomeController(this.context); void _showErrorSnackBar(String? message) { WidgetsBinding.instance.addPostFrameCallback((_) { ScaffoldMessenger.of(context).showSnackBar( SnackBar( content: Text(message.toString()), behavior: SnackBarBehavior.floating, backgroundColor: Colors.deepOrange, ), ); }); } Future getAccounts() async { model.accounts = getFakeAccounts(); notifyListeners(); } Future getProviders() async { try { model.isLoading = true; notifyListeners(); List response = await http.get('/public/providers'); model.providers = response.map((e) => BillProvider.fromJson(e)).toList(); model.filterableProviders = model.providers; if (model.providers.isNotEmpty) { updateSelectedProvider(model.providers[0]); } } catch (e) { logger.e(e); _showErrorSnackBar( "Problem fetching providers, are you connected to the internet?", ); model.errorMessage = e.toString(); model.providers = []; model.filterableProviders = []; } model.isLoading = false; notifyListeners(); } void updateSelectedProvider(BillProvider provider) { model.selectedProvider = provider; // getProducts(provider.uid); notifyListeners(); } Future getTransactions(String userId) async { model.isLoading = true; notifyListeners(); try { Map response = await http.get( '/public/transaction?sort=createdAt,desc&size=3&page=0&userId=$userId', ); PageableModel pageableModel = PageableModel.fromJson(response); model.transactions = pageableModel.content.map((e) => e as Map).toList(); } catch (e) { logger.e(e); _showErrorSnackBar( "Problem fetching transactions, are you connected to the internet?", ); model.errorMessage = e.toString(); model.transactions = []; } finally { model.isLoading = false; notifyListeners(); } } Future getCategories() async { // activate skeletonizer model.categories = getFakeCategoryData(); model.transactions = getFakeTransactions(); // model.filterableProviders = getFakeProviders(); model.isLoading = true; notifyListeners(); // Simulate fetching categories try { List response = await http.get('/public/categories'); model.categories = response.map((e) => Category.fromJson(e)).toList(); if (model.categories.isNotEmpty) { updateSelectedCategory(model.categories[0]); } } on Exception catch (e) { logger.e(e); _showErrorSnackBar( "Problem fetching categories, are you connected to the internet?", ); model.errorMessage = e.toString(); model.categories = []; } finally { model.isLoading = false; notifyListeners(); } } Future updateSelectedCategory(Category? category) async { if (category == null) { model.filterableProviders = model.providers; notifyListeners(); return; } model.selectedCategory = category; model.filterableProviders = model.providers .where((element) => element.category == category.label) .toList(); notifyListeners(); } List> getFakeTransactions() { return [ { "id": "77b2c479-b803-49fc-b5c3-acbf52cba633", "trace": "22a3044b-8f53-4e43-b4f5-c77dcec48d2d", "amount": 25.0, "charge": 0.0, "gatewayCharge": 0.25, "tax": 0.5, "totalAmount": 25.75, "reference": "c838136c-c015-4a0b-9c7c-52f127c8c109", "paymentProcessorLabel": "MPGS", "paymentProcessorImage": "visa-mastercard.png", "debitPhone": "", "debitAccount": "", "debitCurrency": "USD", "debitRef": "peak", "creditPhone": "", "creditAccount": "07088597534", "billClientId": "powertel_zesa", "billName": "Zesa", "type": "REQUEST", "authType": "WEB", "errorMessage": "", "responseCode": "00", "status": "SUCCESS", "sdkActionId": "0aa0d90d-6132-48a7-a5d8-e796f757c73f", }, ]; } List getFakeProviders() { return [ BillProvider( clientId: '1', name: 'ZESA', description: 'Pay your electricity bills easily', requiresAccount: false, requiresAmount: false, requiresAmountFromMerchant: false, requiresPhone: false, requiresReversal: false, additionalDataString: '', processorType: '', uid: '', image: 'econet.png', label: '', category: '', accountFieldName: '', ), ]; } // required by skeletonizer List getFakeCategoryData() { return [ Category( name: 'Airtime', description: 'Pay your electricity bills easily', image: 'assets/images/electricity.png', label: 'Electricity', ), ]; } List getFakeAccounts() { return [ Account( name: 'Vusumuzi Khoza', description: 'USD Wallet', image: 'united-states.png', currency: 'USD', balance: '47655.02', ), Account( name: 'Vusumuzi Khoza', description: 'ZWG Wallet', image: 'zimbabwe.png', currency: 'ZWL', balance: '36.00', ), ]; } }