all changes implemented

design_3.0_latest
WaseemAbbasi22 12 months ago
parent 9072df77c3
commit 904f1919d4

@ -0,0 +1,6 @@
<svg width="20" height="20" viewBox="0 0 20 20" fill="none" xmlns="http://www.w3.org/2000/svg">
<path d="M10.6252 7.91663C10.6252 7.57145 10.3454 7.29163 10.0002 7.29163C9.65503 7.29163 9.3752 7.57145 9.3752 7.91663V11.25C9.3752 11.4157 9.44105 11.5747 9.55826 11.6919L11.2249 13.3586C11.469 13.6026 11.8647 13.6026 12.1088 13.3586C12.3529 13.1145 12.3529 12.7188 12.1088 12.4747L10.6252 10.9911V7.91663Z" fill="#54C166"/>
<path fill-rule="evenodd" clip-rule="evenodd" d="M10.6252 2.29163H11.6669C12.012 2.29163 12.2919 2.0118 12.2919 1.66663C12.2919 1.32145 12.012 1.04163 11.6669 1.04163H8.33354C7.98836 1.04163 7.70854 1.32145 7.70854 1.66663C7.70854 2.0118 7.98836 2.29163 8.33354 2.29163H9.3752V2.73197C5.17992 3.05111 1.8752 6.55627 1.8752 10.8333C1.8752 12.6389 2.46418 14.3069 3.4605 15.6558L2.05826 17.058C1.81418 17.3021 1.81418 17.6978 2.05826 17.9419C2.30234 18.186 2.69807 18.186 2.94215 17.9419L4.28029 16.6038C5.74858 18.0593 7.7694 18.9583 10.0002 18.9583C12.231 18.9583 14.2518 18.0593 15.7201 16.6038L17.0583 17.9419C17.3023 18.186 17.6981 18.186 17.9421 17.9419C18.1862 17.6978 18.1862 17.3021 17.9421 17.058L16.5399 15.6558C17.5362 14.3069 18.1252 12.6389 18.1252 10.8333C18.1252 6.55627 14.8205 3.05111 10.6252 2.73197V2.29163ZM3.1252 10.8333C3.1252 7.03633 6.20325 3.95829 10.0002 3.95829C13.7972 3.95829 16.8752 7.03633 16.8752 10.8333C16.8752 14.6303 13.7972 17.7083 10.0002 17.7083C6.20325 17.7083 3.1252 14.6303 3.1252 10.8333Z" fill="#54C166"/>
<path d="M2.75265 1.8914C3.19022 1.82103 3.59198 1.98844 3.95003 2.16747L4.44628 2.41559C4.75501 2.56996 4.88015 2.94538 4.72579 3.25412C4.57142 3.56285 4.196 3.68799 3.88726 3.53362L3.39101 3.2855C3.04468 3.11233 2.96194 3.1238 2.95111 3.12554C2.94076 3.12721 2.85798 3.14203 2.58346 3.41655C2.30894 3.69107 2.29412 3.77385 2.29246 3.7842C2.29071 3.79503 2.27924 3.87777 2.45241 4.2241L2.70054 4.72035C2.8549 5.02909 2.72976 5.40451 2.42103 5.55888C2.11229 5.71324 1.73687 5.5881 1.5825 5.27937L1.33438 4.78312C1.15535 4.42507 0.987945 4.02331 1.05831 3.58574C1.12876 3.14768 1.41409 2.81816 1.69958 2.53267C1.98507 2.24718 2.31459 1.96184 2.75265 1.8914Z" fill="#54C166"/>
<path d="M17.0491 3.12554C17.0383 3.1238 16.9555 3.11233 16.6092 3.2855L16.1129 3.53363C15.8042 3.68799 15.4288 3.56285 15.2744 3.25412C15.1201 2.94538 15.2452 2.56996 15.5539 2.41559L16.0502 2.16747C16.4082 1.98844 16.81 1.82103 17.2476 1.8914C17.6856 1.96184 18.0151 2.24718 18.3006 2.53267C18.5861 2.81816 18.8715 3.14768 18.9419 3.58574C19.0123 4.02331 18.8449 4.42507 18.6658 4.78312L18.4177 5.27937C18.2633 5.5881 17.8879 5.71324 17.5792 5.55888C17.2704 5.40451 17.1453 5.02909 17.2997 4.72035L17.5478 4.2241C17.721 3.87777 17.7095 3.79503 17.7078 3.7842C17.7061 3.77385 17.6913 3.69107 17.4167 3.41655C17.1422 3.14203 17.0594 3.12721 17.0491 3.12554Z" fill="#54C166"/>
</svg>

After

Width:  |  Height:  |  Size: 2.8 KiB

