import 'dart:convert'; import 'dart:developer'; import 'package:flutter/widgets.dart'; import 'package:http/http.dart'; import 'package:provider/provider.dart'; import 'package:test_sa/controllers/api_routes/api_manager.dart'; import 'package:test_sa/controllers/api_routes/urls.dart'; import 'package:test_sa/controllers/providers/api/all_requests_provider.dart'; import 'package:test_sa/extensions/context_extension.dart'; import 'package:test_sa/extensions/enum_extensions.dart'; import 'package:test_sa/models/enums/user_types.dart'; import 'package:test_sa/models/new_models/dashboard_count.dart'; import 'package:test_sa/models/new_models/dashboard_detail.dart' as DD; import 'package:test_sa/models/new_models/swipe_model.dart'; import 'package:test_sa/new_views/app_style/app_color.dart'; import '../controllers/providers/api/user_provider.dart'; class DashBoardProvider extends ChangeNotifier { bool isAllCountLoading = false; bool isLoading = false; bool _isDetailLoading = false; bool _isShowDashBoardCalendar = true; DateTime _upcomingFilterSelectedDate = DateTime.now(); DateTime get upcomingFilterSelectedDate => _upcomingFilterSelectedDate; set upcomingFilterSelectedDate(DateTime value) { _upcomingFilterSelectedDate = value; notifyListeners(); } bool get isShowDashBoardCalendar => _isShowDashBoardCalendar; set isShowDashBoardCalendar(bool value) { _isShowDashBoardCalendar = value; notifyListeners(); } int _status = 0; int get status => _status; set status(int value) { _status = value; notifyListeners(); } List listIndex = []; int? _currentListIndex; int? get currentListIndex => _currentListIndex; // Helper method to check if a tab index is UnAssigned bool isUnassignedTab(int index) { if (index >= 0 && index < tabs.length) { return tabs[index].requestType == RequestTypeEnum.unassigned; } return false; } // Helper method to get the UnAssigned tab index (returns -1 if not found) int getUnassignedTabIndex() { for (int i = 0; i < tabs.length; i++) { if (tabs[i].requestType == RequestTypeEnum.unassigned) { return i; } } return -1; } set currentListIndex(int? value) { _currentListIndex = value; if (value == null) { listIndex.clear(); } else { // Check if the selected tab is UnAssigned by its requestType bool isUnassignedClicked = isUnassignedTab(value); int unassignedIndex = getUnassignedTabIndex(); bool hasUnassignedSelected = unassignedIndex != -1 && listIndex.contains(unassignedIndex); if (isUnassignedClicked) { // UnAssigned is exclusive - clear all and select only UnAssigned listIndex.clear(); listIndex.add(value); } else { // Other category clicked if (hasUnassignedSelected) { // If UnAssigned was selected, remove it first listIndex.remove(unassignedIndex); } // Toggle the selected category if (listIndex.contains(value)) { listIndex.remove(value); } else { listIndex.add(value); } } } notifyListeners(); } int? stateCode; DashboardCount? dashboardCount; DD.DashboardDetail? _requestDetailList; DD.DashboardDetail? get requestDetailList => _requestDetailList; int getStatusCount(RequestTypeEnum requestType) { switch (requestType) { case RequestTypeEnum.unassigned: return dashboardCount?.data?.countUnAssigned ?? 0; case RequestTypeEnum.open: return dashboardCount?.data?.countOpen ?? 0; case RequestTypeEnum.inProgress: return dashboardCount?.data?.countInprogress ?? 0; case RequestTypeEnum.completed: return dashboardCount?.data?.countComplete ?? 0; case RequestTypeEnum.pendingAcknowledgment: return dashboardCount?.data?.countAcknowledge ?? 0; case RequestTypeEnum.canceled: return dashboardCount?.data?.countCanceled ?? 0; case RequestTypeEnum.closed: return dashboardCount?.data?.countClose ?? 0; case RequestTypeEnum.overdue: return dashboardCount?.data?.countOverdue ?? 0; case RequestTypeEnum.highPriority: return dashboardCount?.data?.countHighPriority ?? 0; default: return 0; } } List tabs = []; void setTabs({required UsersTypes userType, required BuildContext context}) { tabs = CategoryTabs.getTabs(userType: userType, context: context); } set requestDetailList(DD.DashboardDetail? value) { _requestDetailList = value; notifyListeners(); } final pageItemNumber = 10; int pageNum = 1; bool nextPage = true; void reset() { pageNum = 1; nextPage = true; stateCode = null; _requestDetailList = null; dashboardCount = null; } void refreshDashboard({required UsersTypes userType, required BuildContext context}) { setTabs(userType: userType, context: context); getDashBoardCount(usersType: userType); resetRequestDataList(); if (listIndex.isEmpty) { Provider.of(context, listen: false) ..reset() ..getAllRequests(context); } else if (listIndex.length == 1 && isUnassignedTab(listIndex[0])) { // UnAssigned only - check by requestType, not by index getRequestDetail(usersType: userType, status: tabs[listIndex[0]].tag, tabId: tabs[listIndex[0]].id); } else { // Multiple categories selected getMultiSelectCategoryRequests(usersType: userType, context: context); } // notifyListeners(); } void resetRequestDataList() { pageNum = 1; nextPage = true; stateCode = null; _requestDetailList = null; } void getAllRequests(UsersTypes userTypes) { getDashBoardCount(usersType: userTypes); // getRequestDetail(usersType: userTypes); } Future getDashBoardCount({required UsersTypes usersType}) async { isAllCountLoading = true; notifyListeners(); String url = ''; // if (usersType == UsersTypes.qualityUser) { // url = URLs.qaAuditorCount; // } else if (usersType == UsersTypes.engineer || usersType == UsersTypes.assessor || usersType == UsersTypes.assessorTl) { // url = URLs.engineerDashboardCountUrl; // } else { // url = URLs.nurseDashboardCountUrl; // } final urlMap = { UsersTypes.qualityUser: URLs.qaAuditorCount, UsersTypes.commissioningEngineer: URLs.commissioningEngineerCount, UsersTypes.engineer: URLs.engineerDashboardCountUrl, UsersTypes.assessor: URLs.engineerDashboardCountUrl, UsersTypes.assessorTl: URLs.engineerDashboardCountUrl, }; url = urlMap[usersType] ?? URLs.nurseDashboardCountUrl; Response response; try { response = await ApiManager.instance.post(url, body: {}); stateCode = response.statusCode; if (response.statusCode >= 200 && response.statusCode < 300) { dashboardCount = DashboardCount.fromJson(json.decode(response.body)); } isAllCountLoading = false; notifyListeners(); return response.statusCode; } catch (error) { isAllCountLoading = false; stateCode = -1; notifyListeners(); return -1; } } Future getWorkOrderById(int id) async { isLoading = true; notifyListeners(); Response response; try { response = await ApiManager.instance.get(URLs.getWorkOrderByIdUrl + "?workOrderId=$id"); stateCode = response.statusCode; if (response.statusCode >= 200 && response.statusCode < 300) { dashboardCount = DashboardCount.fromJson(json.decode(response.body)); } isAllCountLoading = false; notifyListeners(); return response.statusCode; } catch (error) { isAllCountLoading = false; stateCode = -1; notifyListeners(); return -1; } } void getHighPriorityRequests({bool showLoader = true, required UsersTypes usersType}) { getRequestDetail( showLoader: showLoader, usersType: usersType, isHighPriority: true, ); } void getOverdueRequests({bool showLoader = true, required UsersTypes usersType}) { getRequestDetail(showLoader: showLoader, usersType: usersType, isOverdue: true); } void getOpenRequests({bool showLoader = true, required UsersTypes usersType}) { getRequestDetail(showLoader: showLoader, usersType: usersType, status: 1); } void getInProgressRequests({bool showLoader = true, required UsersTypes usersType}) { getRequestDetail(showLoader: showLoader, usersType: usersType, status: 2); } void getCompletedRequests({bool showLoader = true, required UsersTypes usersType}) { getRequestDetail(showLoader: showLoader, usersType: usersType, status: 3); } void getAcknowledgeRequests({bool showLoader = true, required UsersTypes usersType}) { getRequestDetail(showLoader: showLoader, usersType: usersType, status: 3); } void getClosedRequests({bool showLoader = true, required UsersTypes usersType}) { getRequestDetail(showLoader: showLoader, usersType: usersType, status: 4); } void getMultiSelectCategoryRequests({ bool showLoader = true, required UsersTypes usersType, required BuildContext context, bool? isAscending, }) { // Build filter arrays based on selected tabs List statusTransaction = []; List priority = []; List displayData = []; for (int index in listIndex) { if (index >= 0 && index < tabs.length) { CategoryTabs tab = tabs[index]; // High Priority if (tab.isHighPriority) { if (!priority.contains(1)) priority.add(1); } // Overdue if (tab.isOverDue) { if (!displayData.contains(1)) displayData.add(1); } // Status categories (Open, InProgress, Completed, Closed) if (!tab.isHighPriority && !tab.isOverDue && tab.requestType != RequestTypeEnum.unassigned) { // Map requestType to status value switch (tab.requestType) { case RequestTypeEnum.open: if (!statusTransaction.contains(1)) statusTransaction.add(1); break; case RequestTypeEnum.inProgress: if (!statusTransaction.contains(2)) statusTransaction.add(2); break; case RequestTypeEnum.completed: if (!statusTransaction.contains(4)) statusTransaction.add(4); break; case RequestTypeEnum.closed: if (!statusTransaction.contains(4)) statusTransaction.add(4); break; case RequestTypeEnum.canceled: if (!statusTransaction.contains(5)) statusTransaction.add(5); break; case RequestTypeEnum.pendingAcknowledgment: if (!statusTransaction.contains(3)) statusTransaction.add(3); break; case RequestTypeEnum.unassigned: case RequestTypeEnum.highPriority: case RequestTypeEnum.overdue: // These are handled separately above break; } } } } // Call the multi-filter API Provider.of(context, listen: false).getDashboardMultifilterRequests( context, pagination: false, statusTransaction: statusTransaction, priority: priority, displayData: displayData, isAscending: isAscending, ); } Future makeSwipe({required Swipe model}) async { isLoading = true; SwipeModel swipeResponse = SwipeModel(data: false, message: '', responseCode: 0, isSuccess: false); notifyListeners(); Response response; try { response = await ApiManager.instance.post(URLs.swipeUrl, body: model.toJson()); stateCode = response.statusCode; if (response.statusCode >= 200 && response.statusCode < 300) { swipeResponse = SwipeModel.fromJson(json.decode(response.body)); } isAllCountLoading = false; notifyListeners(); return swipeResponse; } catch (error) { isAllCountLoading = false; stateCode = -1; notifyListeners(); return swipeResponse; } } Future getSwipeLastTransaction({required String userId}) async { isLoading = true; notifyListeners(); Response response; var body = { "userId": userId, }; try { response = await ApiManager.instance.post(URLs.getSwipeLastTransactionUrl, body: body); stateCode = response.statusCode; if (response.statusCode >= 200 && response.statusCode < 300) {} isAllCountLoading = false; notifyListeners(); return response.statusCode; } catch (error) { isAllCountLoading = false; stateCode = -1; notifyListeners(); return -1; } } String getDashboardUrl({required UsersTypes usersType, int? status, int? tabId}) { switch (usersType) { case UsersTypes.qualityUser: return URLs.qaAuditorDetails; case UsersTypes.commissioningEngineer: return URLs.commissioningEngineerDetails; case UsersTypes.engineer: case UsersTypes.assessor: case UsersTypes.assessorTl: if (status == 0) { return URLs.engineerDashboardUpcoming; } else if (status == 1 && tabId == 1) { return URLs.engineerDashboardNotAssignDetails; } else { // status == 1 && tabId == 2 OR any other case return URLs.engineerDashboardDetailsUrl; } default: return URLs.nurseDashboardDetailsUrl; } } Future getRequestDetail( {bool showLoader = true, required UsersTypes usersType, int? status, bool isHighPriority = false, bool isOverdue = false, String? date, int? tabId, bool? isAscending}) async { if (showLoader) { isDetailLoading = showLoader; notifyListeners(); } Response response; String url = ''; // if (usersType == UsersTypes.qualityUser) { // url = URLs.qaAuditorDetails; // } else if (usersType == UsersTypes.engineer || usersType == UsersTypes.assessor || usersType == UsersTypes.assessorTl) { // //need to check pagination for not assigned task @waseem. // // //these checks are to call different apis for dashboard for engineer... // if (status == 0) { // url = URLs.engineerDashboardUpcoming; // } else if (status == 1 && tabId == 1) { // url = URLs.engineerDashboardNotAssignDetails; // } else if (status == 1 && tabId == 2) { // url = URLs.engineerDashboardDetailsUrl; // } else { // url = URLs.engineerDashboardDetailsUrl; // } // } else { // url = URLs.nurseDashboardDetailsUrl; // } url = getDashboardUrl(usersType: usersType, status: status, tabId: tabId); try { Map body = {"pageNumber": pageNum, "pageSize": pageItemNumber}; if (status != null && status == 0) { body["date"] = date ?? upcomingFilterSelectedDate.toIso8601String(); } else if (status == 1 && tabId == 1) { } else { body["statusValue"] = status; } if (isHighPriority) { body["isHighPriority"] = true; body["statusValue"] = null; } if (isOverdue) { body["isOverdue"] = true; body["statusValue"] = null; } if (isAscending != null) body["isAscending"] = isAscending; response = await ApiManager.instance.post(url, body: body); stateCode = response.statusCode; if (response.statusCode >= 200 && response.statusCode < 300) { if (_requestDetailList == null) { _requestDetailList = DD.DashboardDetail.fromJson(json.decode(response.body)); } else { _requestDetailList!.data!.addAll(DD.DashboardDetail.fromJson(json.decode(response.body)).data ?? []); } if (_requestDetailList!.data!.length >= pageItemNumber) { nextPage = true; } else { nextPage = false; } } else { requestDetailList = null; } if (showLoader) { isDetailLoading = false; } notifyListeners(); return response.statusCode; } catch (error) { if (showLoader) { isDetailLoading = false; } stateCode = -1; notifyListeners(); return -1; } } // Future getDashboardEngineerUpcoming({bool showLoader = true, required String date}) async { // if (showLoader) { // isDetailLoading = showLoader; // notifyListeners(); // } // // // Response response; // // try { // Map body = {"pageNumber": pageNum, "pageSize": pageItemNumber}; // response = await ApiManager.instance.post(URLs.engineerDashboardNotAssignDetails, body: body); // stateCode = response.statusCode; // if (response.statusCode >= 200 && response.statusCode < 300) { // if (_requestDetailList == null) { // _requestDetailList = DD.DashboardDetail.fromJson(json.decode(response.body)); // } else { // _requestDetailList!.data!.addAll(DD.DashboardDetail.fromJson(json.decode(response.body)).data ?? []); // } // if (_requestDetailList!.data!.length >= pageItemNumber) { // nextPage = true; // } else { // nextPage = false; // } // } else { // requestDetailList = null; // } // if (showLoader) { // isDetailLoading = false; // } // notifyListeners(); // return response.statusCode; // } catch (error) { // if (showLoader) { // isDetailLoading = false; // } // stateCode = -1; // notifyListeners(); // return -1; // } // } bool get isDetailLoading => _isDetailLoading; set isDetailLoading(bool value) { _isDetailLoading = value; notifyListeners(); } } class CategoryTabs { String label; int tag; int id; RequestTypeEnum requestType; String icon; Color iconColor; bool isHighPriority; bool isOverDue; CategoryTabs({this.isHighPriority = false, this.isOverDue = false, required this.label, required this.tag, required this.id, required this.requestType, required this.icon, required this.iconColor}); static List getTabs({required UsersTypes userType, required BuildContext context}) { List tabs = []; if (userType == UsersTypes.engineer) { // Order: 1-UnAssigned, 2-HighPriority, 3-Overdue, 4-Open, 5-InProgress, 6-Completed tabs.add(CategoryTabs(label: 'UnAssigned', tag: 1, id: 1, requestType: RequestTypeEnum.unassigned, icon: "dashboard/unassigned", iconColor: AppColor.unassignedStatus(context))); tabs.add(CategoryTabs(label: context.translation.highPriority, tag: 3, id: 4, requestType: RequestTypeEnum.highPriority, icon: "high_priority", iconColor: AppColor.red30, isHighPriority: true)); tabs.add(CategoryTabs(label: context.translation.overdue, tag: 3, id: 4, requestType: RequestTypeEnum.overdue, icon: "overdue", iconColor: AppColor.yellowIcon(context), isOverDue: true)); tabs.add(CategoryTabs(label: 'Open', tag: 1, id: 2, requestType: RequestTypeEnum.open, icon: "dashboard/open_icon", iconColor: AppColor.openColor)); tabs.add(CategoryTabs(label: 'In Progress', tag: 2, id: 3, requestType: RequestTypeEnum.inProgress, icon: "dashboard/inprogress_icon", iconColor: AppColor.primary10)); tabs.add(CategoryTabs(label: 'Completed', tag: 3, id: 4, requestType: RequestTypeEnum.completed, icon: "complete_request", iconColor: AppColor.completedColor)); return tabs; } if (userType == UsersTypes.qualityUser) { tabs.add(CategoryTabs(label: 'Open', tag: 1, id: 2, requestType: RequestTypeEnum.open, icon: "dashboard/open_icon", iconColor: AppColor.openColor)); tabs.add(CategoryTabs(label: 'In Progress', tag: 2, id: 3, requestType: RequestTypeEnum.inProgress, icon: "dashboard/inprogress_icon", iconColor: AppColor.primary10)); tabs.add(CategoryTabs(label: 'Closed', tag: 3, id: 4, requestType: RequestTypeEnum.closed, icon: "complete_request", iconColor: AppColor.completedColor)); return tabs; } if (userType == UsersTypes.commissioningEngineer) { tabs.add(CategoryTabs(label: 'Open', tag: 1, id: 2, requestType: RequestTypeEnum.open, icon: "dashboard/open_icon", iconColor: AppColor.openColor)); tabs.add(CategoryTabs(label: 'In Progress', tag: 2, id: 3, requestType: RequestTypeEnum.inProgress, icon: "dashboard/inprogress_icon", iconColor: AppColor.primary10)); tabs.add(CategoryTabs(label: 'Closed', tag: 3, id: 4, requestType: RequestTypeEnum.closed, icon: "complete_request", iconColor: AppColor.completedColor)); return tabs; } tabs.add(CategoryTabs(label: 'Open', tag: 1, id: 2, requestType: RequestTypeEnum.open, icon: "dashboard/open_icon", iconColor: AppColor.openColor)); tabs.add(CategoryTabs(label: 'In Progress', tag: 2, id: 3, requestType: RequestTypeEnum.inProgress, icon: "dashboard/inprogress_icon", iconColor: AppColor.primary10)); // tabs.add(CategoryTabs(label: 'Pending Acknowledgement', tag: 3, id: 1, requestType: RequestTypeEnum.pendingAcknowledgment, icon: "complete_request", iconColor: AppColor.overdueColor)); tabs.add(CategoryTabs(label: 'Acknowledgement', tag: 3, id: 1, requestType: RequestTypeEnum.pendingAcknowledgment, icon: "complete_request", iconColor: AppColor.overdueColor)); tabs.add(CategoryTabs(label: 'Canceled', tag: 6, id: 4, requestType: RequestTypeEnum.canceled, icon: "dashboard/unassigned", iconColor: AppColor.red30)); return tabs; } }