diff --git a/lib/controllers/api_routes/urls.dart b/lib/controllers/api_routes/urls.dart index 30aed29d..e52251cd 100644 --- a/lib/controllers/api_routes/urls.dart +++ b/lib/controllers/api_routes/urls.dart @@ -30,6 +30,7 @@ class URLs { static get getServiceRequestTypes => "$_baseUrl/Lookups/GetLookup?lookupEnum=604"; // get static get getServiceRequestStatus => "$_baseUrl/Lookups/GetLookup?lookupEnum=503"; static get getRepairLocation => "$_baseUrl/Lookups/GetLookup?lookupEnum=504"; + static get equipmentStatus => "$_baseUrl/Lookups/GetLookup?lookupEnum=601"; static get getPreventiveMaintenanceVisits => "$_baseUrl/return/user/calibrations"; // get static get updatePreventiveMaintenanceVisits => "$_baseUrl/Visit/UpdateVisits"; // get @@ -55,10 +56,11 @@ class URLs { static get getServiceReportTypes => "$_baseUrl/Lookups/GetLookup?lookupEnum=501"; // get static get getServiceReportStatus => "$_baseUrl/Lookups/GetLookup?lookupEnum=521"; // get static get getServiceReportLastCalls => "$_baseUrl/WorkOrder/GetLookupCallLastSituationBasedOnCase"; // get - static get getAssetTypes => "$_baseUrl/Lookups/GetLookup?lookupEnum=28"; // get + static get getAssetTypes => "$_baseUrl/Lookups/GetLookup?lookupEnum=500"; // get static get getPartNumber => "$_baseUrl/PartCatalog/GetPartAutoComplete"; // get static get getServiceReportPriority => "$_baseUrl/Lookups/GetLookup?lookupEnum=602"; // get static get getServiceReportDefectTypes => "$_baseUrl/Lookups/GetLookup?lookupEnum=601"; // get + static get getCallRequestForWorkOrder => "$_baseUrl/CallRequest/GetCallRequestForWorkOrder"; // get //gas refill static get getGasTypes => "$_baseUrl/Lookups/GetLookup?lookupEnum=606"; // get diff --git a/lib/controllers/providers/api/device_transfer_provider.dart b/lib/controllers/providers/api/device_transfer_provider.dart index f3cd3a46..b0140531 100644 --- a/lib/controllers/providers/api/device_transfer_provider.dart +++ b/lib/controllers/providers/api/device_transfer_provider.dart @@ -10,7 +10,7 @@ import 'package:test_sa/models/user.dart'; class DeviceTransferProvider extends ChangeNotifier { // number of items call in each request - final pageItemNumber = 50; + final pageItemNumber = 12; //reset provider data void reset() { diff --git a/lib/controllers/providers/api/gas_refill_provider.dart b/lib/controllers/providers/api/gas_refill_provider.dart index ef9beedf..c293bf75 100644 --- a/lib/controllers/providers/api/gas_refill_provider.dart +++ b/lib/controllers/providers/api/gas_refill_provider.dart @@ -9,7 +9,7 @@ import 'package:test_sa/models/user.dart'; class GasRefillProvider extends ChangeNotifier { // number of items call in each request - final pageItemNumber = 50; + final pageItemNumber = 12; //reset provider data void reset() { @@ -50,6 +50,7 @@ class GasRefillProvider extends ChangeNotifier { Map body = {}; body["pageNumber"] = (items?.length ?? 0) ~/ pageItemNumber + 1; body["pageSize"] = pageItemNumber; + print("url:${ URLs.getGasRefill}:body:$body"); response = await ApiManager.instance.post( URLs.getGasRefill, diff --git a/lib/controllers/providers/api/hospitals_provider.dart b/lib/controllers/providers/api/hospitals_provider.dart index 9a54490c..38c1f1aa 100644 --- a/lib/controllers/providers/api/hospitals_provider.dart +++ b/lib/controllers/providers/api/hospitals_provider.dart @@ -10,7 +10,7 @@ import 'package:test_sa/models/user.dart'; class HospitalsProvider extends ChangeNotifier { // number of items call in each request - final pageItemNumber = 50; + final pageItemNumber = 12; //reset provider data void reset() { diff --git a/lib/controllers/providers/api/notifications_provider.dart b/lib/controllers/providers/api/notifications_provider.dart index 05ec6738..b7683ab5 100644 --- a/lib/controllers/providers/api/notifications_provider.dart +++ b/lib/controllers/providers/api/notifications_provider.dart @@ -8,7 +8,7 @@ import 'package:test_sa/models/user.dart'; class NotificationsProvider extends ChangeNotifier { // number of items call in each request - final pageItemNumber = 20; + final pageItemNumber = 12; //reset provider data void reset() { diff --git a/lib/controllers/providers/api/parts_provider.dart b/lib/controllers/providers/api/parts_provider.dart index 7f8cca4f..c0ae098c 100644 --- a/lib/controllers/providers/api/parts_provider.dart +++ b/lib/controllers/providers/api/parts_provider.dart @@ -10,7 +10,7 @@ import 'package:test_sa/models/user.dart'; class PartsProvider extends ChangeNotifier { // number of items call in each request - final pageItemNumber = 50; + final pageItemNumber = 20; //reset provider data void reset() { diff --git a/lib/controllers/providers/api/service_requests_provider.dart b/lib/controllers/providers/api/service_requests_provider.dart index bdd12b03..a044543d 100644 --- a/lib/controllers/providers/api/service_requests_provider.dart +++ b/lib/controllers/providers/api/service_requests_provider.dart @@ -5,6 +5,7 @@ import 'package:http/http.dart'; import 'package:test_sa/controllers/api_routes/api_manager.dart'; import 'package:test_sa/controllers/api_routes/http_status_manger.dart'; import 'package:test_sa/controllers/api_routes/urls.dart'; +import 'package:test_sa/models/call_request_for_work_order_model.dart'; import 'package:test_sa/models/issue.dart'; import 'package:test_sa/models/service_report.dart'; import 'package:test_sa/models/service_request/service_request.dart'; @@ -137,7 +138,7 @@ class ServiceRequestsProvider extends ChangeNotifier { var body = { "id": 0, "calNo": "", - "callCreatedBy": {"id": user.id, "name": user.userName ?? ""}, + "callCreatedBy": {"id": user.userID, "name": user.userName ?? ""}, "assets": serviceRequest.deviceId == null ? [] : [serviceRequest.deviceId], "requestedDate": DateTime.now().toIso8601String(), "requestedTime": DateTime.now().toIso8601String(), @@ -159,7 +160,7 @@ class ServiceRequestsProvider extends ChangeNotifier { // "job": "", "email": user.email, // "land": "", - "contactUserId": user.id, + "contactUserId": user.userID, }, ], "noofFollowup": 0, @@ -245,7 +246,7 @@ class ServiceRequestsProvider extends ChangeNotifier { "job": callSiteContactPerson['job'], "email": callSiteContactPerson['email'] ?? user.email, "land": callSiteContactPerson['land'], - "contactUserId": user.id, + "contactUserId": user.userID, }, ], "callComments": request.callComments, @@ -294,7 +295,7 @@ class ServiceRequestsProvider extends ChangeNotifier { "id": request.id, }, "assetType": report.assetType?.toMap(), - "assignedEmployee": {"id": report.engineer.id, "name": report.engineer.name}, + "assignedEmployee": {"id": report.engineer?.id, "name": report.engineer?.name ?? ""}, "visitDate": report.visitDate?.toIso8601String() ?? "", // "assistantEmployees": [ // {"id": report.engineer.id, "name": report.engineer.name}, @@ -310,7 +311,7 @@ class ServiceRequestsProvider extends ChangeNotifier { // "job": "", "email": user.email, // "land": "", - "contactUserId": user.id, + "contactUserId": user.userID, } ], "calllastSituation": report.callLastSituation?.toMap(), @@ -322,12 +323,7 @@ class ServiceRequestsProvider extends ChangeNotifier { "workingHours": ((report?.endDate?.difference(report?.startDate)?.inMinutes ?? 0) / 60), "travelingHours": report.travelingHours, "travelingExpenses": report.travelingExpense ?? 0, - "faultDescription": { - "id": report.faultDescriptionId, - "defectName": report.type?.name, - "workPerformed": report.workPreformed, - "estimatedTime": report.operatingHours, - }, + if (report.faultDescription != null) "faultDescription": report.faultDescription.toJson(), "sparePartsWorkOrders": report.parts ?.map( (p) => { @@ -337,10 +333,10 @@ class ServiceRequestsProvider extends ChangeNotifier { }, ) ?.toList(), - "reviewComment": "", + "reviewComment": report.reviewComment ?? "", "comment": report.comment, "attachmentsWorkOrder": request.devicePhotos?.map((e) => {"name": e})?.toList(), - "equipmentStatus": report.status?.toMap(), + "equipmentStatus": report.equipmentStatus?.toMap(), "suppEngineerWorkOrders": null, "engSignature": report.signatureEngineer, "nurseSignature": report.signatureNurse, @@ -368,6 +364,28 @@ class ServiceRequestsProvider extends ChangeNotifier { } } + CallRequestForWorkOrder callRequestForWorkOrder; + + Future getCallRequestForWorkOrder({String callId}) async { + Response response; + try { + response = await ApiManager.instance.get( + URLs.getCallRequestForWorkOrder + "?callId=$callId", + ); + stateCode = response.statusCode; + if (response.statusCode >= 200 && response.statusCode < 300) { + // client's request was successfully received + Map listJson = json.decode(response.body)["data"]; + callRequestForWorkOrder = CallRequestForWorkOrder.fromJson(listJson); + } + + notifyListeners(); + return callRequestForWorkOrder; + } catch (error) { + return null; + } + } + Future> searchWorkOrders({@required String callId}) async { Response response; diff --git a/lib/controllers/providers/api/status_drop_down/report/service_report_equipment_status_provider.dart b/lib/controllers/providers/api/status_drop_down/report/service_report_equipment_status_provider.dart new file mode 100644 index 00000000..82ac1f49 --- /dev/null +++ b/lib/controllers/providers/api/status_drop_down/report/service_report_equipment_status_provider.dart @@ -0,0 +1,75 @@ +import 'dart:convert'; + +import 'package:test_sa/controllers/api_routes/api_manager.dart'; +import 'package:test_sa/controllers/api_routes/urls.dart'; +import 'package:test_sa/models/lookup.dart'; +import 'package:test_sa/models/user.dart'; +import 'package:flutter/cupertino.dart'; +import 'package:flutter/material.dart'; +import 'package:http/http.dart'; +import 'package:test_sa/controllers/api_routes/urls.dart'; +import 'package:test_sa/models/lookup.dart'; +import 'package:test_sa/models/user.dart'; + +class ServiceReportEquipmentStatusProvider extends ChangeNotifier { + //reset provider data + void reset() { + _status = null; + _stateCode = null; + } + + // state code of current request to defied error message + // like 400 customer request failed + // 500 service not available + int _stateCode; + + int get stateCode => _stateCode; + + // contain user data + // when user not login or register _user = null + List _status; + + List get statuses => _status; + + // when categories in-process _loading = true + // done _loading = true + // failed _loading = false + bool _loading; + + bool get isLoading => _loading; + + set isLoading(bool isLoading) { + _loading = isLoading; + notifyListeners(); + } + + /// return -2 if request in progress + /// return -1 if error happen when sending request + /// return state code if request complete may be 200, 404 or 403 + /// for more details check http state manager + /// lib\controllers\http_status_manger\http_status_manger.dart + Future getTypes({String host, User user}) async { + if (_loading == true) return -2; + _loading = true; + notifyListeners(); + Response response; + try { + response = await ApiManager.instance.get(URLs.equipmentStatus); + + _stateCode = response.statusCode; + if (response.statusCode >= 200 && response.statusCode < 300) { + // client's request was successfully received + List categoriesListJson = json.decode(response.body)["data"]; + _status = categoriesListJson.map((type) => Lookup.fromJson(type)).toList(); + } + _loading = false; + notifyListeners(); + return response.statusCode; + } catch (error) { + _loading = false; + _stateCode = -1; + notifyListeners(); + return -1; + } + } +} diff --git a/lib/controllers/providers/api/status_drop_down/report/service_report_fault_description_provider.dart b/lib/controllers/providers/api/status_drop_down/report/service_report_fault_description_provider.dart new file mode 100644 index 00000000..8946bd0a --- /dev/null +++ b/lib/controllers/providers/api/status_drop_down/report/service_report_fault_description_provider.dart @@ -0,0 +1,70 @@ +import 'dart:convert'; + +import 'package:flutter/cupertino.dart'; +import 'package:flutter/material.dart'; +import 'package:http/http.dart'; +import 'package:test_sa/controllers/api_routes/api_manager.dart'; +import 'package:test_sa/controllers/api_routes/urls.dart'; +import 'package:test_sa/models/user.dart'; + +import '../../../../../models/fault_description.dart'; + +class ServiceRequestFaultDescriptionProvider extends ChangeNotifier { + //reset provider data + void reset() { + _items = null; + _stateCode = null; + } + + // state code of current request to defied error message + // like 400 customer request failed + // 500 service not available + int _stateCode; + int get stateCode => _stateCode; + + // contain user data + // when user not login or register _user = null + List _items; + List get items => _items; + + // when categories in-process _loading = true + // done _loading = true + // failed _loading = false + bool _loading; + bool get isLoading => _loading; + set isLoading(bool isLoading) { + _loading = isLoading; + notifyListeners(); + } + + /// return -2 if request in progress + /// return -1 if error happen when sending request + /// return state code if request complete may be 200, 404 or 403 + /// for more details check http state manager + /// lib\controllers\http_status_manger\http_status_manger.dart + Future getCallRequestForWorkOrder({String host, User user, String requestId}) async { + if (_loading == true) return -2; + _loading = true; + notifyListeners(); + Response response; + try { + response = await ApiManager.instance.get( + URLs.getCallRequestForWorkOrder + "?callId=$requestId", + ); + _stateCode = response.statusCode; + if (response.statusCode >= 200 && response.statusCode < 300) { + // client's request was successfully received + List listJson = json.decode(response.body)["data"]['asset']['modelDefinition']['modelDefRelatedDefects']; + _items = listJson.map((type) => FaultDescription.fromJson(type)).toList(); + } + _loading = false; + notifyListeners(); + return response.statusCode; + } catch (error) { + _loading = false; + _stateCode = -1; + notifyListeners(); + return -1; + } + } +} diff --git a/lib/main.dart b/lib/main.dart index eef23138..3d85f355 100644 --- a/lib/main.dart +++ b/lib/main.dart @@ -22,6 +22,7 @@ import 'package:test_sa/controllers/providers/api/status_drop_down/gas_refill/ga import 'package:test_sa/controllers/providers/api/status_drop_down/pentry/pentry_task_status_provider.dart'; import 'package:test_sa/controllers/providers/api/status_drop_down/pentry/pentry_visit_status_provider.dart'; import 'package:test_sa/controllers/providers/api/status_drop_down/report/service_report_defect_types_provider.dart'; +import 'package:test_sa/controllers/providers/api/status_drop_down/report/service_report_equipment_status_provider.dart'; import 'package:test_sa/controllers/providers/api/status_drop_down/report/service_report_priority_provider.dart'; import 'package:test_sa/controllers/providers/api/status_drop_down/service_reqest/service_request_first_action_provider.dart'; import 'package:test_sa/controllers/providers/api/status_drop_down/service_reqest/service_request_loan_availability_provider.dart'; @@ -49,6 +50,7 @@ import 'package:test_sa/views/widgets/equipment/single_device_picker.dart'; import 'controllers/providers/api/parts_provider.dart'; import 'controllers/providers/api/preventive_maintenance_visits_provider.dart'; import 'controllers/providers/api/status_drop_down/pentry/pentry_status_provider.dart'; +import 'controllers/providers/api/status_drop_down/report/service_report_fault_description_provider.dart'; import 'controllers/providers/api/status_drop_down/report/service_report_last_calls_provider.dart'; import 'controllers/providers/api/status_drop_down/report/service_report_reasons_provider.dart'; import 'controllers/providers/api/status_drop_down/report/service_report_repair_location_provider.dart'; @@ -95,6 +97,7 @@ class MyApp extends StatelessWidget { ChangeNotifierProvider(create: (_) => PartsProvider()), ChangeNotifierProvider(create: (_) => ServiceReportReasonsProvider()), ChangeNotifierProvider(create: (_) => ServiceReportStatusProvider()), + ChangeNotifierProvider(create: (_) => ServiceReportEquipmentStatusProvider()), ChangeNotifierProvider(create: (_) => ServiceReportTypesProvider()), ChangeNotifierProvider(create: (_) => ServiceStatusProvider()), ChangeNotifierProvider(create: (_) => ServiceReportLastCallsProvider()), @@ -117,6 +120,7 @@ class MyApp extends StatelessWidget { ChangeNotifierProvider(create: (_) => ServiceLoanAvailabilityProvider()), ChangeNotifierProvider(create: (_) => ServiceFirstActionProvider()), ChangeNotifierProvider(create: (_) => ServiceReportRepairLocationProvider()), + ChangeNotifierProvider(create: (_) => ServiceRequestFaultDescriptionProvider()), ], child: GestureDetector( onTap: () { diff --git a/lib/models/call_request_for_work_order_model.dart b/lib/models/call_request_for_work_order_model.dart new file mode 100644 index 00000000..dd0ac5a3 --- /dev/null +++ b/lib/models/call_request_for_work_order_model.dart @@ -0,0 +1,541 @@ +class CallRequestForWorkOrder { + int id; + String callNo; + Asset asset; + AssignedEmployee assignedEmployee; + List callSiteContactPerson; + Status status; + Status callLastSituation; + Status defectType; + Status firstAction; + int assetType; + + CallRequestForWorkOrder( + {this.id, this.callNo, this.asset, this.assignedEmployee, this.callSiteContactPerson, this.status, this.callLastSituation, this.defectType, this.firstAction, this.assetType}); + + CallRequestForWorkOrder.fromJson(Map json) { + id = json['id']; + callNo = json['callNo']; + asset = json['asset'] != null ? new Asset.fromJson(json['asset']) : null; + assignedEmployee = json['assignedEmployee'] != null ? new AssignedEmployee.fromJson(json['assignedEmployee']) : null; + if (json['callSiteContactPerson'] != null) { + callSiteContactPerson = []; + json['callSiteContactPerson'].forEach((v) { + callSiteContactPerson.add(new CallSiteContactPerson.fromJson(v)); + }); + } + status = json['status'] != null ? new Status.fromJson(json['status']) : null; + callLastSituation = json['callLastSituation'] != null ? new Status.fromJson(json['callLastSituation']) : null; + defectType = json['defectType'] != null ? new Status.fromJson(json['defectType']) : null; + firstAction = json['firstAction'] != null ? new Status.fromJson(json['firstAction']) : null; + assetType = json['assetType']; + } + + Map toJson() { + final Map data = new Map(); + data['id'] = this.id; + data['callNo'] = this.callNo; + if (this.asset != null) { + data['asset'] = this.asset.toJson(); + } + if (this.assignedEmployee != null) { + data['assignedEmployee'] = this.assignedEmployee.toJson(); + } + if (this.callSiteContactPerson != null) { + data['callSiteContactPerson'] = this.callSiteContactPerson.map((v) => v.toJson()).toList(); + } + if (this.status != null) { + data['status'] = this.status.toJson(); + } + if (this.callLastSituation != null) { + data['callLastSituation'] = this.callLastSituation.toJson(); + } + if (this.defectType != null) { + data['defectType'] = this.defectType.toJson(); + } + if (this.firstAction != null) { + data['firstAction'] = this.firstAction.toJson(); + } + data['assetType'] = this.assetType; + return data; + } +} + +class Asset { + int id; + String assetSerialNo; + String systemID; + String assetNumber; + ModelDefinition modelDefinition; + String supplier; + String ipAddress; + String macAddress; + String portNumber; + String assetReplace; + String oldAsset; + bool isParent; + String parentAsset; + int assetType; + Site site; + Building building; + String floor; + Department department; + String room; + String testsDay; + String purchasingPrice; + String nbv; + String currency; + String poNo; + String invoiceNumber; + String invoiceDate; + String replacementDate; + Department originDepartment; + Site originSite; + String budgetYear; + String lastPOPrice; + String commissioningStatus; + String productionDate; + String edd; + String technicalInspectionDate; + String deliveryInspectionDate; + String endUserAcceptanceDate; + String receivingCommittee; + String siteWarrantyMonths; + String extendedWarrantyMonths; + String remainderWarrantyMonths; + String eomWarrantyMonthsNo; + String warrantyValue; + String warrantyEndDate; + String warrantyContractConditions; + List technicalGuidanceBooks; + String comment; + String tagCode; + + Asset( + {this.id, + this.assetSerialNo, + this.systemID, + this.assetNumber, + this.modelDefinition, + this.supplier, + this.ipAddress, + this.macAddress, + this.portNumber, + this.assetReplace, + this.oldAsset, + this.isParent, + this.parentAsset, + this.assetType, + this.site, + this.building, + this.floor, + this.department, + this.room, + this.testsDay, + this.purchasingPrice, + this.nbv, + this.currency, + this.poNo, + this.invoiceNumber, + this.invoiceDate, + this.replacementDate, + this.originDepartment, + this.originSite, + this.budgetYear, + this.lastPOPrice, + this.commissioningStatus, + this.productionDate, + this.edd, + this.technicalInspectionDate, + this.deliveryInspectionDate, + this.endUserAcceptanceDate, + this.receivingCommittee, + this.siteWarrantyMonths, + this.extendedWarrantyMonths, + this.remainderWarrantyMonths, + this.eomWarrantyMonthsNo, + this.warrantyValue, + this.warrantyEndDate, + this.warrantyContractConditions, + this.technicalGuidanceBooks, + this.comment, + this.tagCode}); + + Asset.fromJson(Map json) { + id = json['id']; + assetSerialNo = json['assetSerialNo']; + systemID = json['systemID']; + assetNumber = json['assetNumber']; + modelDefinition = json['modelDefinition'] != null ? new ModelDefinition.fromJson(json['modelDefinition']) : null; + supplier = json['supplier']; + ipAddress = json['ipAddress']; + macAddress = json['macAddress']; + portNumber = json['portNumber']; + assetReplace = json['assetReplace']; + oldAsset = json['oldAsset']; + isParent = json['isParent']; + parentAsset = json['parentAsset']; + assetType = json['assetType']; + site = json['site'] != null ? new Site.fromJson(json['site']) : null; + building = json['building']; + floor = json['floor']; + department = json['department'] != null ? new Department.fromJson(json['department']) : null; + room = json['room']; + testsDay = json['testsDay']; + purchasingPrice = json['purchasingPrice']; + nbv = json['nbv']; + currency = json['currency']; + poNo = json['poNo']; + invoiceNumber = json['invoiceNumber']; + invoiceDate = json['invoiceDate']; + replacementDate = json['replacementDate']; + originDepartment = json['originDepartment'] != null ? new Department.fromJson(json['originDepartment']) : null; + originSite = json['originSite'] != null ? new Site.fromJson(json['originSite']) : null; + budgetYear = json['budgetYear']; + lastPOPrice = json['lastPOPrice']; + commissioningStatus = json['commissioningStatus']; + productionDate = json['productionDate']; + edd = json['edd']; + technicalInspectionDate = json['technicalInspectionDate']; + deliveryInspectionDate = json['deliveryInspectionDate']; + endUserAcceptanceDate = json['endUserAcceptanceDate']; + receivingCommittee = json['receivingCommittee']; + siteWarrantyMonths = json['siteWarrantyMonths']; + extendedWarrantyMonths = json['extendedWarrantyMonths']; + remainderWarrantyMonths = json['remainderWarrantyMonths']; + eomWarrantyMonthsNo = json['eomWarrantyMonthsNo']; + warrantyValue = json['warrantyValue']; + warrantyEndDate = json['warrantyEndDate']; + warrantyContractConditions = json['warrantyContractConditions']; + if (json['technicalGuidanceBooks'] != null) { + technicalGuidanceBooks = []; + json['technicalGuidanceBooks'].forEach((v) { + //technicalGuidanceBooks.add(new Null.fromJson(v)); + }); + } + comment = json['comment']; + tagCode = json['tagCode']; + } + + Map toJson() { + final Map data = new Map(); + data['id'] = this.id; + data['assetSerialNo'] = this.assetSerialNo; + data['systemID'] = this.systemID; + data['assetNumber'] = this.assetNumber; + if (this.modelDefinition != null) { + data['modelDefinition'] = this.modelDefinition.toJson(); + } + data['supplier'] = this.supplier; + data['ipAddress'] = this.ipAddress; + data['macAddress'] = this.macAddress; + data['portNumber'] = this.portNumber; + data['assetReplace'] = this.assetReplace; + data['oldAsset'] = this.oldAsset; + data['isParent'] = this.isParent; + data['parentAsset'] = this.parentAsset; + data['assetType'] = this.assetType; + if (this.site != null) { + data['site'] = this.site.toJson(); + } + data['building'] = this.building; + data['floor'] = this.floor; + if (this.department != null) { + data['department'] = this.department.toJson(); + } + data['room'] = this.room; + data['testsDay'] = this.testsDay; + data['purchasingPrice'] = this.purchasingPrice; + data['nbv'] = this.nbv; + data['currency'] = this.currency; + data['poNo'] = this.poNo; + data['invoiceNumber'] = this.invoiceNumber; + data['invoiceDate'] = this.invoiceDate; + data['replacementDate'] = this.replacementDate; + if (this.originDepartment != null) { + data['originDepartment'] = this.originDepartment.toJson(); + } + if (this.originSite != null) { + data['originSite'] = this.originSite.toJson(); + } + data['budgetYear'] = this.budgetYear; + data['lastPOPrice'] = this.lastPOPrice; + data['commissioningStatus'] = this.commissioningStatus; + data['productionDate'] = this.productionDate; + data['edd'] = this.edd; + data['technicalInspectionDate'] = this.technicalInspectionDate; + data['deliveryInspectionDate'] = this.deliveryInspectionDate; + data['endUserAcceptanceDate'] = this.endUserAcceptanceDate; + data['receivingCommittee'] = this.receivingCommittee; + data['siteWarrantyMonths'] = this.siteWarrantyMonths; + data['extendedWarrantyMonths'] = this.extendedWarrantyMonths; + data['remainderWarrantyMonths'] = this.remainderWarrantyMonths; + data['eomWarrantyMonthsNo'] = this.eomWarrantyMonthsNo; + data['warrantyValue'] = this.warrantyValue; + data['warrantyEndDate'] = this.warrantyEndDate; + data['warrantyContractConditions'] = this.warrantyContractConditions; + if (this.technicalGuidanceBooks != null) { + data['technicalGuidanceBooks'] = this.technicalGuidanceBooks.map((v) => v.toJson()).toList(); + } + data['comment'] = this.comment; + data['tagCode'] = this.tagCode; + return data; + } +} + +class ModelDefinition { + int id; + String assetName; + String modelDefCode; + String modelName; + int manufacturerId; + String manufacturerName; + String supplierName; + String replacementDate; + int lifeSpan; + List modelDefRelatedDefects; + List suppliers; + + ModelDefinition( + {this.id, + this.assetName, + this.modelDefCode, + this.modelName, + this.manufacturerId, + this.manufacturerName, + this.supplierName, + this.replacementDate, + this.lifeSpan, + this.modelDefRelatedDefects, + this.suppliers}); + + ModelDefinition.fromJson(Map json) { + id = json['id']; + assetName = json['assetName']; + modelDefCode = json['modelDefCode']; + modelName = json['modelName']; + manufacturerId = json['manufacturerId']; + manufacturerName = json['manufacturerName']; + supplierName = json['supplierName']; + replacementDate = json['replacementDate']; + lifeSpan = json['lifeSpan']; + if (json['modelDefRelatedDefects'] != null) { + modelDefRelatedDefects = []; + json['modelDefRelatedDefects'].forEach((v) { + modelDefRelatedDefects.add(new ModelDefRelatedDefects.fromJson(v)); + }); + } + if (json['suppliers'] != null) { + suppliers = []; + json['suppliers'].forEach((v) { + // suppliers!.add(new Null.fromJson(v)); + }); + } + } + + Map toJson() { + final Map data = new Map(); + data['id'] = this.id; + data['assetName'] = this.assetName; + data['modelDefCode'] = this.modelDefCode; + data['modelName'] = this.modelName; + data['manufacturerId'] = this.manufacturerId; + data['manufacturerName'] = this.manufacturerName; + data['supplierName'] = this.supplierName; + data['replacementDate'] = this.replacementDate; + data['lifeSpan'] = this.lifeSpan; + if (this.modelDefRelatedDefects != null) { + data['modelDefRelatedDefects'] = this.modelDefRelatedDefects.map((v) => v.toJson()).toList(); + } + if (this.suppliers != null) { + data['suppliers'] = this.suppliers.map((v) => v.toJson()).toList(); + } + return data; + } +} + +class ModelDefRelatedDefects { + int id; + String defectName; + String workPerformed; + String estimatedTime; + + ModelDefRelatedDefects({this.id, this.defectName, this.workPerformed, this.estimatedTime}); + + ModelDefRelatedDefects.fromJson(Map json) { + id = json['id']; + defectName = json['defectName']; + workPerformed = json['workPerformed']; + estimatedTime = json['estimatedTime']; + } + + Map toJson() { + final Map data = new Map(); + data['id'] = this.id; + data['defectName'] = this.defectName; + data['workPerformed'] = this.workPerformed; + data['estimatedTime'] = this.estimatedTime; + return data; + } +} + +class Site { + int id; + int customerCode; + String custName; + List buildings; + + Site({this.id, this.customerCode, this.custName, this.buildings}); + + Site.fromJson(Map json) { + id = json['id']; + customerCode = json['customerCode']; + custName = json['custName']; + if (json['buildings'] != null) { + buildings = []; + json['buildings'].forEach((v) { + // buildings!.add(new Null.fromJson(v)); + }); + } + } + + Map toJson() { + final Map data = new Map(); + data['id'] = this.id; + data['customerCode'] = this.customerCode; + data['custName'] = this.custName; + if (this.buildings != null) { + data['buildings'] = this.buildings.map((v) => v.toJson()).toList(); + } + return data; + } +} + +class Department { + int id; + String departmentName; + String departmentCode; + String ntCode; + + Department({this.id, this.departmentName, this.departmentCode, this.ntCode}); + + Department.fromJson(Map json) { + id = json['id']; + departmentName = json['departmentName']; + departmentCode = json['departmentCode']; + ntCode = json['ntCode']; + } + + Map toJson() { + final Map data = new Map(); + data['id'] = this.id; + data['departmentName'] = this.departmentName; + data['departmentCode'] = this.departmentCode; + data['ntCode'] = this.ntCode; + return data; + } +} + +class AssignedEmployee { + String id; + String name; + + AssignedEmployee({this.id, this.name}); + + AssignedEmployee.fromJson(Map json) { + id = json['id']; + name = json['name']; + } + + Map toJson() { + final Map data = new Map(); + data['id'] = this.id; + data['name'] = this.name; + return data; + } +} + +class CallSiteContactPerson { + int id; + Null employeeCode; + String name; + String telephone; + String job; + String email; + Null land; + String contactUserId; + + CallSiteContactPerson({this.id, this.employeeCode, this.name, this.telephone, this.job, this.email, this.land, this.contactUserId}); + + CallSiteContactPerson.fromJson(Map json) { + id = json['id']; + employeeCode = json['employeeCode']; + name = json['name']; + telephone = json['telephone']; + job = json['job']; + email = json['email']; + land = json['land']; + contactUserId = json['contactUserId']; + } + + Map toJson() { + final Map data = new Map(); + data['id'] = this.id; + data['employeeCode'] = this.employeeCode; + data['name'] = this.name; + data['telephone'] = this.telephone; + data['job'] = this.job; + data['email'] = this.email; + data['land'] = this.land; + data['contactUserId'] = this.contactUserId; + return data; + } +} + +class Status { + int id; + String name; + int value; + + Status({this.id, this.name, this.value}); + + Status.fromJson(Map json) { + id = json['id']; + name = json['name']; + value = json['value']; + } + + Map toJson() { + final Map data = new Map(); + data['id'] = this.id; + data['name'] = this.name; + data['value'] = this.value; + return data; + } +} + +class Building { + int id; + String name; + int value; + var floor; + + Building({this.id, this.name, this.value,this.floor}); + + Building.fromJson(Map json) { + id = json['id']; + name = json['name']; + value = json['value']; + floor = json['floor']; + } + + Map toJson() { + final Map data = new Map(); + data['id'] = this.id; + data['name'] = this.name; + data['value'] = this.value; + data['floor'] = this.floor; + return data; + } +} + diff --git a/lib/models/fault_description.dart b/lib/models/fault_description.dart new file mode 100644 index 00000000..ecc99f7f --- /dev/null +++ b/lib/models/fault_description.dart @@ -0,0 +1,36 @@ +class FaultDescription { + FaultDescription({ + this.id, + this.defectName, + this.workPerformed, + this.estimatedTime,}); + + FaultDescription.fromJson(dynamic json) { + id = json['id']; + defectName = json['defectName']; + workPerformed = json['workPerformed']; + estimatedTime = json['estimatedTime']; + } + num id; + String defectName; + String workPerformed; + String estimatedTime; +FaultDescription copyWith({ num id, + String defectName, + String workPerformed, + String estimatedTime, +}) => FaultDescription( id: id ?? this.id, + defectName: defectName ?? this.defectName, + workPerformed: workPerformed ?? this.workPerformed, + estimatedTime: estimatedTime ?? this.estimatedTime, +); + Map toJson() { + final map = {}; + map['id'] = id; + map['defectName'] = defectName; + map['workPerformed'] = workPerformed; + map['estimatedTime'] = estimatedTime; + return map; + } + +} \ No newline at end of file diff --git a/lib/models/service_report.dart b/lib/models/service_report.dart index 28b117d1..3b681d2a 100644 --- a/lib/models/service_report.dart +++ b/lib/models/service_report.dart @@ -3,6 +3,7 @@ import 'dart:typed_data'; import 'package:test_sa/controllers/api_routes/urls.dart'; import 'package:test_sa/models/device/device.dart'; import 'package:test_sa/models/engineer.dart'; +import 'package:test_sa/models/fault_description.dart'; import 'package:test_sa/models/lookup.dart'; import 'package:test_sa/models/part.dart'; import 'package:test_sa/models/service_request/service_request.dart'; @@ -18,7 +19,7 @@ class ServiceReport { Lookup callLastSituation; Lookup repairLocation; Engineer engineer; - Lookup status; + Lookup equipmentStatus; Lookup type; Lookup reason; int faultDescriptionId; @@ -40,46 +41,49 @@ class ServiceReport { Uint8List localNurseSignature; Uint8List localEngineerSignature; int travelingExpense; + String reviewComment; + FaultDescription faultDescription; - ServiceReport({ - this.id, - this.visitDate, - this.endDate, - this.assetType, - this.status, - this.type, - this.faultDescriptionId, - //this.workHours, - this.travelingHours, - this.parts, - this.engineer, - this.workPreformed, - this.reason, - this.operatingHours, - this.callLastSituation, - this.jobSheetNumber, - this.image, - this.device, - this.invoiceCode, - this.invoiceNumber, - this.quantity = "1", - this.timer, - this.signatureNurse, - this.signatureEngineer, - this.localNurseSignature, - this.localEngineerSignature, - this.comment, - this.repairLocation, - this.travelingExpense, - this.startDate, - }); + ServiceReport( + {this.id, + this.visitDate, + this.endDate, + this.assetType, + this.equipmentStatus, + this.type, + this.faultDescriptionId, + //this.workHours, + this.travelingHours, + this.parts, + this.engineer, + this.workPreformed, + this.reason, + this.operatingHours, + this.callLastSituation, + this.jobSheetNumber, + this.image, + this.device, + this.invoiceCode, + this.invoiceNumber, + this.quantity = "1", + this.timer, + this.signatureNurse, + this.signatureEngineer, + this.localNurseSignature, + this.localEngineerSignature, + this.comment, + this.repairLocation, + this.travelingExpense, + this.startDate, + this.reviewComment, + this.faultDescription}); Map toMap(ServiceRequest request) { Map _map = {}; if (id != null) _map["id"] = id; if (visitDate != null) _map["visitDate"] = visitDate.toIso8601String(); //if(serviceType != null) _map["service_type"] = serviceType.id.toString(); - if (status != null) _map["status"] = status?.toMap(); + if (equipmentStatus != null) _map["status"] = equipmentStatus?.toMap(); if (type != null) _map["typeOfWO"] = type?.toMap(); if (assetType != null) _map["TypeOfWO"] = assetType?.toMap(); //if(faultDescriptionId != null && faultDescriptionId.isNotEmpty) _map["fault_description"] = faultDescriptionId; @@ -96,6 +100,10 @@ class ServiceReport { // "workPerformed":workPreformed // }; // } + if (travelingHours != null) _map["traveling_hours"] = travelingHours; + if (workPreformed != null && workPreformed.isNotEmpty) { + _map["faultDescription"] = faultDescription.toJson(); + } if (jobSheetNumber != null && jobSheetNumber.isNotEmpty) _map["job_sheet_no"] = jobSheetNumber; if (parts != null && parts.isNotEmpty) { _map["sparePartsWorkOrders"] = parts.map((e) => e.toJson()).toList(); @@ -129,15 +137,16 @@ class ServiceReport { _map["startofWorkTime"] = startDate; _map["endofWorkTime"] = endDate; _map["workingHours"] = endDate?.difference(startDate)?.inHours ?? 0; + _map["reviewComment"] = reviewComment; return _map; } bool validate() { if (visitDate == null) return false; //if(serviceType == null) return false; - if (status == null) return false; - if (type == null && assetType == null) return false; - if (engineer == null) return false; + if (equipmentStatus == null) return false; + //if (type == null && assetType == null) return false; + // if (engineer == null) return false; if (callLastSituation == null) return false; if (callLastSituation?.value == 12) { // if(invoiceCode != null || invoiceCode?.isEmpty == true) return false; @@ -145,7 +154,7 @@ class ServiceReport { } if (parts == null) return false; //if(endDate == null) return false; - //if(reason == null) return false; + if (reason == null) return false; //todo uncoment this line //if((device?.id == null || device.id.isEmpty) && type?.id != 1) return false; //if(quantity == null || quantity.isEmpty) return false; @@ -166,9 +175,9 @@ class ServiceReport { assetType: Lookup.fromJson(parsedJson["assetType"]), callLastSituation: Lookup.fromJson(parsedJson["calllastSituation"]), reason: Lookup.fromJson(parsedJson["reason"]), - status: Lookup.fromJson(parsedJson["status"]), + equipmentStatus: Lookup.fromJson(parsedJson["status"]), type: Lookup.fromJson(parsedJson["typeOfWO"]), - //faultDescriptionId: parsedJson["fault_description"], + faultDescriptionId: parsedJson["fault_description"], endDate: DateTime.tryParse(parsedJson["endofWorkTime"]), //invoiceCode: parsedJson["invoice_code"], //invoiceNumber: parsedJson["invoice_no"], @@ -186,6 +195,7 @@ class ServiceReport { device: Device.fromJson(parsedJson["callRequest"]["asset"]), signatureNurse: URLs.getFileUrl(parsedJson["nurseSignature"]), signatureEngineer: URLs.getFileUrl(parsedJson["engSignature"]), + reviewComment: parsedJson['reviewComment'], ); } diff --git a/lib/models/service_request/search_work_order.dart b/lib/models/service_request/search_work_order.dart index a130fee0..713e9125 100644 --- a/lib/models/service_request/search_work_order.dart +++ b/lib/models/service_request/search_work_order.dart @@ -237,7 +237,7 @@ class Asset { String oldAsset; String isParent; String parentAsset; - String assetType; + int assetType; Site site; String building; String floor; diff --git a/lib/views/pages/user/requests/create_request.dart b/lib/views/pages/user/requests/create_request.dart index 3d2b6de8..91b87bed 100644 --- a/lib/views/pages/user/requests/create_request.dart +++ b/lib/views/pages/user/requests/create_request.dart @@ -14,7 +14,6 @@ import 'package:test_sa/controllers/validator/validator.dart'; import 'package:test_sa/extensions/int_extensions.dart'; import 'package:test_sa/extensions/widget_extensions.dart'; import 'package:test_sa/models/device/device.dart'; -import 'package:test_sa/models/lookup.dart'; import 'package:test_sa/models/service_request/service_request.dart'; import 'package:test_sa/models/subtitle.dart'; import 'package:test_sa/views/app_style/colors.dart'; @@ -39,7 +38,6 @@ import '../../../widgets/status/service_request/service_request_loan_availabilit class CreateRequestPage extends StatefulWidget { static const String id = "/create-request"; final ServiceRequest serviceRequest; - const CreateRequestPage({this.serviceRequest, Key key}) : super(key: key); @override @@ -54,6 +52,7 @@ class CreateRequestPageState extends State { ServiceRequest _serviceRequest; final List _deviceImages = []; bool _isLoading = false; + bool _showDatePicker = false; Device _device; Subtitle _subtitle; final GlobalKey _formKey = GlobalKey(); @@ -69,6 +68,7 @@ class CreateRequestPageState extends State { _serviceRequest = widget.serviceRequest; _device = _serviceRequest.device; _deviceImages.addAll(_serviceRequest.devicePhotos.map((e) => File(e)).toList()); + _showDatePicker = _serviceRequest.firstAction != null && _serviceRequest.firstAction.name == "Need a visit"; } else { _serviceRequest = ServiceRequest(); } @@ -216,11 +216,12 @@ class CreateRequestPageState extends State { onSelect: (status) { _dateTime = null; _serviceRequest.firstAction = status; + _showDatePicker = _serviceRequest.firstAction != null && _serviceRequest.firstAction.name == "Need a visit"; _serviceRequestsProvider.notifyListeners(); }, ), - if (_serviceRequest.firstAction != null) 12.height, - if (_serviceRequest?.firstAction?.id == 405) + if (_showDatePicker) 12.height, + if (_showDatePicker) ADatePicker( date: _dateTime, from: DateTime.now(), @@ -270,7 +271,7 @@ class CreateRequestPageState extends State { initialValue: _serviceRequest.callComments, hintText: _subtitle.maintenanceIssue, prefixIconData: FontAwesomeIcons.triangleExclamation, - style: Theme.of(context).textTheme.headline6, + style: Theme.of(context).textTheme.titleLarge, textInputType: TextInputType.multiline, validator: (value) => Validator.hasValue(value) ? null : _subtitle.maintenanceIssueRequired, onSaved: (value) { @@ -281,6 +282,18 @@ class CreateRequestPageState extends State { RecordSound(onRecord: (audio) { _serviceRequest.audio = audio; }), + 12.height, + if (widget.serviceRequest != null) + ATextFormField( + controller: _commentController, + initialValue: _serviceRequest.comments, + hintText: _subtitle.comment, + style: Theme.of(context).textTheme.titleMedium, + textInputType: TextInputType.multiline, + onSaved: (value) { + _serviceRequest.comments = value; + }, + ), ], ).paddingOnly(left: 20, right: 20), Padding( diff --git a/lib/views/pages/user/requests/report/create_service_report.dart b/lib/views/pages/user/requests/report/create_service_report.dart index 84d22d83..ad6647e6 100644 --- a/lib/views/pages/user/requests/report/create_service_report.dart +++ b/lib/views/pages/user/requests/report/create_service_report.dart @@ -11,6 +11,8 @@ import 'package:test_sa/controllers/providers/api/status_drop_down/report/servic import 'package:test_sa/controllers/providers/api/user_provider.dart'; import 'package:test_sa/controllers/providers/settings/setting_provider.dart'; import 'package:test_sa/controllers/validator/validator.dart'; +import 'package:test_sa/models/call_request_for_work_order_model.dart'; +import 'package:test_sa/models/engineer.dart'; import 'package:test_sa/models/part.dart'; import 'package:test_sa/models/service_report.dart'; import 'package:test_sa/models/service_request/service_request.dart'; @@ -29,14 +31,15 @@ import 'package:test_sa/views/widgets/loaders/loading_manager.dart'; import 'package:test_sa/views/widgets/parts/auto_complete_parts_field.dart'; import 'package:test_sa/views/widgets/parts/part_item.dart'; import 'package:test_sa/views/widgets/status/employee/engineers_mune.dart'; +import 'package:test_sa/views/widgets/status/report/service_report_equipment_status.dart'; import 'package:test_sa/views/widgets/status/report/service_report_last_call.dart'; import 'package:test_sa/views/widgets/status/report/service_report_reasons.dart'; import 'package:test_sa/views/widgets/status/report/service_report_status.dart'; -import 'package:test_sa/views/widgets/status/report/service_status.dart'; -import 'package:test_sa/views/widgets/timer/app_timer.dart'; import 'package:test_sa/views/widgets/titles/app_sub_title.dart'; +import '../../../../../controllers/providers/api/status_drop_down/report/service_types_provider.dart'; import '../../../../widgets/speech_to_text/speech_to_text.dart'; +import '../../../../widgets/status/report/service_report_fault_description.dart'; import '../../../../widgets/status/report/service_report_repair_location.dart'; class CreateServiceReport extends StatefulWidget { @@ -53,26 +56,29 @@ class _CreateServiceReportState extends State with TickerPr UserProvider _userProvider; SettingProvider _settingProvider; ServiceRequestsProvider _serviceRequestsProvider; - + ServiceStatusProvider _assetTypeProvider; bool _validate = false; ServiceReport _serviceReport; bool _isLoading = false; + bool _showCommentField = false; Subtitle _subtitle; File _image; final GlobalKey _formKey = GlobalKey(); final GlobalKey _scaffoldKey = GlobalKey(); - TextEditingController _faultController = TextEditingController(); - TextEditingController _workPreformedController = TextEditingController(); + final TextEditingController _faultController = TextEditingController(); + final TextEditingController _workPreformedController = TextEditingController(); @override void initState() { _serviceReport = ServiceReport( - visitDate: DateTime.now(), - //type: const Lookup(value: 2), - device: widget.request.device, - parts: []); + visitDate: DateTime.now(), + //type: const Lookup(value: 2), + device: widget.request.device, + parts: [], + ); super.initState(); + // _isLoading = true; } @override @@ -82,11 +88,31 @@ class _CreateServiceReportState extends State with TickerPr super.dispose(); } + CallRequestForWorkOrder _callRequestForWorkOrder; + + void getRequestForWorkOrder() async { + _isLoading = true; + setState(() {}); + _callRequestForWorkOrder = await _serviceRequestsProvider.getCallRequestForWorkOrder(callId: widget.request.id); + _serviceReport.engineer = Engineer.fromJson(_callRequestForWorkOrder.assignedEmployee?.toJson()); + await _assetTypeProvider.getTypes(user: _userProvider.user, host: _settingProvider.host); + _isLoading = false; + setState(() {}); + } + @override Widget build(BuildContext context) { _userProvider = Provider.of(context); _settingProvider = Provider.of(context); _serviceRequestsProvider = Provider.of(context); + _assetTypeProvider = Provider.of(context); + if (_callRequestForWorkOrder == null) { + getRequestForWorkOrder(); + } + _serviceReport.assetType = _assetTypeProvider.statuses?.firstWhere( + (element) => element.value == _callRequestForWorkOrder?.assetType, + orElse: () => null, + ); _subtitle = AppLocalization.of(context).subtitle; return Scaffold( key: _scaffoldKey, @@ -169,6 +195,7 @@ class _CreateServiceReportState extends State with TickerPr ]), child: Column( mainAxisSize: MainAxisSize.min, + crossAxisAlignment: CrossAxisAlignment.start, children: [ // Report type and Reasons Row( @@ -267,12 +294,32 @@ class _CreateServiceReportState extends State with TickerPr const SizedBox( height: 4, ), - ServiceAssetTypeMenu( - initialValue: _serviceReport.assetType, - onSelect: (status) { - _serviceReport.assetType = status; + + LoadingManager( + isLoading: _assetTypeProvider.isLoading, + isFailedLoading: _assetTypeProvider.statuses == null, + stateCode: _assetTypeProvider.stateCode, + onRefresh: () async { + _assetTypeProvider.reset(); + await _assetTypeProvider.getTypes(user: _userProvider.user, host: _settingProvider.host); + _serviceReport?.assetType = _assetTypeProvider.statuses?.firstWhere( + (element) => element.value == _callRequestForWorkOrder.assetType, + orElse: () => null, + ); }, + child: ATextFormField( + initialValue: _serviceReport?.assetType?.name ?? "NULL", + textAlign: TextAlign.center, + enable: false, + style: Theme.of(context).textTheme.titleMedium, + ), ), + // ServiceAssetTypeMenu( + // initialValue: _serviceReport.assetType, + // onSelect: (status) { + // _serviceReport.assetType = status; + // }, + // ), const SizedBox( height: 8, ), @@ -284,8 +331,9 @@ class _CreateServiceReportState extends State with TickerPr child: Column( crossAxisAlignment: CrossAxisAlignment.start, children: [ - ASubTitle(_subtitle.reportStatus), - _validate && _serviceReport.status == null + // ASubTitle(_subtitle.reportStatus), + ASubTitle("Equipment Status"), + _validate && _serviceReport.equipmentStatus == null ? ASubTitle( _subtitle.requiredWord, color: Colors.red, @@ -294,13 +342,20 @@ class _CreateServiceReportState extends State with TickerPr const SizedBox( height: 4, ), - ServiceReportStatusMenu( + // ServiceReportStatusMenu( + // report: _serviceReport, + // request: widget.request, + // onSelect: (status) { + // _serviceReport.status = status; + // }, + // ), + ServiceReportEquipmentStatusMenu( report: _serviceReport, request: widget.request, onSelect: (status) { - _serviceReport.status = status; + _serviceReport.equipmentStatus = status; }, - ), + ) ], ), ), @@ -345,6 +400,21 @@ class _CreateServiceReportState extends State with TickerPr ), ], ), + if (_showCommentField) + const SizedBox( + height: 8, + ), + if (_showCommentField) + ATextFormField( + initialValue: _serviceReport?.reviewComment, + hintText: "Review Comment", + textAlign: TextAlign.center, + style: Theme.of(context).textTheme.titleMedium, + textInputType: TextInputType.multiline, + onSaved: (value) { + _serviceReport.reviewComment = value; + }, + ), SizedBox( height: 8 * AppStyle.getScaleFactor(context), ), @@ -393,6 +463,7 @@ class _CreateServiceReportState extends State with TickerPr ), ], ), + const SizedBox(height: 8), ASubTitle(_subtitle.workingHours), const SizedBox(height: 4), ATextFormField( @@ -409,26 +480,57 @@ class _CreateServiceReportState extends State with TickerPr // _serviceReport.workHours = value; }, ), + const SizedBox( + height: 8, + ), + // device sn + Visibility( + visible: widget.request.deviceSerialNumber == null, + child: Column( + crossAxisAlignment: CrossAxisAlignment.start, + children: [ + ASubTitle(_subtitle.deviceSN), + _validate && _serviceReport.device?.id == null + ? ASubTitle( + _subtitle.requiredWord, + color: Colors.red, + ) + : const SizedBox.shrink(), + AutoCompleteDeviceField( + hospitalId: widget.request.hospitalId, + initialValue: _serviceReport.device, + onPick: (id) { + _serviceReport.device.id = id; + }, + ), + const SizedBox( + height: 8, + ), + ], + ), + ), + + // Report status and Service Type + if (_showCommentField) + const SizedBox( + height: 8, + ), + if (_showCommentField) + ATextFormField( + initialValue: _serviceReport?.reviewComment, + hintText: "Review Comment", + textAlign: TextAlign.center, + style: Theme.of(context).textTheme.titleMedium, + textInputType: TextInputType.multiline, + onSaved: (value) { + _serviceReport.reviewComment = value; + }, + ), SizedBox( height: 8 * AppStyle.getScaleFactor(context), ), - const ASubTitle("Assigned Employee"), - const SizedBox(height: 8), - _validate && _serviceReport.engineer == null - ? ASubTitle( - _subtitle.requiredWord, - color: Colors.red, - ) - : const SizedBox.shrink(), - const SizedBox(height: 4), - EngineersMenu( - initialValue: _serviceReport.engineer, - onSelect: (engineer) { - _serviceReport.engineer = engineer; - }, - ), - const SizedBox(height: 8), + // invoice number & code _serviceReport.callLastSituation?.id != 12 ? const SizedBox.shrink() @@ -455,13 +557,17 @@ class _CreateServiceReportState extends State with TickerPr ], ), ), - const SizedBox(width: 8), + const SizedBox( + width: 8, + ), Expanded( child: Column( crossAxisAlignment: CrossAxisAlignment.start, children: [ ASubTitle(_subtitle.invoiceCode), - const SizedBox(height: 4), + const SizedBox( + height: 4, + ), ATextFormField( initialValue: _serviceReport?.invoiceCode, textAlign: TextAlign.center, @@ -478,51 +584,57 @@ class _CreateServiceReportState extends State with TickerPr ], ), const SizedBox(height: 8), - Row( - children: [ - ASubTitle(_subtitle.faultDescription), - Expanded( - child: SizedBox( - height: 32 * AppStyle.getScaleFactor(context), - child: SpeechToTextButton( - controller: _faultController, - mini: true, - ), - ), - ), - ], + ASubTitle(_subtitle.faultDescription), + const SizedBox( + height: 4, ), - const SizedBox(height: 4), - ATextFormField( - initialValue: _serviceReport?.faultDescriptionId?.toString(), - textAlign: TextAlign.center, - controller: _faultController, - style: Theme.of(context).textTheme.titleMedium, - validator: (value) => Validator.hasValue(value) ? null : _subtitle.requiredWord, - textInputType: TextInputType.multiline, - onSaved: (value) { - _serviceReport.faultDescriptionId = int.tryParse(value) ?? 0; + ServiceReportFaultDescription( + requestId: widget.request?.id, + initialValue: _serviceReport.faultDescription, + onSelect: (status) { + _serviceReport.faultDescription = status; + setState(() {}); }, ), - const SizedBox(height: 8), + const SizedBox( + height: 4, + ), + // ATextFormField( + // initialValue: _serviceReport?.faultDescriptionId?.toString(), + // textAlign: TextAlign.center, + // controller: _faultController, + // style: Theme.of(context).textTheme.titleMedium, + // validator: (value) => Validator.hasValue(value) ? null : _subtitle.requiredWord, + // textInputType: TextInputType.multiline, + // onSaved: (value) { + // _serviceReport.faultDescriptionId = int.tryParse(value) ?? 0; + // }, + // ), + const SizedBox( + height: 8, + ), Row( children: [ ASubTitle(_subtitle.workPreformed), - Expanded( - child: SizedBox( - height: 32 * AppStyle.getScaleFactor(context), - child: SpeechToTextButton( - controller: _workPreformedController, - mini: true, - ), - ), - ), + // Expanded( + // child: SizedBox( + // height: 32 * AppStyle.getScaleFactor(context), + // child: SpeechToTextButton( + // controller: _workPreformedController, + // mini: true, + // ), + // ), + // ), ], ), - const SizedBox(height: 4), + const SizedBox( + height: 4, + ), ATextFormField( initialValue: _serviceReport?.workPreformed, textAlign: TextAlign.center, + enable: false, + hintText: _serviceReport.faultDescription?.workPerformed ?? "", controller: _workPreformedController, style: Theme.of(context).textTheme.subtitle1, validator: (value) => Validator.hasValue(value) ? null : _subtitle.requiredWord, @@ -531,7 +643,9 @@ class _CreateServiceReportState extends State with TickerPr _serviceReport.workPreformed = value; }, ), - const SizedBox(height: 8), + const SizedBox( + height: 8, + ), const SizedBox(height: 8), Row( diff --git a/lib/views/pages/user/requests/report/edit_service_report.dart b/lib/views/pages/user/requests/report/edit_service_report.dart index e92f4c7c..848fc4f2 100644 --- a/lib/views/pages/user/requests/report/edit_service_report.dart +++ b/lib/views/pages/user/requests/report/edit_service_report.dart @@ -295,7 +295,7 @@ class _EditServiceReportState extends State with TickerProvid crossAxisAlignment: CrossAxisAlignment.start, children: [ ASubTitle(_subtitle.reportStatus), - _validate && _serviceReport.status == null + _validate && _serviceReport.equipmentStatus == null ? ASubTitle( _subtitle.requiredWord, color: Colors.red, @@ -308,7 +308,7 @@ class _EditServiceReportState extends State with TickerProvid report: _serviceReport, request: widget.request, onSelect: (status) { - _serviceReport.status = status; + _serviceReport.equipmentStatus = status; }, ), ], diff --git a/lib/views/pages/user/visits/pantry/edit_pentry.dart b/lib/views/pages/user/visits/pantry/edit_pentry.dart index d0df5e34..55d356b9 100644 --- a/lib/views/pages/user/visits/pantry/edit_pentry.dart +++ b/lib/views/pages/user/visits/pantry/edit_pentry.dart @@ -73,7 +73,7 @@ class _EditPentryState extends State with SingleTickerProviderStateM if (_pentry.pmKits.isEmpty) _pentry.pmKits.add(PMKit()); if (_pentry.calibrationTools.isEmpty) _pentry.calibrationTools.add(CalibrationTool()); if (_pentry.ppmCheckLists.isEmpty) _pentry.ppmCheckLists.add(PPMCheckList()); - _tabController = TabController(length: 4, vsync: this); + _tabController = TabController(length: 3, vsync: this); super.initState(); } @@ -113,9 +113,9 @@ class _EditPentryState extends State with SingleTickerProviderStateM Tab( text: "PPM Check List", ), - Tab( - text: "Calibration Tools", - ), + // Tab( + // text: "Calibration Tools", + // ), Tab( text: "PK Kits", ), diff --git a/lib/views/widgets/status/report/fault_desc_menu.dart b/lib/views/widgets/status/report/fault_desc_menu.dart new file mode 100644 index 00000000..9250c7dd --- /dev/null +++ b/lib/views/widgets/status/report/fault_desc_menu.dart @@ -0,0 +1,110 @@ +import 'package:flutter/material.dart'; +import 'package:test_sa/models/fault_description.dart'; +import 'package:test_sa/views/app_style/colors.dart'; +import 'package:test_sa/views/app_style/sizing.dart'; + +class FaultDescriptionMenu extends StatefulWidget { + final List statuses; + final FaultDescription initialStatus; + final Function(FaultDescription) onSelect; + + const FaultDescriptionMenu({Key key, this.statuses, this.onSelect, this.initialStatus}) : super(key: key); + + @override + _SingleStatusMenuState createState() => _SingleStatusMenuState(); +} + +class _SingleStatusMenuState extends State { + FaultDescription _selectedStatus; + + @override + void setState(VoidCallback fn) { + if (mounted) super.setState(fn); + } + + @override + void didUpdateWidget(covariant FaultDescriptionMenu oldWidget) { + if (widget.initialStatus != null) { + final result = widget.statuses?.where((element) { + return element == widget.initialStatus; + }); + if (result.isNotEmpty) { + _selectedStatus = result.first; + } else { + _selectedStatus = null; + } + if ((widget.initialStatus?.id ?? "") != (_selectedStatus?.id ?? "")) { + widget.onSelect(_selectedStatus); + } + } else { + _selectedStatus = null; + } + super.didUpdateWidget(oldWidget); + } + + @override + void initState() { + if (widget.initialStatus != null) { + final result = widget.statuses?.where((element) { + return element == widget.initialStatus; + }); + if (result.isNotEmpty) _selectedStatus = result.first; + if (widget.initialStatus.id != _selectedStatus?.id) { + widget.onSelect(_selectedStatus); + } + } + + super.initState(); + } + + @override + Widget build(BuildContext context) { + return Container( + padding: const EdgeInsets.symmetric(horizontal: 16), + decoration: BoxDecoration( + color: AColors.inputFieldBackgroundColor, + border: Border.all( + color: Color(0xffefefef), + ), + borderRadius: BorderRadius.circular(AppStyle.borderRadius * AppStyle.getScaleFactor(context)), + // boxShadow: const [ + // AppStyle.boxShadow + // ] + ), + child: DropdownButton( + value: _selectedStatus, + iconSize: 24, + icon: const Icon(Icons.keyboard_arrow_down_rounded), + elevation: 0, + isExpanded: true, + hint: Text( + "Select", + style: Theme.of(context).textTheme.subtitle1, + ), + style: TextStyle(color: Theme.of(context).primaryColor), + underline: SizedBox.shrink(), + onChanged: (FaultDescription newValue) { + setState(() { + _selectedStatus = newValue; + }); + widget.onSelect(newValue); + }, + items: widget.statuses.map>( + (FaultDescription value) { + return DropdownMenuItem( + value: value, + child: Text( + value.defectName ?? "", + style: Theme.of(context).textTheme.subtitle1.copyWith( + color: Theme.of(context).primaryColor, + fontSize: 11, + //fontWeight: FontWeight.bold + ), + ), + ); + }, + ).toList(), + ), + ); + } +} diff --git a/lib/views/widgets/status/report/service_report_equipment_status.dart b/lib/views/widgets/status/report/service_report_equipment_status.dart new file mode 100644 index 00000000..1a0382b1 --- /dev/null +++ b/lib/views/widgets/status/report/service_report_equipment_status.dart @@ -0,0 +1,76 @@ +import 'dart:math'; + +import 'package:flutter/material.dart'; +import 'package:provider/provider.dart'; +import 'package:test_sa/controllers/providers/api/status_drop_down/report/service_report_last_calls_provider.dart'; +import 'package:test_sa/controllers/providers/api/status_drop_down/report/service_report_equipment_status_provider.dart'; +import 'package:test_sa/controllers/providers/api/user_provider.dart'; +import 'package:test_sa/controllers/providers/settings/setting_provider.dart'; +import 'package:test_sa/models/lookup.dart'; +import 'package:test_sa/models/service_report.dart'; +import 'package:test_sa/models/service_request/service_request.dart'; +import 'package:test_sa/views/widgets/loaders/loading_manager.dart'; +import 'package:test_sa/views/widgets/status/single_status_menu.dart'; + +class ServiceReportEquipmentStatusMenu extends StatefulWidget { + final Function(Lookup) onSelect; + final ServiceReport report; + final ServiceRequest request; + + const ServiceReportEquipmentStatusMenu({Key key, this.onSelect, this.report, this.request}) : super(key: key); + + @override + State createState() => _ServiceReportEquipmentStatusMenuState(); +} + +class _ServiceReportEquipmentStatusMenuState extends State { + bool firstTime = true; + @override + Widget build(BuildContext context) { + SettingProvider settingProvider = Provider.of(context); + UserProvider userProvider = Provider.of(context); + ServiceReportEquipmentStatusProvider menuProvider = Provider.of(context); + ServiceReportLastCallsProvider callsLastSituationsProvider = Provider.of(context); + if (firstTime) { + callsLastSituationsProvider.reset(); + + firstTime = false; + } + return LoadingManager( + isLoading: menuProvider.isLoading == true || callsLastSituationsProvider.isLoading == true, + isFailedLoading: menuProvider.statuses == null || callsLastSituationsProvider.calls == null, + stateCode: menuProvider.stateCode == null || callsLastSituationsProvider.stateCode == null ? null : max(menuProvider.stateCode ?? 0, callsLastSituationsProvider.stateCode ?? 0), + onRefresh: () async { + await callsLastSituationsProvider.getCalls( + user: userProvider.user, + host: settingProvider.host, + serviceStatus: widget.report.equipmentStatus?.id, + typeName: widget.report.type?.name, + id: widget.report.id, + woId: widget.request.id, + ); + if (menuProvider.stateCode == null) { + menuProvider.reset(); + await menuProvider.getTypes(user: userProvider.user, host: settingProvider.host); + setState(() {}); + } + }, + child: SingleStatusMenu( + statuses: menuProvider.statuses, + initialStatus: widget.report.equipmentStatus, + onSelect: (status) { + widget.report.callLastSituation = null; + callsLastSituationsProvider.getCalls( + user: userProvider.user, + host: settingProvider.host, + serviceStatus: status.id, + id: widget.report.id, + woId: widget.request.id, + typeName: widget.report.type?.name, + ); + + widget.onSelect(status); + }, + )); + } +} diff --git a/lib/views/widgets/status/report/service_report_fault_description.dart b/lib/views/widgets/status/report/service_report_fault_description.dart new file mode 100644 index 00000000..544fcbb3 --- /dev/null +++ b/lib/views/widgets/status/report/service_report_fault_description.dart @@ -0,0 +1,43 @@ +import 'package:flutter/material.dart'; +import 'package:provider/provider.dart'; +import 'package:test_sa/controllers/providers/api/status_drop_down/report/service_report_fault_description_provider.dart'; +import 'package:test_sa/controllers/providers/api/user_provider.dart'; +import 'package:test_sa/controllers/providers/settings/setting_provider.dart'; +import 'package:test_sa/models/fault_description.dart'; +import 'package:test_sa/views/widgets/loaders/loading_manager.dart'; +import 'package:test_sa/views/widgets/status/report/fault_desc_menu.dart'; + +import '../../app_text_form_field.dart'; + +class ServiceReportFaultDescription extends StatelessWidget { + final String requestId; + final Function(FaultDescription) onSelect; + final FaultDescription initialValue; + + const ServiceReportFaultDescription({Key key, this.requestId, this.onSelect, this.initialValue}) : super(key: key); + @override + Widget build(BuildContext context) { + SettingProvider settingProvider = Provider.of(context); + UserProvider userProvider = Provider.of(context); + ServiceRequestFaultDescriptionProvider menuProvider = Provider.of(context); + return LoadingManager( + isLoading: menuProvider.isLoading, + isFailedLoading: menuProvider.items == null, + stateCode: menuProvider.stateCode, + onRefresh: () async { + menuProvider.reset(); + await menuProvider.getCallRequestForWorkOrder(user: userProvider.user, host: settingProvider.host, requestId: requestId); + }, + child: (menuProvider.items?.isEmpty ?? true) + ? const ATextFormField( + initialValue: "", + enable: false, + ) + : FaultDescriptionMenu( + initialStatus: initialValue, + statuses: menuProvider.items, + onSelect: onSelect, + ), + ); + } +} diff --git a/lib/views/widgets/status/report/service_report_status.dart b/lib/views/widgets/status/report/service_report_status.dart index 5d3f797a..b21057cb 100644 --- a/lib/views/widgets/status/report/service_report_status.dart +++ b/lib/views/widgets/status/report/service_report_status.dart @@ -44,7 +44,7 @@ class _ServiceReportStatusMenuState extends State { await callsLastSituationsProvider.getCalls( user: userProvider.user, host: settingProvider.host, - serviceStatus: widget.report.status?.id, + serviceStatus: widget.report.equipmentStatus?.id, typeName: widget.report.type?.name, id: widget.report.id, woId: widget.request.id, @@ -57,7 +57,7 @@ class _ServiceReportStatusMenuState extends State { }, child: SingleStatusMenu( statuses: menuProvider.statuses, - initialStatus: widget.report.status, + initialStatus: widget.report.equipmentStatus, onSelect: (status) { widget.report.callLastSituation = null; callsLastSituationsProvider.getCalls(