@ -43,6 +43,7 @@ class URLs {
static get engineerDashboardCountUrl=> '$_baseUrl/ServiceRequest/GetDashboardEngineerCount';
static get engineerDashboardDetailsUrl=> '$_baseUrl/ServiceRequest/GetDashboardEngineerDetails';
static get engineerDashboardNotAssignDetails=> '$_baseUrl/ServiceRequest/GetDashboardEngineerNotAssignDetails';
static get engineerDashboardUpcoming=> '$_baseUrl/ServiceRequest/GetDashboardEngineerUpcoming';
static get engineerAcceptUrl=> '$_baseUrl/ServiceRequest/EngineerAccept';
static get engineerAssignHimSelfUrl=> '$_baseUrl/ServiceRequest/AssignEngineerToHimself';
static get engineerRejectUrl=> '$_baseUrl/ServiceRequest/EngineerReject';
@ -53,6 +54,7 @@ class URLs {
static get reOrderActivity=> '$_baseUrl/ServiceRequest/ReOrderActivity';
static get engineerConfirmArriveUrl=> '$_baseUrl/ServiceRequest/EngineerConfirmArrive';
static get engineerUpdateWorkOrderUrl=> '$_baseUrl/ServiceRequest/EngineerUpdateWorkOrder';
static get engineerSetReminderUrl=> '$_baseUrl/ServiceRequest/EngineerSetReminder';
static get getWorkOrderByIdUrl=> '$_baseUrl/ServiceRequest/GetWorkOrderById';
static get getQrCodeUrl=> '$_baseUrl/ServiceRequest/GetQRCode';
static get deleteActivitySparePartUrl=> '$_baseUrl/ServiceRequest/DeleteActivitySparePart';
@ -123,6 +125,7 @@ class URLs {
static get getServiceReportRejectionReasons => "$_baseUrl/Lookups/GetLookup?lookupEnum=1303";
static get getServiceReportReasonsNew => "$_baseUrl/Lookups/GetLookupReasonNew?lookupEnum=505";
static get getServiceReportRetirementType => "$_baseUrl/Lookups/GetLookup?lookupEnum=415";
static get getVisitReminderTimeValue => "$_baseUrl/Lookups/GetLookup?lookupEnum=1211";
static get getServiceReportActivityStatus => "$_baseUrl/Lookups/GetLookup?lookupEnum=1302";
static get getServiceReportTypes => "$_baseUrl/Lookups/GetLookup?lookupEnum=501"; // get
static get getServiceReportTypesForWO => "$_baseUrl/Lookups/GetLookup?lookupEnum=34"; // get

@ -1,4 +1,5 @@
import 'dart:convert';
import 'dart:developer';
import 'package:flutter/widgets.dart';
import 'package:http/http.dart';
@ -51,7 +52,7 @@ class DashBoardProvider extends ChangeNotifier {
List<CategoryTabs> tabs = [];
void setTabs({required UsersTypes userType, required BuildContext context}) {
void setTabs({required UsersTypes userType, required BuildContext context}) {
tabs = CategoryTabs.getTabs(userType: userType, context: context);
}
@ -71,8 +72,9 @@ class DashBoardProvider extends ChangeNotifier {
_requestDetailList = null;
dashboardCount = null;
}
void refreshDashboard({required UsersTypes userType,required BuildContext context}) {
setTabs(userType:userType,context: context);
void refreshDashboard({required UsersTypes userType, required BuildContext context}) {
setTabs(userType: userType, context: context);
getDashBoardCount(usersType: userType);
resetRequestDataList();
getRequestDetail(usersType: userType, status: tabs[currentListIndex].tag);
@ -143,7 +145,11 @@ class DashBoardProvider extends ChangeNotifier {
}
void getHighPriorityRequests({bool showLoader = true, required UsersTypes usersType}) {
getRequestDetail(showLoader: showLoader, usersType: usersType, isHighPriority: true);
getRequestDetail(
showLoader: showLoader,
usersType: usersType,
isHighPriority: true,
);
}
void getOverdueRequests({bool showLoader = true, required UsersTypes usersType}) {
@ -170,19 +176,21 @@ class DashBoardProvider extends ChangeNotifier {
getRequestDetail(showLoader: showLoader, usersType: usersType, status: 4);
}
Future<int> getRequestDetail({bool showLoader = true, required UsersTypes usersType, int? status, bool isHighPriority = false, bool isOverdue = false}) async {
Future<int> getRequestDetail({bool showLoader = true, required UsersTypes usersType, int? status, bool isHighPriority = false, bool isOverdue = false, String? date}) async {
if (showLoader) {
isDetailLoading = showLoader;
notifyListeners();
}
Response response;
String url = '';
if (usersType == UsersTypes.engineer) {
if(status==0){
//these checks are to call different apis for dashboard for engineer...
if (status == 0) {
url = URLs.engineerDashboardUpcoming;
} else if (status == 1) {
url = URLs.engineerDashboardNotAssignDetails;
}else{
} else {
url = URLs.engineerDashboardDetailsUrl;
}
} else {
@ -190,52 +198,17 @@ class DashBoardProvider extends ChangeNotifier {
}
try {
Map<String, dynamic> body = {"pageNumber": pageNum, "pageSize": pageItemNumber};
if (status != null&&status!=0) body["statusValue"] = status;
if (status != null && status == 0) {
body["date"] = date ?? DateTime.now().toIso8601String();
} else {
body["statusValue"] = status;
}
if (isHighPriority) body["isHighPriority"] = true;
if (isOverdue) body["isOverdue"] = true;
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<int> getEngineerDashboardNotAssignedDetail({bool showLoader = true,}) async {
if (showLoader) {
isDetailLoading = showLoader;
notifyListeners();
}
Response response;
try {
Map<String, dynamic> 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));
@ -265,6 +238,48 @@ class DashBoardProvider extends ChangeNotifier {
}
}
// Future<int> getDashboardEngineerUpcoming({bool showLoader = true, required String date}) async {
// if (showLoader) {
// isDetailLoading = showLoader;
// notifyListeners();
// }
//
//
// Response response;
//
// try {
// Map<String, dynamic> 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) {

@ -70,7 +70,6 @@ class _DashboardViewState extends State<DashboardView> {
if (isFCM) {
FirebaseNotificationManger.initialized(context);
NotificationManger.initialisation((notificationDetails) {
print('i am called with notification details ${notificationDetails.toString()}');
FirebaseNotificationManger.handleMessage(context, json.decode(notificationDetails.payload!));
}, (id, title, body, payload) async {});

@ -23,29 +23,29 @@ class RequestCategoryFragment extends StatelessWidget {
bool isNurse = (Provider.of<UserProvider>(context, listen: false).user?.type) == UsersTypes.normal_user;
return Column(mainAxisSize: MainAxisSize.min, crossAxisAlignment: CrossAxisAlignment.start, children: <Widget>[
//TODO uncommit this to get the calendar card..
// !isNurse
// ? Column(
// children: [
// Row(
// mainAxisAlignment: MainAxisAlignment.spaceBetween,
// children: [
// context.translation.allWorkOrder.heading4(context),
// GestureDetector(
// onTap: () {
// dashboardProvider.isShowDashBoardCalendar = !dashboardProvider.isShowDashBoardCalendar;
// },
// child: dashboardProvider.isShowDashBoardCalendar ? AppAsset.listIcon.toSvgAsset() : AppAsset.calendarIcon.toSvgAsset())
// ],
// ),
// dashboardProvider.isShowDashBoardCalendar
// ? Padding(
// padding: EdgeInsets.only(top: 12.toScreenHeight),
// child: const WeeklyCalendarFragment(),
// )
// : const SizedBox(),
// ],
// ).paddingOnly(start: 16, end: 16)
// :
!isNurse&&dashboardProvider.tabs[dashboardProvider.currentListIndex].tag==0
? Column(
children: [
Row(
mainAxisAlignment: MainAxisAlignment.spaceBetween,
children: [
context.translation.allWorkOrder.heading4(context),
GestureDetector(
onTap: () {
dashboardProvider.isShowDashBoardCalendar = !dashboardProvider.isShowDashBoardCalendar;
},
child: dashboardProvider.isShowDashBoardCalendar ? AppAsset.listIcon.toSvgAsset() : AppAsset.calendarIcon.toSvgAsset())
],
),
dashboardProvider.isShowDashBoardCalendar
? Padding(
padding: EdgeInsets.only(top: 12.toScreenHeight),
child: const WeeklyCalendarFragment(),
)
: const SizedBox(),
],
).paddingOnly(start: 14, end: 12)
:
context.translation.allWorkOrder.heading4(context).paddingOnly(start: 16, end: 16),
getTabs(
requestsProvider: dashboardProvider,

@ -2,6 +2,7 @@
import 'package:flutter/material.dart';
import 'package:provider/provider.dart';
import 'package:test_sa/controllers/api_routes/api_manager.dart';
import 'package:test_sa/controllers/providers/settings/setting_provider.dart';
import 'package:test_sa/dashboard_latest/dashboard_provider.dart';
import 'package:test_sa/extensions/context_extension.dart';
import 'package:test_sa/extensions/int_extensions.dart';
@ -35,7 +36,7 @@ class RequestsFragment extends StatelessWidget {
context.isDark ? AppColor.redStatus(context) : AppColor.red30,
),
listItem(snapshot.dashboardCount?.data?.countOverdue ?? 0, "overdue", context.translation.overdue, context, snapshot.isAllCountLoading, 1, AppColor.yellowIcon(context)),
listItem(snapshot.dashboardCount?.data?.countOpen ?? 0, "new_request", ApiManager.instance.user?.type == UsersTypes.engineer ? context.translation.inProgress : context.translation.newR,
listItem(snapshot.dashboardCount?.data?.countInprogress ?? 0, "new_request", ApiManager.instance.user?.type == UsersTypes.engineer ? context.translation.inProgress : context.translation.newR,
context, snapshot.isAllCountLoading, 2, AppColor.primary10),
listItem(snapshot.dashboardCount?.data?.countComplete ?? 0, "complete_request", context.translation.completed, context, snapshot.isAllCountLoading, 3, AppColor.greenStatus(context)),
],
@ -47,8 +48,9 @@ class RequestsFragment extends StatelessWidget {
return GestureDetector(
onTap: isLoading
? null
: () {
: () async {
Navigator.push(context, MaterialPageRoute(builder: (context) => RequestsListPage(index, title)));
Provider.of<DashBoardProvider>(context, listen: false).refreshDashboard(userType: Provider.of<SettingProvider>(context, listen: false).user!.type!, context: context);
},
child: Column(
crossAxisAlignment: CrossAxisAlignment.center,

@ -33,6 +33,10 @@ extension EnumExtensionsWorkOrder on WorkOrderNextStepEnum {
case WorkOrderNextStepEnum.waitingForRequesterToConfirm:
//replace with correct value...
return 31;
case WorkOrderNextStepEnum.eFixRemotely:
return 35;
case WorkOrderNextStepEnum.eNeedVisit:
return 36;
}
}
}
@ -62,6 +66,10 @@ extension IntExtensionsWorkOrder on int {
return WorkOrderNextStepEnum.assetRetirementManagementApproval;
case 31:
return WorkOrderNextStepEnum.waitingForRequesterToConfirm;
case 35:
return WorkOrderNextStepEnum.eFixRemotely;
case 36:
return WorkOrderNextStepEnum.eNeedVisit;
default:
return WorkOrderNextStepEnum.onlyView;
}

@ -54,6 +54,7 @@ import 'package:test_sa/providers/service_request_providers/requested_through_pr
import 'package:test_sa/providers/service_request_providers/type_of_request_provider.dart';
import 'package:test_sa/providers/work_order/activity_status_provider.dart';
import 'package:test_sa/providers/work_order/fault_description_provider.dart';
import 'package:test_sa/providers/work_order/need_visit_reminder_time_provider.dart';
import 'package:test_sa/providers/work_order/reason_provider.dart';
import 'package:test_sa/providers/work_order/retirement_type_provider.dart';
import 'package:test_sa/providers/work_order/service_type_provider.dart';
@ -79,6 +80,7 @@ import 'package:test_sa/views/pages/user/requests/work_order/work_orders_list_pa
import 'package:test_sa/views/widgets/departments/single_department_picker.dart';
import 'package:test_sa/views/widgets/equipment/asset_detail_page.dart';
import 'package:test_sa/views/widgets/equipment/single_device_picker.dart';
import 'controllers/notification/notification_manger.dart';
import 'controllers/providers/api/gas_refill_comments.dart';
import 'controllers/providers/api/user_provider.dart';
import 'controllers/providers/settings/setting_provider.dart';
@ -93,9 +95,9 @@ import 'package:timezone/timezone.dart' as tz;
void main() async {
WidgetsFlutterBinding.ensureInitialized();
// _configureLocalTimeZone();
// NotificationManger.initialisation((notificationDetails) {
// }, (id, title, body, payload) async {});
_configureLocalTimeZone();
NotificationManger.initialisation((notificationDetails) {
}, (id, title, body, payload) async {});
if (Platform.isIOS) {
await Firebase.initializeApp(
@ -232,6 +234,7 @@ class MyApp extends StatelessWidget {
ChangeNotifierProvider(create: (_) => FaultDescriptionProvider()),
ChangeNotifierProvider(create: (_) => RetirementTypeProvider()),
ChangeNotifierProvider(create: (_) => ActivityStatusProvider()),
ChangeNotifierProvider(create: (_) => NeedVisitReminderTimeProvider()),
///todo deleted
//ChangeNotifierProvider(create: (_) => AssetTypesProvider()),

@ -4,6 +4,8 @@ enum WorkOrderNextStepEnum {
nTakeAction, // 5
eRejectAccept, // 9
eFixRemotelyNeedVisit, // 12
eFixRemotely, // 35
eNeedVisit, // 36
eArrived, // 15
verifyAssetDetail, // 16
activity, // 17

@ -4,6 +4,7 @@ import 'package:test_sa/models/new_models/assistant_employee.dart';
import 'package:test_sa/models/new_models/work_order_detail_model.dart';
import 'package:test_sa/models/service_request/supp_engineer_work_orders.dart';
import 'package:test_sa/models/service_request/supplier_details.dart';
import 'package:test_sa/models/timer_model.dart';
class ActivityMaintenanceHelperModel {
int? id;
@ -32,6 +33,8 @@ class ActivityMaintenanceHelperModel {
SuppEngineerWorkOrders? supEngineer;
ActivityMaintenanceAssistantEmployees? modelAssistantEmployees;
List<AssistantEmployees>? assistantEmployees;
List<ActivityMaintenanceTimers>? activityMaintenanceTimers=[];
TimerModel? activityMaintenanceTimerModel = TimerModel();
ActivityMaintenanceHelperModel(
{this.id,
@ -43,6 +46,7 @@ class ActivityMaintenanceHelperModel {
this.supplier,
this.endTime,
this.workingHour,
this.activityMaintenanceTimerModel,
this.travelHours,
this.repairLocation,
this.assignedEmployeeId,
@ -55,6 +59,7 @@ class ActivityMaintenanceHelperModel {
this.assistantEmployees,
this.supEngineer,
this.assignedEmployee,
this.activityMaintenanceTimers,
this.modelAssistantEmployees});
@ -76,10 +81,8 @@ class ActivityMaintenanceHelperModel {
data['supplierStartTime'] = supplierStartTime?.toIso8601String();
data['supplierEndTime'] = supplierEndTime?.toIso8601String();
data['supplierWorkingHour'] = supplierWorkingHour;
// //TODO remove this when backend fix this on their side..
// if(activityStatus!=null){
// data['lastSituationId'] = activityStatus?.id;
// }
//TODO fix this properly...
data['activityMaintenanceTimers'] = activityMaintenanceTimers;
if (assistantEmployees != null&&assistantEmployees!.isNotEmpty) {
data['assistantEmployees'] = [modelAssistantEmployees?.toJson()];
}

@ -61,6 +61,7 @@ class WorkOrderData {
required this.assignedEmployee,
required this.lastActivityStatus,
required this.status,
required this.setReminder,
required this.nextStep,
required this.assetVerificationType,
required this.workOrderContactPerson,
@ -106,6 +107,7 @@ class WorkOrderData {
WorkOrderAssignedEmployee? assignedEmployee;
Lookup? lastActivityStatus;
Lookup? status;
Lookup? setReminder;
Lookup? nextStep;
int? assetVerificationType;
List<WorkOrderContactPerson> workOrderContactPerson;
@ -150,8 +152,9 @@ class WorkOrderData {
room: json["room"],
assetType: json["assetType"] == null ? null : Lookup.fromJson(json["assetType"]),
assignedEmployee: json["assignedEmployee"] == null ? null : WorkOrderAssignedEmployee.fromJson(json["assignedEmployee"]),
lastActivityStatus: json["lastActivityStatus"]!=null?Lookup.fromJson(json["lastActivityStatus"]):null,
lastActivityStatus: json["lastActivityStatus"] != null ? Lookup.fromJson(json["lastActivityStatus"]) : null,
status: json["status"] == null ? null : Lookup.fromJson(json["status"]),
setReminder: json["setReminder"] == null ? null : Lookup.fromJson(json["setReminder"]),
nextStep: json["nextStep"] == null ? null : Lookup.fromJson(json["nextStep"]),
assetVerificationType: json["assetVerificationType"],
workOrderContactPerson: json["workOrderContactPerson"] == null ? [] : List<WorkOrderContactPerson>.from(json["workOrderContactPerson"]!.map((x) => WorkOrderContactPerson.fromJson(x))),
@ -174,7 +177,7 @@ class WorkOrderData {
totalWorkingHours: json["totalWorkingHours"],
workOrderHistory: json["workOrderHistory"] == null ? [] : List<WorkOrderHistory>.from(json["workOrderHistory"]!.map((x) => WorkOrderHistory.fromJson(x))),
activities: json["activities"] == null ? [] : List<Activities>.from(json["activities"]!.map((x) => Activities.fromJson(x))),
needAVisitDateTime: DateTime.tryParse(json["requestedDate"] ?? ""),
needAVisitDateTime: DateTime.tryParse(json["needAVisitDateTime"] ?? ""),
needAVisitComment: json["needAVisitComment"],
activityAssetToBeRetireds: json["activityAssetToBeRetireds"] == null ? [] : List<dynamic>.from(json["activityAssetToBeRetireds"]!.map((x) => x)),
);
@ -200,6 +203,7 @@ class WorkOrderData {
"assignedEmployee": assignedEmployee?.toJson(),
"lastActivityStatus": lastActivityStatus,
"status": status?.toJson(),
"setReminder": setReminder?.toJson(),
"nextStep": nextStep?.toJson(),
"assetVerificationType": assetVerificationType,
"workOrderContactPerson": workOrderContactPerson.map((x) => x?.toJson()).toList(),
@ -298,6 +302,7 @@ class WorkOrderAssignedEmployee {
"languageId": languageId,
};
}
class AssetLoan {
AssetLoan({
required this.id,
@ -336,8 +341,6 @@ class AssetLoan {
};
}
class Activities {
int? id;
int? orderNo;
@ -535,8 +538,8 @@ class WorkOrderHistory {
WorkOrderHistory({
required this.id,
required this.workorderStatus,
this.assetVerificationType,
this.photoVerfication,
this.assetVerificationType,
this.photoVerfication,
required this.activityStatus,
required this.date,
required this.timeDifference,
@ -554,7 +557,7 @@ class WorkOrderHistory {
Lookup? assetVerificationType;
dynamic activityStatus;
DateTime? date;
String timeDifference ='';
String timeDifference = '';
String? photoVerfication;
WorkOrderAssignedEmployee? user;
Lookup? step;
@ -617,6 +620,7 @@ class ActivityMaintenance {
String? supplierEndTime;
double? supplierWorkingHours;
List<ActivityMaintenanceAssistantEmployees>? assistantEmployees;
List<ActivityMaintenanceTimers>? activityMaintenanceTimers;
ActivityMaintenance(
{this.id,
@ -628,6 +632,7 @@ class ActivityMaintenance {
this.travelHours,
this.repairLocation,
this.assignedEmployee,
this.activityMaintenanceTimers,
this.technicalComment,
this.supplier,
this.supplierEngineer,
@ -647,7 +652,6 @@ class ActivityMaintenance {
repairLocation = json['repairLocation'] != null ? Lookup.fromJson(json['repairLocation']) : null;
assignedEmployee = json['assignedEmployee'] != null ? AssignedEmployee.fromJson(json['assignedEmployee']) : null;
technicalComment = json['technicalComment'];
//json["supplier"] == null ? null : Lookup.fromJson(json["supplier"]),
supplier = json["supplier"] == null ? null : Lookup.fromJson(json["supplier"]);
supplierEngineer = json["supplierEngineer"] == null ? null : Lookup.fromJson(json["supplierEngineer"]);
@ -661,6 +665,12 @@ class ActivityMaintenance {
assistantEmployees!.add(ActivityMaintenanceAssistantEmployees.fromJson(v));
});
}
if (json['activityMaintenanceTimers'] != null) {
activityMaintenanceTimers = <ActivityMaintenanceTimers>[];
json['activityMaintenanceTimers'].forEach((v) {
activityMaintenanceTimers!.add(ActivityMaintenanceTimers.fromJson(v));
});
}
}
Map<String, dynamic> toJson() {
@ -766,3 +776,28 @@ class ActivityMaintenanceAssistantEmployees {
return data;
}
}
class ActivityMaintenanceTimers {
int? id;
String? startTime;
String? endTime;
dynamic workingHours;
ActivityMaintenanceTimers({this.id, this.startTime, this.endTime, this.workingHours});
ActivityMaintenanceTimers.fromJson(Map<String, dynamic> json) {
id = json['id'];
startTime = json['startTime'];
endTime = json['endTime'];
workingHours = json['workingHours'];
}
Map<String, dynamic> toJson() {
final Map<String, dynamic> data = <String, dynamic>{};
data['id'] = id;
data['startTime'] = startTime;
data['endTime'] = endTime;
data['workingHours'] = workingHours;
return data;
}
}

@ -17,6 +17,7 @@ class RequestPaginatedListview extends StatelessWidget {
@override
Widget build(BuildContext context) {
print('count i got is ${totalCount}');
return ListView.builder(
itemCount: list.length < totalCount ? list.length + 1 : list.length,
controller: scrollController,

@ -1,3 +1,5 @@
import 'dart:async';
import 'package:flutter/material.dart';
import 'package:provider/provider.dart';
import 'package:test_sa/controllers/providers/api/user_provider.dart';
@ -31,8 +33,11 @@ class _RequestsListPageState extends State<RequestsListPage> {
void initState() {
super.initState();
_dashBoardProvider = Provider.of<DashBoardProvider>(context, listen: false);
_dashBoardProvider.resetRequestDataList();
callRequestApis();
scheduleMicrotask(() async {
_dashBoardProvider.resetRequestDataList();
callRequestApis();
});
handleScroll();
}
@ -46,8 +51,11 @@ class _RequestsListPageState extends State<RequestsListPage> {
_scrollController = ScrollController();
int pageNo = 1;
_scrollController.addListener(() async {
if (_scrollController.position.pixels == _scrollController.position.maxScrollExtent && !_dashBoardProvider.isDetailLoading) {
if (_scrollController.position.pixels == _scrollController.position.maxScrollExtent &&
!_dashBoardProvider.isDetailLoading &&
(_dashBoardProvider.requestDetailList!.data!.length < _dashBoardProvider.requestDetailList!.totalRows!.toInt())) {
pageNo = pageNo + 1;
_dashBoardProvider.pageNum = pageNo;
callRequestApis(showLoader: false, pageNo: pageNo);
}
});
@ -95,10 +103,11 @@ class _RequestsListPageState extends State<RequestsListPage> {
}));
}
Future<void> callRequestApis({bool showLoader = true, int pageNo = 1, int pageSize = 12}) async {
Future<void> callRequestApis({bool showLoader = true, int pageNo = 1, int pageSize = 10}) async {
UsersTypes usersTypes = Provider.of<UserProvider>(context, listen: false).user!.type!;
if (widget.index == 0) {
// high priority
_dashBoardProvider.getHighPriorityRequests(usersType: usersTypes, showLoader: showLoader);
} else if (widget.index == 1) {
// overdue

@ -26,8 +26,6 @@ class FaultDescriptionProvider extends ChangeNotifier {
try {
response = await ApiManager.instance.get(URLs.getFaultDescription+"?assetId=$assetId",);
print('url is ${URLs.getFaultDescription+"?assetId=$assetId"}');
print('response of get fault is ${response.body}');
List<FaultDescription> list = [];
if (response.statusCode >= 200 && response.statusCode < 300) {
// client's request was successfully received

@ -0,0 +1,35 @@
import 'dart:convert';
import 'package:http/http.dart';
import 'package:test_sa/providers/loading_list_notifier.dart';
import '../../controllers/api_routes/api_manager.dart';
import '../../controllers/api_routes/urls.dart';
import '../../models/lookup.dart';
class NeedVisitReminderTimeProvider extends LoadingListNotifier<Lookup> {
@override
Future getDate() async {
if (loading == true) return -2;
loading = true;
notifyListeners();
try {
Response response = await ApiManager.instance.get(URLs.getVisitReminderTimeValue);
print('response i got is ${response.body}');
stateCode = response.statusCode;
if (response.statusCode >= 200 && response.statusCode < 300) {
// client's request was successfully received
List categoriesListJson = json.decode(response.body)["data"];
items = categoriesListJson.map((item) => Lookup.fromJson(item)).toList();
}
loading = false;
notifyListeners();
return response.statusCode;
} catch (error) {
loading = false;
stateCode = -1;
notifyListeners();
return -1;
}
}
}

@ -123,6 +123,7 @@ class ServiceRequestDetailProvider extends ChangeNotifier {
void updateNeedVisitHelperModel(NeedVisitHelperModel? value) {
needVisitHelperModel = value;
log ("value:${value!.visitDate.toString()}");
notifyListeners();
}
@ -380,6 +381,7 @@ class ServiceRequestDetailProvider extends ChangeNotifier {
stateCode = response.statusCode;
if (response.statusCode >= 200 && response.statusCode < 300) {
currentWorkOrder = WorkOrderDetail.fromJson(json.decode(response.body));
notifyListeners();
}
isLoading = false;
notifyListeners();
@ -469,6 +471,33 @@ class ServiceRequestDetailProvider extends ChangeNotifier {
}
}
//engineer Confirm Arrive......
Future<int> engineerSetReminder({required int workOrderId, required int reminderId}) async {
Response response;
try {
//"workOrderCreatedById": "string"
Map<String, dynamic> body = {
"workOrderId": workOrderId,
"setReminderId": reminderId,
};
isLoading = true;
notifyListeners();
response = await ApiManager.instance.post(URLs.engineerSetReminderUrl, body: body);
stateCode = response.statusCode;
if (response.statusCode >= 200 && response.statusCode < 300) {
currentWorkOrder = WorkOrderDetail.fromJson(json.decode(response.body));
}
if (response.statusCode >= 200 && response.statusCode < 300) {}
isLoading = false;
notifyListeners();
return response.statusCode;
} catch (e) {
log("engineer accept [error] : $e");
isLoading = false;
notifyListeners();
return -1;
}
}
//assignEngineerToWorkOrder......
Future<CommonResponseModel> assignEngineerWorkOrder({required String workOrderId, required String engineerId}) async {
try {
@ -739,7 +768,6 @@ class ServiceRequestDetailProvider extends ChangeNotifier {
body: activityMaintenanceHelperModel!.toJson(),
);
stateCode = response.statusCode;
print('response of activity maintenace part is ${response.body}');
if (response.statusCode >= 200 && response.statusCode < 300) {
// currentWorkOrder = WorkOrderDetail.fromJson(json.decode(response.body));
// updateCurrentWorkOrder(currentWorkOrder);

@ -16,6 +16,7 @@ import 'package:test_sa/extensions/widget_extensions.dart';
import 'package:test_sa/new_views/common_widgets/app_lazy_loading.dart';
import 'package:test_sa/service_request_latest/service_request_detail_provider.dart';
import 'package:huawei_push/huawei_push.dart' as h_push;
class ServiceRequestUtils {
static double calculateAndAssignWorkingHours({
required DateTime? startTime,
@ -33,6 +34,7 @@ class ServiceRequestUtils {
return -1; // Indicating invalid input
}
}
static String calculateTimeDifference(DateTime startDate, DateTime endDate) {
try {
Duration diff = startDate.difference(endDate);
@ -52,9 +54,31 @@ class ServiceRequestUtils {
}
}
static void getQrCode({required BuildContext context }) async{
static String formatTimerDuration(int seconds) {
int hours = seconds ~/ 3600;
int minutes = (seconds % 3600) ~/ 60;
int remainingSeconds = seconds % 60;
String formattedDuration = '';
if (hours > 0) {
formattedDuration += '$hours hour${hours > 1 ? 's' : ''} ';
}
if (minutes > 0) {
formattedDuration += '$minutes minute${minutes > 1 ? 's' : ''} ';
}
if (remainingSeconds > 0) {
formattedDuration += '$remainingSeconds second${remainingSeconds > 1 ? 's' : ''} ';
}
if (formattedDuration.isEmpty) {
formattedDuration = 'Less than a second';
}
return formattedDuration.trim();
}
static void getQrCode({required BuildContext context}) async {
showDialog(context: context, barrierDismissible: false, builder: (context) => const AppLazyLoading());
ServiceRequestDetailProvider requestDetailProvider = Provider.of<ServiceRequestDetailProvider>(context,listen:false);
ServiceRequestDetailProvider requestDetailProvider = Provider.of<ServiceRequestDetailProvider>(context, listen: false);
String? base64String = await requestDetailProvider.getQrCode(workOrderId: requestDetailProvider.currentWorkOrder!.data!.requestId ?? 0);
Navigator.pop(context);
if (base64String != null) {
@ -66,7 +90,7 @@ class ServiceRequestUtils {
builder: (BuildContext context) {
return AlertDialog(
backgroundColor: Colors.white,
title:context.translation.scanQr.heading6(context).center,
title: context.translation.scanQr.heading6(context).center,
content: Image.memory(
bytes, // Displaying the QR code from base64
fit: BoxFit.contain, // Ensure the image fits well in the dialog
@ -74,61 +98,41 @@ class ServiceRequestUtils {
return const Icon(Icons.error, color: Colors.red);
},
),
);
},
);
} else {
print('Failed to get the QR code');
}
}
static Widget testScheduleNotificationButton({required BuildContext context}){
return ElevatedButton(
child: const Text('Schedule notifications'),
onPressed: () {
// debugPrint('Notification Scheduled for $D');
// NotificationManger.showNotification(context: context, title: 'test notification', subtext: 'test notification', hashcode: 1);
DateTime scheduleTime= DateTime.now().add(const Duration(seconds: 10));
NotificationManger.scheduleNotification(
title: 'Scheduled Notification',
body: '$scheduleTime',
scheduledNotificationDateTime: scheduleTime);();
},
);
static void scheduleNotification({required BuildContext context, required DateTime scheduleDateTime}) {
DateTime scheduleTime = scheduleDateTime;
NotificationManger.scheduleNotification(title: 'Scheduled Notification', body: '$scheduleTime', scheduledNotificationDateTime: scheduleTime);
}
//steps:
//add permission for andriod..
//add string in info.plist for ios...
//create event..
static Widget testAddEventToCalendarButton({required BuildContext context}){
return ElevatedButton(
child: const Text('Add Event to Calendar'),
onPressed: () async {
var currentLocation = getLocation( await FlutterTimezone.getLocalTimezone());
setLocalLocation(currentLocation);
await Future.delayed(const Duration(seconds: 2));
var eventToCreate = Event(
"1",
title: "test123",
description: "test",
start: TZDateTime.now(currentLocation),
end: TZDateTime.now(currentLocation).add(const Duration(seconds: 10)),
);
final createEventResult =
await DeviceCalendarPlugin().createOrUpdateEvent(eventToCreate);
if (createEventResult!.isSuccess) {
Fluttertoast.showToast(msg: 'added successfully');
}
},
static void addEventToCalendar({required BuildContext context, required DateTime start, required DateTime end,required String title}) async {
var currentLocation = getLocation(await FlutterTimezone.getLocalTimezone());
setLocalLocation(currentLocation);
await Future.delayed(const Duration(seconds: 2));
TZDateTime startDate = TZDateTime.from(start, currentLocation);
TZDateTime endDate = TZDateTime.from(end, currentLocation);
var eventToCreate = Event(
"1",
title: title,
description: "You have reminder for Visit",
start: startDate,
end: endDate,
);
print('title i got is ${eventToCreate.title}');
await DeviceCalendarPlugin().createOrUpdateEvent(eventToCreate);
}
// Map<String, dynamic> messageData = message.data;
// if (messageData["notificationType"] != null && messageData["accept"] != null) {
// if (messageData["notificationType"] == "arrivalConfirmation") {
@ -141,7 +145,6 @@ class ServiceRequestUtils {
// }
// }
static Future<bool?> listenForApproval() async {
print('listen for approval called..');
bool isVerified = false;
@ -198,6 +201,7 @@ class ServiceRequestUtils {
return false;
}
}
class ConfirmArrivalNotificationModel {
final String? transactionType;
final String? requestId;
@ -234,4 +238,4 @@ class ConfirmArrivalNotificationModel {
'accept': accept,
};
}
}
}

@ -201,6 +201,29 @@ class FooterActionButton {
textColor: AppColor.neutral150,
fontSize: 12.toScreenWidth,
));
case WorkOrderNextStepEnum.eFixRemotely:
return footerContainer(
child: AppFilledButton(
label: context.translation.fixedRemotely,
maxWidth: true,
buttonColor: AppColor.green70,
onPressed: () async {
requestDetailProvider.fixRemotelyHelperModel = FixRemotelyHelperModel();
ServiceRequestBottomSheet.fixRemotelyBottomSheet(context: context);
},
),
);
case WorkOrderNextStepEnum.eNeedVisit:
return footerContainer(
child: AppFilledButton(
label: context.translation.needAVisit,
maxWidth: true,
buttonColor: AppColor.neutral50,
onPressed: () async {
requestDetailProvider.needVisitHelperModel = NeedVisitHelperModel();
ServiceRequestBottomSheet.initialVisitBottomSheet(context: context);
},
));
}
} else {
if (workOrderNextStepStatus == WorkOrderNextStepEnum.nTakeAction) {

@ -20,6 +20,7 @@ import 'package:test_sa/new_views/common_widgets/app_filled_button.dart';
import 'package:test_sa/new_views/common_widgets/app_lazy_loading.dart';
import 'package:test_sa/new_views/common_widgets/default_app_bar.dart';
import 'package:test_sa/service_request_latest/service_request_detail_provider.dart';
import 'package:test_sa/service_request_latest/utilities/service_request_utils.dart';
import 'package:test_sa/service_request_latest/views/components/action_button/footer_action_button.dart';
import 'package:test_sa/service_request_latest/views/components/bottom_sheets/service_request_bottomsheet.dart';
import 'package:test_sa/service_request_latest/views/forms/maintenance_request/maintenance_request_main.dart';
@ -248,7 +249,9 @@ class _ActivitiesListViewState extends State<ActivitiesListView> {
}
Widget maintenanceActivityCard({required ServiceRequestDetailProvider requestDetailProvider, required UserProvider userProvider, required BuildContext context, required Activities activity}) {
print('activity i got is ${activity.toJson()}');
double totalWorkingHours =
activity.activityMaintenance?.activityMaintenanceTimers?.fold(0.0, (sum, item) => (sum ?? 0) + DateTime.parse(item.endTime!).difference(DateTime.parse(item.startTime!)).inSeconds) ?? 0;
return Column(
mainAxisSize: MainAxisSize.min,
crossAxisAlignment: CrossAxisAlignment.start,
@ -296,16 +299,16 @@ class _ActivitiesListViewState extends State<ActivitiesListView> {
),
3.height,
Text(
'${context.translation.workingHours}: ${activity.activityMaintenance?.workingHours??'-'}',
'${context.translation.workingHours}: ${totalWorkingHours > 0.0 ? ServiceRequestUtils.formatTimerDuration(totalWorkingHours.round()) : '-'}',
style: AppTextStyles.bodyText2.copyWith(color: AppColor.neutral120),
),
2.height,
if(activity.activityMaintenance?.assignedEmployee!=null&&activity.activityMaintenance!.assistantEmployees!.isNotEmpty)...[
if (activity.activityMaintenance?.assignedEmployee != null && activity.activityMaintenance!.assistantEmployees!.isNotEmpty) ...[
Text(
'${context.translation.assistantEmployee}: ${activity.activityMaintenance?.assistantEmployees?.first.user?.userName}',
style: AppTextStyles.bodyText2.copyWith(color: AppColor.neutral120),
),
]else...[
] else ...[
Text(
'${context.translation.assignedEmployee}: ${activity.activityMaintenance?.assignedEmployee?.userName}',
style: AppTextStyles.bodyText2.copyWith(color: AppColor.neutral120),
@ -359,6 +362,7 @@ class _ActivitiesListViewState extends State<ActivitiesListView> {
supplierStartTime: activity.activityMaintenance?.supplierStartTime != null ? DateTime.parse(activity.activityMaintenance!.supplierStartTime!) : null,
supplierEndTime: activity.activityMaintenance?.supplierEndTime != null ? DateTime.parse(activity.activityMaintenance!.supplierEndTime!) : null,
supplierWorkingHour: activity.activityMaintenance?.supplierWorkingHours,
activityMaintenanceTimers: activity.activityMaintenance?.activityMaintenanceTimers ?? [],
supplier: activity.activityMaintenance?.supplier != null
? SupplierDetails(
id: activity.activityMaintenance?.supplier?.id,

@ -1,4 +1,5 @@
import 'dart:convert';
import 'dart:developer';
import 'package:flutter/material.dart';
import 'package:flutter/services.dart';
@ -17,6 +18,7 @@ import 'package:test_sa/models/lookup.dart';
import 'package:test_sa/new_views/common_widgets/app_lazy_loading.dart';
import 'package:test_sa/new_views/common_widgets/single_item_drop_down_menu.dart';
import 'package:test_sa/providers/service_request_providers/reject_reason_provider.dart';
import 'package:test_sa/providers/work_order/need_visit_reminder_time_provider.dart';
import 'package:test_sa/service_request_latest/service_request_detail_provider.dart';
import 'package:test_sa/service_request_latest/utilities/service_request_utils.dart';
import 'package:test_sa/service_request_latest/views/forms/maintenance_request/maintenance_request_main.dart';
@ -31,12 +33,12 @@ import '../../../../new_views/common_widgets/app_filled_button.dart';
import '../../../../new_views/common_widgets/app_text_form_field.dart';
class ServiceRequestBottomSheet {
static buildBottomSheetParent({required BuildContext context, required Widget childWidget,bool ?isDismissible}) {
static buildBottomSheetParent({required BuildContext context, required Widget childWidget, bool? isDismissible}) {
return showModalBottomSheet(
context: context,
useSafeArea: true,
isScrollControlled: true,
isDismissible:isDismissible??true,
isDismissible: isDismissible ?? true,
backgroundColor: Colors.transparent,
builder: (context) => SingleChildScrollView(
child: childWidget,
@ -202,14 +204,14 @@ class ServiceRequestBottomSheet {
buttonColor: AppColor.green70,
loading: false,
onPressed: () async {
if(requestDetailProvider.fixRemotelyHelperModel?.startDate==null&&requestDetailProvider.fixRemotelyHelperModel?.endDate==null){
if (requestDetailProvider.fixRemotelyHelperModel?.startDate == null && requestDetailProvider.fixRemotelyHelperModel?.endDate == null) {
"Please Select start and end date".showToast;
return;
}
requestDetailProvider.fixRemotelyHelperModel?.workOrderId = requestDetailProvider.currentWorkOrder?.data?.requestId;
requestDetailProvider.engineerFixRemotely();
Navigator.pop(context);
const SizedBox().flushBar(context: context, title: '', message: context.translation.youMarkedThisIssueAsFixedWaitingForTheRequesterToConfirm);
const SizedBox().flushBar(context: context, title: '', message: context.translation.youMarkedThisIssueAsFixedWaitingForTheRequesterToConfirm);
},
),
),
@ -246,25 +248,24 @@ class ServiceRequestBottomSheet {
date: requestDetailProvider.needVisitHelperModel?.visitDate,
formatDateWithTime: true,
onDatePicker: (selectedDate) {
if (selectedDate != null) {
showTimePicker(
context: context,
initialTime: TimeOfDay.now(),
).then((selectedTime) {
// Handle the selected date and time here.
if (selectedTime != null) {
DateTime selectedDateTime = DateTime(
selectedDate.year,
selectedDate.month,
selectedDate.day,
selectedTime.hour,
selectedTime.minute,
);
requestDetailProvider.needVisitHelperModel?.visitDate = selectedDateTime;
requestDetailProvider.updateNeedVisitHelperModel(requestDetailProvider.needVisitHelperModel);
}
});
}
showTimePicker(
context: context,
initialTime: TimeOfDay.now(),
).then((selectedTime) {
// Handle the selected date and time here.
if (selectedTime != null) {
DateTime selectedDateTime = DateTime(
selectedDate.year,
selectedDate.month,
selectedDate.day,
selectedTime.hour,
selectedTime.minute,
);
requestDetailProvider.needVisitHelperModel?.visitDate = selectedDateTime;
requestDetailProvider.updateNeedVisitHelperModel(requestDetailProvider.needVisitHelperModel);
print('selected date time i got is ${requestDetailProvider.needVisitHelperModel?.visitDate}');
}
});
},
),
8.height,
@ -290,24 +291,30 @@ class ServiceRequestBottomSheet {
buttonColor: AppColor.primary10,
loading: false,
onPressed: () async {
if(requestDetailProvider.needVisitHelperModel?.visitDate==null){
if (requestDetailProvider.needVisitHelperModel?.visitDate == null) {
"Please select visit date".showToast;
return;
}
if (requestDetailProvider.currentWorkOrder?.data?.nextStep!.workOrderNextStepEnum == WorkOrderNextStepEnum.eArrived) {
requestDetailProvider.updateNeedVisitHelperModel(NeedVisitHelperModel(
workOrderId: requestDetailProvider.needVisitHelperModel?.workOrderId,
visitDate: requestDetailProvider.needVisitHelperModel?.visitDate,
comment: requestDetailProvider.needVisitHelperModel?.comment,
));
requestDetailProvider.needVisitHelperModel?.workOrderId = requestDetailProvider.currentWorkOrder!.data!.requestId;
// requestDetailProvider.updateNeedVisitHelperModel(NeedVisitHelperModel(
// workOrderId: requestDetailProvider.needVisitHelperModel?.workOrderId,
// visitDate: requestDetailProvider.needVisitHelperModel?.visitDate,
// comment: requestDetailProvider.needVisitHelperModel?.comment,
// ));
print('visit date i got is ${requestDetailProvider.needVisitHelperModel?.visitDate}');
requestDetailProvider.engineerUpdateNeedVisit();
// await requestDetailProvider.getWorkOrderById(id: requestDetailProvider.needVisitHelperModel!.workOrderId!);
} else {
requestDetailProvider.needVisitHelperModel?.workOrderId = requestDetailProvider.currentWorkOrder!.data!.requestId;
requestDetailProvider.engineerNeedVisit();
requestDetailProvider.needVisitHelperModel = NeedVisitHelperModel();
getReminderTimeList(context: context);
initialVisitReminderBottomSheet(context: context);
}
Navigator.pop(context);
// initialVisitReminderBottomSheet(context: context);
Navigator.pop(context);
//
},
),
@ -317,49 +324,60 @@ class ServiceRequestBottomSheet {
}));
}
static Future initialVisitReminderBottomSheet({required BuildContext context}) {
String selectedReminderTime = '10 minutes before';
static Future<void> getReminderTimeList({required BuildContext context}) async {
NeedVisitReminderTimeProvider timeProvider = Provider.of<NeedVisitReminderTimeProvider>(context, listen: false);
timeProvider.reset();
WidgetsBinding.instance.addPostFrameCallback((_) {
timeProvider.getDate();
});
}
static Future initialVisitReminderBottomSheet({required BuildContext context, Lookup? reminder}) {
Lookup selectedReminderTime = reminder ?? Lookup();
Widget reminderTimeWidget({required BuildContext context}) {
List<String> reminderTimeList = ['5 minutes before', '10 minutes before', '15 minutes before'];
return Consumer<NeedVisitReminderTimeProvider>(builder: (cxt, snapshot, _) {
if (snapshot.loading) {
return const ALoading();
}
return StatefulBuilder(
builder: (context, setState) {
return Wrap(
direction: Axis.vertical,
runSpacing: 8,
spacing: 8,
children: [
for (var element in reminderTimeList)
Row(
mainAxisSize: MainAxisSize.min,
children: [
SizedBox(
width: 24,
height: 24,
child: Radio<String>(
value: element,
activeColor: Colors.red,
fillColor: MaterialStateColor.resolveWith((states) {
if (states.contains(MaterialState.selected)) return AppColor.primary10;
return AppColor.neutral130;
}),
groupValue: selectedReminderTime,
onChanged: (String? value) {
setState(() {
selectedReminderTime = value!;
});
},
return StatefulBuilder(
builder: (context, setState) {
return Wrap(
direction: Axis.vertical,
runSpacing: 8,
spacing: 20,
children: [
for (var element in snapshot.items)
Row(
mainAxisSize: MainAxisSize.min,
children: [
SizedBox(
width: 24,
height: 24,
child: Radio<Lookup>(
value: element,
activeColor: Colors.red,
fillColor: MaterialStateColor.resolveWith((states) {
if (states.contains(MaterialState.selected)) return AppColor.primary10;
return AppColor.neutral130;
}),
groupValue: selectedReminderTime,
onChanged: (Lookup? value) {
setState(() {
selectedReminderTime = value!;
});
},
),
),
),
8.width,
Text(element, style: AppTextStyles.bodyText.copyWith(color: AppColor.neutral120)),
],
)
],
);
},
);
8.width,
Text(element.name ?? '', style: AppTextStyles.bodyText.copyWith(color: AppColor.neutral120)),
],
)
],
);
},
).toShimmer(isShow: snapshot.loading);
});
}
return buildBottomSheetParent(
@ -380,7 +398,7 @@ class ServiceRequestBottomSheet {
alignment: AlignmentDirectional.centerStart,
child: context.translation.youCanSetTheReminderInAlarmToRemindYouBeforeVisit.bodyText2(context),
),
12.height,
30.height,
reminderTimeWidget(context: context),
30.height,
Row(
@ -393,20 +411,6 @@ class ServiceRequestBottomSheet {
textColor: AppColor.black10,
loading: false,
onPressed: () async {
if (requestDetailProvider.currentWorkOrder?.data?.nextStep!.workOrderNextStepEnum == WorkOrderNextStepEnum.eArrived) {
requestDetailProvider.updateNeedVisitHelperModel(
NeedVisitHelperModel(
workOrderId: requestDetailProvider.needVisitHelperModel?.workOrderId,
visitDate: requestDetailProvider.needVisitHelperModel?.visitDate,
comment: requestDetailProvider.needVisitHelperModel?.comment,
),
);
requestDetailProvider.engineerUpdateNeedVisit();
} else {
requestDetailProvider.needVisitHelperModel?.workOrderId = requestDetailProvider.currentWorkOrder!.data!.requestId;
requestDetailProvider.engineerNeedVisit();
requestDetailProvider.needVisitHelperModel = NeedVisitHelperModel();
}
Navigator.pop(context);
},
),
@ -418,19 +422,16 @@ class ServiceRequestBottomSheet {
buttonColor: AppColor.primary10,
loading: false,
onPressed: () async {
if (requestDetailProvider.currentWorkOrder?.data?.nextStep!.workOrderNextStepEnum == WorkOrderNextStepEnum.eArrived) {
requestDetailProvider.updateNeedVisitHelperModel(
NeedVisitHelperModel(
workOrderId: requestDetailProvider.needVisitHelperModel?.workOrderId,
visitDate: requestDetailProvider.needVisitHelperModel?.visitDate,
comment: requestDetailProvider.needVisitHelperModel?.comment,
),
);
requestDetailProvider.engineerUpdateNeedVisit();
} else {
requestDetailProvider.needVisitHelperModel?.workOrderId = requestDetailProvider.currentWorkOrder!.data!.requestId;
requestDetailProvider.engineerNeedVisit();
requestDetailProvider.needVisitHelperModel = NeedVisitHelperModel();
requestDetailProvider.engineerSetReminder(workOrderId: requestDetailProvider.currentWorkOrder!.data!.requestId!, reminderId: selectedReminderTime.id!);
try {
DateTime visitDateTime = DateTime.parse(requestDetailProvider.currentWorkOrder!.data!.needAVisitDateTime.toString());
DateTime updatedDateTime = visitDateTime.subtract(Duration(minutes: selectedReminderTime.value ?? 0));
if (updatedDateTime.isAfter(DateTime.now())) {
ServiceRequestUtils.scheduleNotification(context: context, scheduleDateTime: updatedDateTime);
ServiceRequestUtils.addEventToCalendar(context: context, start: updatedDateTime, end: visitDateTime, title: context.translation.needAVisit);
}
} catch (e) {
log('error $e');
}
Navigator.pop(context);
},
@ -445,6 +446,7 @@ class ServiceRequestBottomSheet {
),
);
}
static Future getQRCodeBottomSheet({required BuildContext context}) async {
// Show the loading dialog while fetching QR code
showDialog(context: context, barrierDismissible: false, builder: (context) => const AppLazyLoading());
@ -481,12 +483,12 @@ class ServiceRequestBottomSheet {
child: isLoading
? const ALoading() // Show loader while fetching the new QR code
: Image.memory(
bytes, // Displaying the QR code from base64
fit: BoxFit.contain, // Ensure the image fits well in the dialog
errorBuilder: (context, error, stackTrace) {
return const Icon(Icons.error, color: Colors.red);
},
),
bytes, // Displaying the QR code from base64
fit: BoxFit.contain, // Ensure the image fits well in the dialog
errorBuilder: (context, error, stackTrace) {
return const Icon(Icons.error, color: Colors.red);
},
),
),
),
12.height,
@ -538,7 +540,6 @@ class ServiceRequestBottomSheet {
},
),
16.height,
],
);
},
@ -549,7 +550,6 @@ class ServiceRequestBottomSheet {
}
}
static Future rejectRequestBottomSheet({required BuildContext context}) {
TextEditingController _commentController = TextEditingController();
return buildBottomSheetParent(
@ -854,7 +854,7 @@ class ServiceRequestBottomSheet {
buttonColor: AppColor.green70,
loading: false,
onPressed: () {
if(feedback.isEmpty){
if (feedback.isEmpty) {
"Please provide feedback".showToast;
return;
}
@ -1045,8 +1045,8 @@ class ServiceRequestBottomSheet {
],
);
}));
}
static Future nurseVerifyArrivalBottomSheet({required BuildContext context}) {
return buildBottomSheetParent(
context: context,
@ -1094,7 +1094,7 @@ class ServiceRequestBottomSheet {
buttonColor: AppColor.green70,
onPressed: () async {
Navigator.pop(context);
int? status = await requestDetailProvider.nurseConfirmEngineerArrival(workOrderId: requestDetailProvider.currentWorkOrder?.data?.requestId ?? 0);
int? status = await requestDetailProvider.nurseConfirmEngineerArrival(workOrderId: requestDetailProvider.currentWorkOrder?.data?.requestId ?? 0);
if (status == 200) {
requestDetailProvider.getWorkOrderById(id: requestDetailProvider.currentWorkOrder!.data!.requestId!);
}
@ -1105,13 +1105,13 @@ class ServiceRequestBottomSheet {
],
);
}));
}
static Future waitingForApprovalBottomSheet({required BuildContext context}) {
return buildBottomSheetParent(
context: context,
childWidget: Consumer<ServiceRequestDetailProvider>(builder: (context, ServiceRequestDetailProvider requestDetailProvider, child) {
return Column(
return Column(
mainAxisSize: MainAxisSize.min,
crossAxisAlignment: CrossAxisAlignment.start,
children: [
@ -1132,7 +1132,5 @@ class ServiceRequestBottomSheet {
],
);
}));
}
}

@ -1,3 +1,5 @@
import 'dart:developer';
import 'package:flutter/material.dart';
import 'package:provider/provider.dart';
import 'package:test_sa/extensions/context_extension.dart';
@ -9,9 +11,18 @@ import 'package:test_sa/new_views/app_style/app_color.dart';
import 'package:test_sa/service_request_latest/service_request_detail_provider.dart';
import 'package:test_sa/service_request_latest/views/components/bottom_sheets/service_request_bottomsheet.dart';
class InitialVisitCard extends StatelessWidget {
class InitialVisitCard extends StatefulWidget {
const InitialVisitCard({Key? key}) : super(key: key);
@override
State<InitialVisitCard> createState() => _InitialVisitCardState();
}
class _InitialVisitCardState extends State<InitialVisitCard> {
@override
void initState() {
super.initState();
}
@override
Widget build(BuildContext context) {
return Consumer<ServiceRequestDetailProvider>(builder: (context, ServiceRequestDetailProvider requestDetailProvider, snapshot) {
@ -27,13 +38,22 @@ class InitialVisitCard extends StatelessWidget {
children: [
Row(mainAxisAlignment: MainAxisAlignment.spaceBetween, children: [
Text(
requestDetailProvider.needVisitHelperModel!.visitDate.toString().toInitialVisitCardFormat,
requestDetailProvider.needVisitHelperModel!.visitDate != null ? requestDetailProvider.needVisitHelperModel!.visitDate.toString().toInitialVisitCardFormat : '',
textAlign: TextAlign.end,
style: AppTextStyles.heading6.copyWith(color: context.isDark ? AppColor.neutral30 : AppColor.black10),
),
"edit_icon".toSvgAsset(height: 21, width: 21).onPress(() {
ServiceRequestBottomSheet.initialVisitBottomSheet(context: context);
}),
Row(
children: [
"reminder_icon".toSvgAsset(height: 21, width: 21).onPress(() {
ServiceRequestBottomSheet.getReminderTimeList(context: context);
ServiceRequestBottomSheet.initialVisitReminderBottomSheet(context: context, reminder: requestDetailProvider.currentWorkOrder?.data?.setReminder);
}),
24.width,
"edit_icon".toSvgAsset(height: 21, width: 21).onPress(() {
ServiceRequestBottomSheet.initialVisitBottomSheet(context: context);
}),
],
),
]),
2.height,
context.translation.visitDateAndTime.bodyText2(context).custom(color: AppColor.neutral120),

@ -25,7 +25,7 @@ import 'package:test_sa/views/widgets/requests/request_status.dart';
import 'package:test_sa/views/widgets/sound/sound_player.dart';
class ServiceRequestDetailView extends StatelessWidget {
ServiceRequestDetailView({Key? key}) : super(key: key);
const ServiceRequestDetailView({Key? key}) : super(key: key);
@override
Widget build(BuildContext context) {
@ -54,6 +54,7 @@ class ServiceRequestDetailView extends StatelessWidget {
).expanded,
FooterActionButton.requestDetailsFooterWidget(
workOrderNextStepStatus: requestProvider.currentWorkOrder!.data!.nextStep!.workOrderNextStepEnum!,
// workOrderNextStepStatus: WorkOrderNextStepEnum.eNeedVisit,
activities: requestProvider.currentWorkOrder!.data?.activities ?? [],
userProvider: _userProvider,
context: context),
@ -213,7 +214,6 @@ class ServiceRequestDetailView extends StatelessWidget {
'${context.translation.assetStatus}: ${workOrder.equipmentStatus?.name ?? "-"}',
style: AppTextStyles.bodyText.copyWith(color: context.isDark ? AppColor.neutral10 : AppColor.neutral120),
),
//TODO need to confirm from backend..
Text(
'${context.translation.activityStatus}: ${workOrder.lastActivityStatus?.name ?? "-"}',
style: AppTextStyles.bodyText.copyWith(color: context.isDark ? AppColor.neutral10 : AppColor.neutral120),
@ -330,11 +330,11 @@ class ServiceRequestDetailView extends StatelessWidget {
if (requestDetailProvider.currentWorkOrder!.data!.needAVisitDateTime != null &&
userProvider.user?.type == UsersTypes.engineer &&
requestDetailProvider.currentWorkOrder?.data?.nextStep!.workOrderNextStepEnum == WorkOrderNextStepEnum.eArrived) {
requestDetailProvider.needVisitHelperModel = NeedVisitHelperModel(
workOrderId: requestDetailProvider.currentWorkOrder?.data?.requestId,
visitDate: requestDetailProvider.currentWorkOrder?.data?.needAVisitDateTime,
comment: requestDetailProvider.currentWorkOrder?.data?.needAVisitComment,
);
// requestDetailProvider.needVisitHelperModel = NeedVisitHelperModel(
// workOrderId: requestDetailProvider.currentWorkOrder?.data?.requestId,
// visitDate: requestDetailProvider.currentWorkOrder?.data?.needAVisitDateTime,
// comment: requestDetailProvider.currentWorkOrder?.data?.needAVisitComment,
// );
return const InitialVisitCard();
} else {
return const SizedBox();

@ -1,9 +1,12 @@
import 'dart:developer';
import 'package:flutter/material.dart';
import 'package:intl/intl.dart';
import 'package:provider/provider.dart';
import 'package:test_sa/dashboard_latest/dashboard_provider.dart';
import 'package:test_sa/extensions/int_extensions.dart';
import 'package:test_sa/extensions/text_extensions.dart';
import 'package:test_sa/models/enums/user_types.dart';
import 'package:test_sa/new_views/app_style/app_color.dart';
class WeeklyCalendarFragment extends StatefulWidget {
@ -51,6 +54,10 @@ class _WeeklyCalendarFragmentState extends State<WeeklyCalendarFragment> {
setState(() {
selectedDate = currentDate; // Update selected date on tap
});
log('selected date:${selectedDate?.toIso8601String()}');
DashBoardProvider dashBoardProvider = Provider.of<DashBoardProvider>(context, listen: false);
dashBoardProvider.resetRequestDataList();
dashBoardProvider.getRequestDetail(usersType: UsersTypes.engineer, date: selectedDate?.toIso8601String(), status: 0);
},
);
},
@ -94,7 +101,7 @@ class _WeeklyCalendarFragmentState extends State<WeeklyCalendarFragment> {
decoration: ShapeDecoration(
color: AppColor.background(context),
shape: RoundedRectangleBorder(
borderRadius: BorderRadius.circular(14),
borderRadius: BorderRadius.circular(10),
side: isSelected
? const BorderSide(color: AppColor.primary10, width: 2) // Blue border if selected
: BorderSide.none,

@ -12,6 +12,7 @@ import 'package:test_sa/service_request_latest/service_request_detail_provider.d
import 'package:test_sa/service_request_latest/utilities/service_request_utils.dart';
import 'package:test_sa/service_request_latest/views/forms/maintenance_request/components/assistant_employee_card.dart';
import 'package:test_sa/views/widgets/date_and_time/date_picker.dart';
import 'package:test_sa/views/widgets/timer/app_timer.dart';
import '../../../../../models/lookup.dart';
import '../../../../../new_views/common_widgets/app_text_form_field.dart';
import '../../../../../new_views/common_widgets/single_item_drop_down_menu.dart';
@ -37,8 +38,7 @@ class _InternalMaintenanceRequestState extends State<InternalMaintenanceRequest>
_requestDetailProvider = Provider.of<ServiceRequestDetailProvider>(context, listen: false);
super.initState();
WidgetsBinding.instance.addPostFrameCallback((_) {
_travellingHoursController.text =
_requestDetailProvider?.activityMaintenanceHelperModel?.travelHours != null ? _requestDetailProvider!.activityMaintenanceHelperModel!.travelHours.toString() : '';
_travellingHoursController.text= _requestDetailProvider?.activityMaintenanceHelperModel?.travelHours != null ? _requestDetailProvider!.activityMaintenanceHelperModel!.travelHours.toString() : '';
});
// _isLoading = true;
}
@ -55,6 +55,7 @@ class _InternalMaintenanceRequestState extends State<InternalMaintenanceRequest>
@override
Widget build(BuildContext context) {
return Consumer<ServiceRequestDetailProvider>(builder: (context, requestDetailProvider, child) {
double totalWorkingHours = _requestDetailProvider?.activityMaintenanceHelperModel?.activityMaintenanceTimers?.fold(0.0, (sum, item) => (sum ?? 0) + DateTime.parse(item.endTime!).difference(DateTime.parse(item.startTime!)).inSeconds) ?? 0;
return SingleChildScrollView(
child: Column(
children: [
@ -92,95 +93,136 @@ class _InternalMaintenanceRequestState extends State<InternalMaintenanceRequest>
},
),
8.height,
Row(
mainAxisSize: MainAxisSize.min,
children: [
ADatePicker(
label: context.translation.startTime,
hideShadow: true,
backgroundColor: AppColor.neutral100,
date: requestDetailProvider.activityMaintenanceHelperModel?.startTime,
formatDateWithTime: true,
onDatePicker: (selectedDate) {
showTimePicker(
context: context,
initialTime: TimeOfDay.now(),
).then((selectedTime) {
// Handle the selected date and time here.
if (selectedTime != null) {
DateTime selectedDateTime = DateTime(
selectedDate.year,
selectedDate.month,
selectedDate.day,
selectedTime.hour,
selectedTime.minute,
);
requestDetailProvider.activityMaintenanceHelperModel?.startTime = selectedDateTime;
requestDetailProvider.activityMaintenanceHelperModel?.endTime = null;
requestDetailProvider.updateActivityMaintenanceHelperModel(requestDetailProvider.activityMaintenanceHelperModel);
_workingHoursController.clear();
ServiceRequestUtils.calculateAndAssignWorkingHours(
startTime: requestDetailProvider.activityMaintenanceHelperModel!.startTime,
endTime: requestDetailProvider.activityMaintenanceHelperModel!.endTime,
workingHoursController: _workingHoursController,
updateModel: (hours) {
requestDetailProvider.activityMaintenanceHelperModel?.workingHour = hours;
},
);
}
});
},
).expanded,
8.width,
ADatePicker(
label: context.translation.endTime,
hideShadow: true,
backgroundColor: AppColor.neutral100,
date: requestDetailProvider.activityMaintenanceHelperModel?.endTime,
formatDateWithTime: true,
onDatePicker: (selectedDate) {
showTimePicker(
context: context,
initialTime: TimeOfDay.now(),
).then((selectedTime) {
// Handle the selected date and time here.
if (selectedTime != null) {
DateTime selectedDateTime = DateTime(selectedDate.year, selectedDate.month, selectedDate.day, selectedTime.hour, selectedTime.minute);
if (requestDetailProvider.activityMaintenanceHelperModel!.startTime != null &&
selectedDateTime.isBefore(requestDetailProvider.activityMaintenanceHelperModel!.startTime!)) {
"End Date time must be greater then start date".showToast;
return;
}
requestDetailProvider.activityMaintenanceHelperModel?.endTime = selectedDateTime;
requestDetailProvider.updateActivityMaintenanceHelperModel(requestDetailProvider.activityMaintenanceHelperModel);
ServiceRequestUtils.calculateAndAssignWorkingHours(
startTime: requestDetailProvider.activityMaintenanceHelperModel!.startTime,
endTime: requestDetailProvider.activityMaintenanceHelperModel!.endTime,
workingHoursController: _workingHoursController,
updateModel: (hours) {
requestDetailProvider.activityMaintenanceHelperModel?.workingHour = hours;
},
);
}
});
},
).expanded,
],
),
8.height,
AppTextFormField(
labelText: context.translation.workingHours,
backgroundColor: AppColor.neutral80,
controller: _workingHoursController,
suffixIcon: "clock".toSvgAsset(width: 20, color: context.isDark ? AppColor.neutral10 : null).paddingOnly(end: 16),
initialValue: requestDetailProvider.activityMaintenanceHelperModel?.workingHour != null ? requestDetailProvider.activityMaintenanceHelperModel?.workingHour.toString() : '',
textAlign: TextAlign.center,
labelStyle: AppTextStyles.textFieldLabelStyle,
enable: false,
showShadow: false,
style: Theme.of(context).textTheme.titleMedium,
AppTimer(
label: context.translation.timer,
timer: requestDetailProvider.activityMaintenanceHelperModel?.activityMaintenanceTimerModel,
enabled: requestDetailProvider.activityMaintenanceHelperModel?.activityMaintenanceTimerModel?.endAt == null,
timerProgress: (isRunning) {
print("timerProgress:$isRunning");
},
onChange: (timer) async {
requestDetailProvider.activityMaintenanceHelperModel?.activityMaintenanceTimerModel = timer;
return true;
},
),
// Row(
// mainAxisSize: MainAxisSize.min,
// children: [
// ADatePicker(
// label: context.translation.startTime,
// hideShadow: true,
// backgroundColor: AppColor.neutral100,
// date: requestDetailProvider.activityMaintenanceHelperModel?.startTime,
// formatDateWithTime: true,
// onDatePicker: (selectedDate) {
// showTimePicker(
// context: context,
// initialTime: TimeOfDay.now(),
// ).then((selectedTime) {
// // Handle the selected date and time here.
// if (selectedTime != null) {
// DateTime selectedDateTime = DateTime(
// selectedDate.year,
// selectedDate.month,
// selectedDate.day,
// selectedTime.hour,
// selectedTime.minute,
// );
// requestDetailProvider.activityMaintenanceHelperModel?.startTime = selectedDateTime;
// requestDetailProvider.activityMaintenanceHelperModel?.endTime = null;
// requestDetailProvider.updateActivityMaintenanceHelperModel(requestDetailProvider.activityMaintenanceHelperModel);
// _workingHoursController.clear();
// ServiceRequestUtils.calculateAndAssignWorkingHours(
// startTime: requestDetailProvider.activityMaintenanceHelperModel!.startTime,
// endTime: requestDetailProvider.activityMaintenanceHelperModel!.endTime,
// workingHoursController: _workingHoursController,
// updateModel: (hours) {
// requestDetailProvider.activityMaintenanceHelperModel?.workingHour = hours;
// },
// );
// }
// });
// },
// ).expanded,
// 8.width,
// ADatePicker(
// label: context.translation.endTime,
// hideShadow: true,
// backgroundColor: AppColor.neutral100,
// date: requestDetailProvider.activityMaintenanceHelperModel?.endTime,
// formatDateWithTime: true,
// onDatePicker: (selectedDate) {
// showTimePicker(
// context: context,
// initialTime: TimeOfDay.now(),
// ).then((selectedTime) {
// // Handle the selected date and time here.
// if (selectedTime != null) {
// DateTime selectedDateTime = DateTime(selectedDate.year, selectedDate.month, selectedDate.day, selectedTime.hour, selectedTime.minute);
// if (requestDetailProvider.activityMaintenanceHelperModel!.startTime != null &&
// selectedDateTime.isBefore(requestDetailProvider.activityMaintenanceHelperModel!.startTime!)) {
// "End Date time must be greater then start date".showToast;
// return;
// }
// requestDetailProvider.activityMaintenanceHelperModel?.endTime = selectedDateTime;
// requestDetailProvider.updateActivityMaintenanceHelperModel(requestDetailProvider.activityMaintenanceHelperModel);
// ServiceRequestUtils.calculateAndAssignWorkingHours(
// startTime: requestDetailProvider.activityMaintenanceHelperModel!.startTime,
// endTime: requestDetailProvider.activityMaintenanceHelperModel!.endTime,
// workingHoursController: _workingHoursController,
// updateModel: (hours) {
// requestDetailProvider.activityMaintenanceHelperModel?.workingHour = hours;
// },
// );
// }
// });
// },
// ).expanded,
// ],
// ),
8.height,
if (totalWorkingHours > 0.0) ...[
Container(
height: 56.toScreenHeight,
padding: EdgeInsets.symmetric(horizontal: 16.toScreenWidth),
alignment: Alignment.centerLeft,
decoration: BoxDecoration(
color: context.isDark ? AppColor.neutral40 : AppColor.background(context),
borderRadius: BorderRadius.circular(10),
boxShadow: [BoxShadow(color: Colors.black.withOpacity(0.05), blurRadius: 10)],
),
child: Column(
crossAxisAlignment: CrossAxisAlignment.start,
mainAxisAlignment: MainAxisAlignment.center,
children: [
Text(
"Total Working Time",
style: Theme.of(context).textTheme.bodySmall?.copyWith(color: context.isDark ? null : AppColor.neutral20, fontWeight: FontWeight.w500),
),
Text(
" ${ServiceRequestUtils.formatTimerDuration(totalWorkingHours.round())}",
style: Theme.of(context).textTheme.bodyMedium,
),
],
),
),
8.height,
],
// if (totalWorkingHours > 0.0) ...[
// AppTextFormField(
// labelText: context.translation.workingHours,
// backgroundColor: AppColor.neutral80,
// controller: _workingHoursController,
// suffixIcon: "clock".toSvgAsset(width: 20, color: context.isDark ? AppColor.neutral10 : null).paddingOnly(end: 16),
// initialValue: requestDetailProvider.activityMaintenanceHelperModel?.workingHour != null ? requestDetailProvider.activityMaintenanceHelperModel?.workingHour.toString() : '',
// textAlign: TextAlign.center,
// labelStyle: AppTextStyles.textFieldLabelStyle,
// enable: false,
// showShadow: false,
// style: Theme.of(context).textTheme.titleMedium,
// ),
// 8.height,
// ],
AppTextFormField(
labelText: context.translation.travelingHours,
controller: _travellingHoursController,

@ -99,10 +99,25 @@ class _MaintenanceRequestFormState extends State<MaintenanceRequestForm> with Si
//TODO add this as dropdown not added in design yet Bhaa need to confirm with hussain then.
requestDetailProvider.activityMaintenanceHelperModel?.lastSituationId = 282;
print('model is ${requestDetailProvider.activityMaintenanceHelperModel?.toJson()}');
if (validate(model: requestDetailProvider.activityMaintenanceHelperModel!)) {
print('value of timer is ${requestDetailProvider.activityMaintenanceHelperModel?.activityMaintenanceTimerModel.toString()}');
ActivityMaintenanceTimers model = ActivityMaintenanceTimers(
id: 0,
startTime: requestDetailProvider.activityMaintenanceHelperModel?.activityMaintenanceTimerModel?.startAt!.toIso8601String(), // Handle potential null
endTime: requestDetailProvider.activityMaintenanceHelperModel?.activityMaintenanceTimerModel?.endAt?.toIso8601String(), // Handle potential null
workingHours: ((requestDetailProvider.activityMaintenanceHelperModel?.activityMaintenanceTimerModel?.durationInSecond ?? 0) / 60 / 60),
);
print('model i got is ${model.toJson()}');
requestDetailProvider.activityMaintenanceHelperModel?.activityMaintenanceTimers =requestDetailProvider.activityMaintenanceHelperModel?.activityMaintenanceTimers??[];
requestDetailProvider.activityMaintenanceHelperModel?.activityMaintenanceTimers?.add(
ActivityMaintenanceTimers(
id: 0,
startTime: requestDetailProvider.activityMaintenanceHelperModel?.activityMaintenanceTimerModel?.startAt!.toIso8601String(), // Handle potential null
endTime: requestDetailProvider.activityMaintenanceHelperModel?.activityMaintenanceTimerModel?.endAt?.toIso8601String(), // Handle potential null
workingHours: ((requestDetailProvider.activityMaintenanceHelperModel?.activityMaintenanceTimerModel?.durationInSecond ?? 0) / 60 / 60),
),
);
showDialog(context: context, barrierDismissible: false, builder: (context) => const AppLazyLoading());
int status = -1;
if (requestDetailProvider.activityMaintenanceHelperModel?.id == 0) {
@ -130,23 +145,33 @@ class _MaintenanceRequestFormState extends State<MaintenanceRequestForm> with Si
}
bool validate({required ActivityMaintenanceHelperModel model}) {
print('employee id is ${model.assignedEmployeeId}');
if (model.activityStatus == null) {
Fluttertoast.showToast(msg: "${context.translation.youHaveToSelect} ${context.translation.activityStatus}");
return false;
} else if (model.startTime == null) {
Fluttertoast.showToast(msg: "${context.translation.youHaveToSelect} ${context.translation.startTime}");
}
if (model.activityMaintenanceTimerModel?.startAt == null) {
Fluttertoast.showToast(msg: "Working Hours Required");
return false;
} else if (model.endTime == null) {
Fluttertoast.showToast(msg: "${context.translation.youHaveToSelect} ${context.translation.endTime}");
}
if (model.activityMaintenanceTimerModel?.endAt == null) {
Fluttertoast.showToast(msg: "Please Stop The Timer");
return false;
}
// if (model.startTime == null) {
// Fluttertoast.showToast(msg: "${context.translation.youHaveToSelect} ${context.translation.startTime}");
// return false;
// }
// if (model.endTime == null) {
// Fluttertoast.showToast(msg: "${context.translation.youHaveToSelect} ${context.translation.endTime}");
// return false;
// }
// else if (model.travelHours == null) {
// Fluttertoast.showToast(msg: "${context.translation.youHaveToSelect} ${context.translation.travelingHours}");
// return false;
// }
else if (model.repairLocation == null) {
if (model.repairLocation == null) {
Fluttertoast.showToast(msg: "${context.translation.youHaveToSelect} ${context.translation.repairLocation}");
return false;
}

@ -7,6 +7,7 @@ import 'package:test_sa/extensions/text_extensions.dart';
import 'package:test_sa/extensions/widget_extensions.dart';
import 'package:test_sa/models/enums/user_types.dart';
import 'package:test_sa/models/enums/work_order_next_step.dart';
import 'package:test_sa/models/helper_data_models/workorder/work_order_helper_models.dart';
import 'package:test_sa/new_views/app_style/app_color.dart';
import 'package:test_sa/new_views/common_widgets/default_app_bar.dart';
import 'package:test_sa/service_request_latest/service_request_detail_provider.dart';
@ -43,6 +44,11 @@ class _ServiceRequestDetailMainState extends State<ServiceRequestDetailMain> {
if (isNurse && (_requestProvider.currentWorkOrder?.data?.nextStep?.workOrderNextStepEnum == WorkOrderNextStepEnum.waitingForRequesterToConfirm)) {
ServiceRequestBottomSheet.nurseVerifyArrivalBottomSheet(context: context);
}
_requestProvider.needVisitHelperModel = NeedVisitHelperModel(
workOrderId: _requestProvider.currentWorkOrder?.data?.requestId,
visitDate: _requestProvider.currentWorkOrder?.data?.needAVisitDateTime,
comment: _requestProvider.currentWorkOrder?.data?.needAVisitComment,
);
}
@override
@ -62,10 +68,6 @@ class _ServiceRequestDetailMainState extends State<ServiceRequestDetailMain> {
bool isNurse = (Provider.of<UserProvider>(context, listen: false).user?.type) == UsersTypes.normal_user;
return WillPopScope(
onWillPop: () async {
ServiceRequestDetailProvider requestDetailProvider = Provider.of<ServiceRequestDetailProvider>(context, listen: false);
if (requestDetailProvider.timer != null && requestDetailProvider.timer!.isActive) {
requestDetailProvider.stopTimer();
}
stopTimer();
return true;
},
@ -91,7 +93,7 @@ class _ServiceRequestDetailMainState extends State<ServiceRequestDetailMain> {
: IconButton(
icon: const Icon(Icons.home),
onPressed: () {
stopTimer();
// stopTimer();
Navigator.pop(context);
},
),
@ -126,10 +128,10 @@ class _ServiceRequestDetailMainState extends State<ServiceRequestDetailMain> {
),
),
12.height,
TabBarView(
const TabBarView(
children: [
ServiceRequestDetailView(),
const HistoryLogView(),
HistoryLogView(),
],
).expanded,
],

Loading…
Cancel
Save