Previous Business Logic in Work order & sub work order

main_design2.0
zaid.daoud 2 years ago
parent aad9c3dde1
commit 5bf73172f6

@ -1,4 +1,5 @@
import 'dart:convert';
import 'dart:developer';
import 'package:flutter/cupertino.dart';
import 'package:flutter/material.dart';
@ -56,6 +57,7 @@ class ServiceRequestFaultDescriptionProvider extends ChangeNotifier {
// client's request was successfully received
List listJson = json.decode(response.body)["data"]['asset']['modelDefinition']['modelDefRelatedDefects'];
_items = listJson?.map((type) => FaultDescription.fromJson(type))?.toList() ?? [];
log("${_items}Zaid");
}
_loading = false;
notifyListeners();

@ -368,5 +368,7 @@
"mrNumber" : "MR Number",
"vendorEng" : "المهندس المزود",
"vendorName" : "اسم المزود",
"reset" : "اعادة تعيين"
"reset" : "اعادة تعيين",
"solution" : "الحل",
"technicalComment" : "تعليق تقني"
}

@ -371,5 +371,7 @@
"mrNumber" : "MR Number",
"vendorEng" : "Vendor Engineer",
"vendorName" : "Vendor Name",
"reset" : "Reset"
"reset" : "Reset",
"solution" : "Solution",
"technicalComment" : "Technical Comment"
}

@ -67,6 +67,7 @@ import 'package:test_sa/providers/service_request_providers/priority_provider.da
import 'package:test_sa/providers/service_request_providers/request_status_provider.dart';
import 'package:test_sa/providers/service_request_providers/requested_through_provider.dart';
import 'package:test_sa/providers/service_request_providers/type_of_request_provider.dart';
import 'package:test_sa/providers/work_order/asset_types_provider.dart';
import 'package:test_sa/providers/work_order/reason_provider.dart';
import 'package:test_sa/providers/work_order/service_type_provider.dart';
import 'package:test_sa/providers/work_order/vendor_provider.dart';
@ -186,6 +187,7 @@ class MyApp extends StatelessWidget {
ChangeNotifierProvider(create: (_) => FirstActionStatusProvider()),
ChangeNotifierProvider(create: (_) => LoanAvailabilityProvider()),
ChangeNotifierProvider(create: (_) => ReasonProvider()),
ChangeNotifierProvider(create: (_) => AssetTypesProvider()),
ChangeNotifierProvider(create: (_) => ServiceTypeProvider()),
ChangeNotifierProvider(create: (_) => PPMVisitStatusProvider()),
ChangeNotifierProvider(create: (_) => PentryTaskStatusProvider()),

@ -1,14 +1,18 @@
class FaultDescription {
import 'package:test_sa/models/base.dart';
class FaultDescription extends Base {
FaultDescription({
this.id,
this.defectName,
this.workPerformed,
this.estimatedTime,
});
}):super(name : defectName, identifier: id?.toString());
FaultDescription.fromJson(dynamic json) {
id = json['id'];
identifier = id?.toString();
defectName = json['defectName'];
name = defectName;
workPerformed = json['workPerformed'];
estimatedTime = json['estimatedTime'];
}

@ -0,0 +1,36 @@
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 AssetTypesProvider extends LoadingListNotifier<Lookup> {
@override
Future getDate() async {
if (loading == true) return -2;
loading = true;
notifyListeners();
loading = true;
notifyListeners();
try {
Response response = await ApiManager.instance.get(URLs.getAssetTypes);
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;
}
}
}

@ -37,8 +37,11 @@ import '../../../providers/loading_list_notifier.dart';
import '../../../providers/work_order/reason_provider.dart';
import '../../widgets/date_and_time/date_picker.dart';
import '../../widgets/e_signature/e_signature.dart';
import '../../widgets/loaders/loading_manager.dart';
import '../../widgets/status/report/service_report_assistant_employee_menu.dart';
import '../../widgets/status/report/service_report_fault_description.dart';
import '../../widgets/status/report/service_report_last_call.dart';
import '../../widgets/status/report/service_report_repair_location.dart';
import '../../widgets/timer/app_timer.dart';
class CreateSubWorkOrderPage extends StatefulWidget {
@ -60,6 +63,8 @@ class _CreateSubWorkOrderPageState extends State<CreateSubWorkOrderPage> {
bool _showVendorFields = false;
SuppEngineerWorkOrders engineer;
SupplierDetails initialSupplier;
final TextEditingController _workPreformedController =
TextEditingController();
@override
void initState() {
@ -70,11 +75,16 @@ class _CreateSubWorkOrderPageState extends State<CreateSubWorkOrderPage> {
supplier: null,
parentWOId: widget.workOrder.id,
);
_serviceReport = ServiceReport(id: widget.workOrder.id, assetType: widget.workOrder.assetType, equipmentStatus: widget.workOrder.equipmentStatus);
_serviceReport = ServiceReport(
id: widget.workOrder.id,
assetType: widget.workOrder.assetType,
equipmentStatus: widget.workOrder.equipmentStatus);
_isLoading = true;
super.initState();
if (context.mounted) {
Provider.of<ServiceReportAssistantsEmployeeProvider>(context, listen: false).reset();
Provider.of<ServiceReportAssistantsEmployeeProvider>(context,
listen: false)
.reset();
}
}
@ -83,12 +93,18 @@ class _CreateSubWorkOrderPageState extends State<CreateSubWorkOrderPage> {
Future getAssetType() async {
Provider.of<ServiceReportLastCallsProvider>(context, listen: false).reset();
final serviceRequestProvider = Provider.of<ServiceRequestsProvider>(context);
Provider.of<ServiceRequestFaultDescriptionProvider>(context, listen: false).reset();
assetTypesProvider = Provider.of<ServiceStatusProvider>(context, listen: false);
_callRequestForWorkOrder = await serviceRequestProvider.getCallRequestForWorkOrder(callId: widget.workOrder.callRequest.id.toString());
final serviceRequestProvider =
Provider.of<ServiceRequestsProvider>(context);
Provider.of<ServiceRequestFaultDescriptionProvider>(context, listen: false)
.reset();
assetTypesProvider =
Provider.of<ServiceStatusProvider>(context, listen: false);
_callRequestForWorkOrder =
await serviceRequestProvider.getCallRequestForWorkOrder(
callId: widget.workOrder.callRequest.id.toString());
if (_subWorkOrders?.parentWOId != null) {
final subWoDetails = await serviceRequestProvider.getSubWorkOrderDetails(parentId: _subWorkOrders?.parentWOId.toString());
final subWoDetails = await serviceRequestProvider.getSubWorkOrderDetails(
parentId: _subWorkOrders?.parentWOId.toString());
_subWorkOrders.copyDetails(subWoDetails);
_serviceReport.equipmentStatus = subWoDetails.equipmentStatus;
_serviceReport.reason = subWoDetails.reason;
@ -105,13 +121,20 @@ class _CreateSubWorkOrderPageState extends State<CreateSubWorkOrderPage> {
engineer = _subWorkOrders.suppEngineerWorkOrders?.last;
engineer?.id = engineer?.supplierContactId;
}
_subWorkOrders.supplier ??= SupplierDetails(id: _subWorkOrders?.supplier?.id);
_subWorkOrders.supplier ??=
SupplierDetails(id: _subWorkOrders?.supplier?.id);
}
setState(() {
_isLoading = false;
});
}
@override
void dispose() {
_workPreformedController?.dispose();
super.dispose();
}
@override
Widget build(BuildContext context) {
if (_callRequestForWorkOrder == null) {
@ -135,10 +158,15 @@ class _CreateSubWorkOrderPageState extends State<CreateSubWorkOrderPage> {
child: Column(
crossAxisAlignment: CrossAxisAlignment.stretch,
children: [
(widget.workOrder?.callRequest?.asset?.site?.name ?? "").heading5(context),
(widget.workOrder?.callRequest?.asset?.site
?.name ??
"")
.heading5(context),
8.height,
"${context.translation.assetNo}: ${widget.workOrder?.callRequest?.asset?.assetNumber ?? ""}".bodyText(context),
"${context.translation.callId}: ${widget.workOrder?.callRequest?.id}".bodyText(context),
"${context.translation.assetNo}: ${widget.workOrder?.callRequest?.asset?.assetNumber ?? ""}"
.bodyText(context),
"${context.translation.callId}: ${widget.workOrder?.callRequest?.id}"
.bodyText(context),
],
).paddingAll(16),
),
@ -146,9 +174,11 @@ class _CreateSubWorkOrderPageState extends State<CreateSubWorkOrderPage> {
8.height,
ADatePicker(
label: context.translation.returnToService,
date: DateTime.tryParse(_subWorkOrders.visitDate ?? ""),
date: DateTime.tryParse(
_subWorkOrders.visitDate ?? ""),
onDatePicker: (date) {
_subWorkOrders.visitDate = date?.toIso8601String();
_subWorkOrders.visitDate =
date?.toIso8601String();
setState(() {});
},
),
@ -163,6 +193,32 @@ class _CreateSubWorkOrderPageState extends State<CreateSubWorkOrderPage> {
},
),
8.height,
LoadingManager(
isLoading: assetTypesProvider.isLoading,
isFailedLoading:
assetTypesProvider.statuses == null,
stateCode: assetTypesProvider.stateCode,
onRefresh: () async {
assetTypesProvider.reset();
await assetTypesProvider.getTypes();
_serviceReport?.assetType =
assetTypesProvider.statuses?.firstWhere(
(element) =>
element.value ==
_serviceReport.callRequest.assetType,
orElse: () => null,
);
},
child: AppTextFormField(
labelText: context.translation.assetType,
initialValue:
_serviceReport?.assetType?.name ?? "NULL",
textAlign: TextAlign.center,
enable: false,
style: Theme.of(context).textTheme.titleMedium,
),
),
8.height,
SingleItemDropDownMenu<Lookup, ReasonProvider>(
context: context,
title: context.translation.reason,
@ -172,7 +228,8 @@ class _CreateSubWorkOrderPageState extends State<CreateSubWorkOrderPage> {
},
),
8.height,
SingleItemDropDownMenu<Lookup, EquipmentStatusProvider>(
SingleItemDropDownMenu<Lookup,
EquipmentStatusProvider>(
context: context,
title: context.translation.equipmentStatus,
initialValue: _subWorkOrders.equipmentStatus,
@ -188,12 +245,15 @@ class _CreateSubWorkOrderPageState extends State<CreateSubWorkOrderPage> {
onSelect: (status) {
_serviceReport.calllastSituation = status;
if (checkVendorFieldsVisibility(status)) {
_subWorkOrders.supplier ??= SupplierDetails(id: _subWorkOrders?.supplier?.id);
_subWorkOrders.supplier ??= SupplierDetails(
id: _subWorkOrders?.supplier?.id);
engineer = null;
} else {
_subWorkOrders.supplier = initialSupplier;
}
if (status?.value == 12 || _subWorkOrders.calllastSituation?.value == 12) {
if (status?.value == 12 ||
_subWorkOrders.calllastSituation?.value ==
12) {
_subWorkOrders.calllastSituation = status;
_subWorkOrders.mrNumber = null;
} else {
@ -202,7 +262,8 @@ class _CreateSubWorkOrderPageState extends State<CreateSubWorkOrderPage> {
setState(() {});
},
),
if (_subWorkOrders.calllastSituation?.value == 12) const SizedBox(height: 8),
if (_subWorkOrders.calllastSituation?.value == 12)
const SizedBox(height: 8),
if (_subWorkOrders.calllastSituation?.value == 12)
AppTextFormField(
labelText: context.translation.mrNumber,
@ -213,24 +274,30 @@ class _CreateSubWorkOrderPageState extends State<CreateSubWorkOrderPage> {
),
if (_showVendorFields) const SizedBox(height: 8),
if (_showVendorFields)
SingleItemDropDownMenu<SupplierDetails, VendorProvider>(
SingleItemDropDownMenu<SupplierDetails,
VendorProvider>(
context: context,
title: context.translation.vendorEng,
initialValue: _subWorkOrders.supplier,
onSelect: (supplier) {
if (supplier != null) {
_subWorkOrders.supplier = supplier;
log(_subWorkOrders.supplier?.suppPersons?.map((e) => e.personName)?.toString());
log(_subWorkOrders.supplier?.suppPersons
?.map((e) => e.personName)
?.toString());
setState(() {});
}
},
),
if (_showVendorFields) const SizedBox(height: 8),
if (_showVendorFields)
SingleItemDropDownMenu<SuppPersons, NullableLoadingProvider>(
SingleItemDropDownMenu<SuppPersons,
NullableLoadingProvider>(
context: context,
title: context.translation.vendorName,
enabled: _subWorkOrders.supplier?.suppPersons?.isNotEmpty ?? false,
enabled: _subWorkOrders
.supplier?.suppPersons?.isNotEmpty ??
false,
staticData: _subWorkOrders.supplier.suppPersons,
onSelect: (suppPerson) {
if (suppPerson != null) {
@ -239,30 +306,66 @@ class _CreateSubWorkOrderPageState extends State<CreateSubWorkOrderPage> {
supplierContactId: suppPerson?.id,
personName: suppPerson?.personName,
contact: suppPerson?.contact,
externalEngCode: suppPerson?.externalEngCode,
externalEngCode:
suppPerson?.externalEngCode,
email: suppPerson?.email,
);
}
},
),
8.height,
ServiceReportFaultDescription(
requestId: widget.workOrder?.callRequest?.id?.toString(),
initialValue: _serviceReport.faultDescription,
onSelect: (status) {
_serviceReport.faultDescription = status;
_workPreformedController?.text = _serviceReport
.faultDescription?.workPerformed;
},
),
8.height,
AppTextFormField(
labelText: context.translation.solution,
initialValue:
_serviceReport?.faultDescription?.workPerformed,
textAlign: TextAlign.center,
enable: false,
controller: _workPreformedController,
),
8.height,
ServiceReportAssistantEmployeeMenu(
title: context.translation.assignAssistant,
assetId: widget.workOrder?.callRequest?.asset?.id,
initialValue: (_subWorkOrders.assistantEmployees?.isNotEmpty ?? false) ? _subWorkOrders.assistantEmployees?.first : null,
initialValue: (_subWorkOrders
.assistantEmployees?.isNotEmpty ??
false)
? _subWorkOrders.assistantEmployees?.first
: null,
onSelect: (employee) {
_subWorkOrders.assistantEmployees = [employee.copyWith(id: 0)];
_subWorkOrders.assistantEmployees = [
employee.copyWith(id: 0)
];
},
),
8.height,
SingleItemDropDownMenu<SparePart, NullableLoadingProvider>(
SingleItemDropDownMenu<SparePart,
NullableLoadingProvider>(
context: context,
title: context.translation.partNo,
staticData: _subWorkOrders.sparePartsWorkOrders.map((e) => e.sparePart).toList(),
initialValue: (_subWorkOrders.sparePartsWorkOrders?.isNotEmpty ?? false) ? _subWorkOrders.sparePartsWorkOrders.first.sparePart : null,
staticData: _subWorkOrders.sparePartsWorkOrders
.map((e) => e.sparePart)
.toList(),
initialValue: (_subWorkOrders
.sparePartsWorkOrders?.isNotEmpty ??
false)
? _subWorkOrders
.sparePartsWorkOrders.first.sparePart
: null,
onSelect: (part) {
_subWorkOrders.sparePartsWorkOrders.clear();
_subWorkOrders.sparePartsWorkOrders.add(SparePartsWorkOrders(id: 0, sparePart: part, qty: 0));
_subWorkOrders.sparePartsWorkOrders.add(
SparePartsWorkOrders(
id: 0, sparePart: part, qty: 0));
setState(() {});
},
),
@ -270,28 +373,60 @@ class _CreateSubWorkOrderPageState extends State<CreateSubWorkOrderPage> {
AppTextFormField(
labelText: context.translation.quantity,
textInputType: TextInputType.number,
enable: _subWorkOrders?.sparePartsWorkOrders?.isNotEmpty,
initialValue: (_subWorkOrders.sparePartsWorkOrders?.isNotEmpty ?? false) ? _subWorkOrders.sparePartsWorkOrders.first.qty?.toString() : null,
enable: _subWorkOrders
?.sparePartsWorkOrders?.isNotEmpty,
initialValue: (_subWorkOrders
.sparePartsWorkOrders?.isNotEmpty ??
false)
? _subWorkOrders.sparePartsWorkOrders.first.qty
?.toString()
: null,
onSaved: (text) {
if (_subWorkOrders.sparePartsWorkOrders?.isNotEmpty ?? false) {
_subWorkOrders.sparePartsWorkOrders.first.qty = num.tryParse(text ?? "");
if (_subWorkOrders
.sparePartsWorkOrders?.isNotEmpty ??
false) {
_subWorkOrders.sparePartsWorkOrders.first.qty =
num.tryParse(text ?? "");
}
},
),
8.height,
MultiFilesPicker(label: context.translation.attachImage, files: _files),
ServiceReportRepairLocation(
label: context.translation.repairLocation,
initialValue: _subWorkOrders.repairLocation,
onSelect: (status) {
_subWorkOrders.repairLocation = status;
},
),
8.height,
ESignature(
title: context.translation.engSign,
oldSignature: _subWorkOrders.engSignature,
newSignature: _subWorkOrders.localEngSignature,
onSaved: (signature) {
// if (signature == null || signature.isEmpty) {
// setState(() {});
// return;
// }
_subWorkOrders.localEngSignature = signature;
_subWorkOrders.engSignature = signature != null ? "${DateTime.now().toIso8601String()}.png|${base64Encode(signature)}" : null;
MultiFilesPicker(
label: context.translation.attachImage,
files: _files),
AppTextFormField(
labelText: context.translation.travelingExpense,
initialValue: _serviceReport?.travelingExpenses?.toString(),
textInputType: TextInputType.number,
onSaved: (value) {
_serviceReport.travelingExpenses = int.tryParse(value) ?? 0;
},
),
8.height,
AppTextFormField(
labelText: context.translation.travelingHours,
initialValue: _serviceReport?.travelingHours?.toString(),
textInputType: TextInputType.number,
onSaved: (value) {
_serviceReport.travelingHours = int.tryParse(value) ?? 0;
},
),
8.height,
AppTextFormField(
initialValue: _serviceReport?.comment,
labelText: context.translation.technicalComment,
alignLabelWithHint: true,
textInputType: TextInputType.multiline,
onSaved: (value) {
_serviceReport.comment = value;
},
),
],
@ -303,29 +438,47 @@ class _CreateSubWorkOrderPageState extends State<CreateSubWorkOrderPage> {
onPressed: () async {
setState(() {});
_subWorkOrders.suppEngineerWorkOrders ?? [];
if (engineer != null) _subWorkOrders.suppEngineerWorkOrders.add(engineer..id = 0);
if (engineer != null)
_subWorkOrders.suppEngineerWorkOrders
.add(engineer..id = 0);
if (await validate()) {
_subWorkOrders.attachmentsWorkOrder ??= [];
for (var file in _files) {
_subWorkOrders.attachmentsWorkOrder.add(Attachment(id: 0, name: "${file.path.split("/").last}|${base64Encode(file.readAsBytesSync())}"));
_subWorkOrders.attachmentsWorkOrder.add(Attachment(
id: 0,
name:
"${file.path.split("/").last}|${base64Encode(file.readAsBytesSync())}"));
}
if (_formKey.currentState?.validate() ?? false) {}
_formKey.currentState?.save();
final serviceRequestsProvider = Provider.of<ServiceRequestsProvider>(context, listen: false);
for (var element in (_subWorkOrders?.suppEngineerWorkOrders ?? [])) {
final serviceRequestsProvider =
Provider.of<ServiceRequestsProvider>(context,
listen: false);
for (var element
in (_subWorkOrders?.suppEngineerWorkOrders ?? [])) {
if (element != null) {
element.id = 0;
}
}
showDialog(context: context, barrierDismissible: false, builder: (context) => const AppLazyLoading());
final status = await serviceRequestsProvider.createSubWorkOrder(workOrder: _subWorkOrders);
showDialog(
context: context,
barrierDismissible: false,
builder: (context) => const AppLazyLoading());
final status = await serviceRequestsProvider
.createSubWorkOrder(workOrder: _subWorkOrders);
Navigator.of(context).pop();
if (status >= 200 && status < 300) {
Fluttertoast.showToast(msg: context.translation.successfulRequestMessage);
Fluttertoast.showToast(
msg:
context.translation.successfulRequestMessage);
Navigator.of(context).pop();
} else {
String errorMessage = HttpStatusManger.getStatusMessage(status: serviceRequestsProvider.stateCode, subtitle: context.translation);
ScaffoldMessenger.of(context).showSnackBar(SnackBar(content: Text(errorMessage)));
String errorMessage =
HttpStatusManger.getStatusMessage(
status: serviceRequestsProvider.stateCode,
subtitle: context.translation);
ScaffoldMessenger.of(context).showSnackBar(
SnackBar(content: Text(errorMessage)));
}
}
},
@ -337,9 +490,16 @@ class _CreateSubWorkOrderPageState extends State<CreateSubWorkOrderPage> {
}
bool checkVendorFieldsVisibility(Lookup callsLastSituation) {
bool result = (_subWorkOrders.supplier?.suppliername?.isNotEmpty ?? false) ||
(callsLastSituation?.name?.toLowerCase()?.contains("under repair-vendor") ?? false) ||
(callsLastSituation?.name?.toLowerCase()?.contains("waiting for vendor") ?? false);
bool result =
(_subWorkOrders.supplier?.suppliername?.isNotEmpty ?? false) ||
(callsLastSituation?.name
?.toLowerCase()
?.contains("under repair-vendor") ??
false) ||
(callsLastSituation?.name
?.toLowerCase()
?.contains("waiting for vendor") ??
false);
setState(() {
_showVendorFields = result;
});
@ -348,22 +508,39 @@ class _CreateSubWorkOrderPageState extends State<CreateSubWorkOrderPage> {
Future<bool> validate() async {
if (_subWorkOrders.reason == null) {
Fluttertoast.showToast(msg: "${context.translation.youHaveToSelect} ${context.translation.reason}");
Fluttertoast.showToast(
msg:
"${context.translation.youHaveToSelect} ${context.translation.reason}");
return false;
} else if (_subWorkOrders.equipmentStatus == null) {
Fluttertoast.showToast(msg: "${context.translation.youHaveToSelect} ${context.translation.equipmentStatus}");
Fluttertoast.showToast(
msg:
"${context.translation.youHaveToSelect} ${context.translation.equipmentStatus}");
return false;
} else if (_subWorkOrders.calllastSituation == null) {
Fluttertoast.showToast(msg: "${context.translation.youHaveToSelect} ${context.translation.callLastSituation}");
Fluttertoast.showToast(
msg:
"${context.translation.youHaveToSelect} ${context.translation.callLastSituation}");
return false;
} else if (_showVendorFields && _subWorkOrders.suppEngineerWorkOrders == null) {
Fluttertoast.showToast(msg: "${context.translation.youHaveToSelect} ${context.translation.vendorEng}");
} else if (_showVendorFields &&
_subWorkOrders.suppEngineerWorkOrders == null) {
Fluttertoast.showToast(
msg:
"${context.translation.youHaveToSelect} ${context.translation.vendorEng}");
return false;
} else if (_showVendorFields && (_subWorkOrders.supplier.suppliername == null || _subWorkOrders.supplier.suppliername.isEmpty)) {
Fluttertoast.showToast(msg: "${context.translation.youHaveToSelect} ${context.translation.vendorName}");
} else if (_showVendorFields &&
(_subWorkOrders.supplier.suppliername == null ||
_subWorkOrders.supplier.suppliername.isEmpty)) {
Fluttertoast.showToast(
msg:
"${context.translation.youHaveToSelect} ${context.translation.vendorName}");
return false;
} else if (_subWorkOrders.calllastSituation.value == 12 && (_subWorkOrders.sparePartsWorkOrders == null || _subWorkOrders.sparePartsWorkOrders.isEmpty)) {
Fluttertoast.showToast(msg: "${context.translation.youHaveToSelect} ${context.translation.partNo}");
} else if (_subWorkOrders.calllastSituation.value == 12 &&
(_subWorkOrders.sparePartsWorkOrders == null ||
_subWorkOrders.sparePartsWorkOrders.isEmpty)) {
Fluttertoast.showToast(
msg:
"${context.translation.youHaveToSelect} ${context.translation.partNo}");
return false;
} else if (_subWorkOrders?.timer?.startAt == null) {
await Fluttertoast.showToast(msg: "Working Hours Required");

@ -1,4 +1,5 @@
import 'dart:convert';
import 'dart:developer';
import 'dart:io';
import 'package:flutter/material.dart';
@ -6,6 +7,7 @@ import 'package:provider/provider.dart';
import 'package:test_sa/attachment.dart';
import 'package:test_sa/controllers/providers/api/parts_provider.dart';
import 'package:test_sa/controllers/providers/api/service_requests_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/extensions/context_extension.dart';
@ -16,6 +18,7 @@ import 'package:test_sa/models/service_request/service_report.dart';
import 'package:test_sa/models/service_request/service_request.dart';
import 'package:test_sa/new_views/common_widgets/app_filled_button.dart';
import 'package:test_sa/providers/loading_list_notifier.dart';
import 'package:test_sa/providers/service_request_providers/equipment_status_provider.dart';
import 'package:test_sa/providers/work_order/reason_provider.dart';
import 'package:test_sa/providers/work_order/service_type_provider.dart';
import 'package:test_sa/views/widgets/e_signature/e_signature.dart';
@ -30,13 +33,15 @@ import '../../../../../models/service_request/spare_parts.dart';
import '../../../../../new_views/common_widgets/app_text_form_field.dart';
import '../../../../../new_views/common_widgets/default_app_bar.dart';
import '../../../../../new_views/common_widgets/single_item_drop_down_menu.dart';
import '../../../../../providers/work_order/asset_types_provider.dart';
import '../../../../widgets/date_and_time/date_picker.dart';
import '../../../../widgets/images/multi_image_picker.dart';
import '../../../../widgets/status/report/service_report_fault_description.dart';
import '../../../../widgets/timer/app_timer.dart';
/// todo : TBD (compare with the design)
class CreateServiceReport extends StatefulWidget {
static final String id = "/create-service-report";
static const String id = "/create-service-report";
final ServiceRequest request;
const CreateServiceReport({Key key, this.request}) : super(key: key);
@ -157,6 +162,36 @@ class _CreateServiceReportState extends State<CreateServiceReport> with TickerPr
},
),
8.height,
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 == _serviceReport.callRequest.assetType,
orElse: () => null,
);
},
child: AppTextFormField(
labelText: context.translation.assetType,
initialValue: _serviceReport?.assetType?.name ?? "NULL",
textAlign: TextAlign.center,
enable: false,
style: Theme.of(context).textTheme.titleMedium,
),
),
8.height,
SingleItemDropDownMenu<Lookup, EquipmentStatusProvider>(
context: context,
title: context.translation.equipmentStatus,
initialValue: _serviceReport.equipmentStatus,
onSelect: (value) {
_serviceReport.equipmentStatus = value;
},
),
8.height,
SingleItemDropDownMenu<Lookup, ReasonProvider>(
context: context,
title: context.translation.reason,
@ -181,6 +216,23 @@ class _CreateServiceReportState extends State<CreateServiceReport> with TickerPr
},
),
8.height,
ServiceReportFaultDescription(
requestId: widget.request?.id,
initialValue: _serviceReport.faultDescription,
onSelect: (status) {
_serviceReport.faultDescription = status;
_workPreformedController?.text = _serviceReport.faultDescription?.workPerformed;
},
),
8.height,
AppTextFormField(
labelText: context.translation.solution,
initialValue: _serviceReport?.faultDescription?.workPerformed,
textAlign: TextAlign.center,
enable: false,
controller: _workPreformedController,
),
8.height,
ServiceReportAssistantEmployeeMenu(
title: context.translation.assignAssistant,
assetId: _serviceReport.callRequest?.asset?.id,
@ -214,6 +266,34 @@ class _CreateServiceReportState extends State<CreateServiceReport> with TickerPr
},
),
8.height,
AppTextFormField(
labelText: context.translation.travelingExpense,
initialValue: _serviceReport?.travelingExpenses?.toString(),
textInputType: TextInputType.number,
onSaved: (value) {
_serviceReport.travelingExpenses = int.tryParse(value) ?? 0;
},
),
8.height,
AppTextFormField(
labelText: context.translation.travelingHours,
initialValue: _serviceReport?.travelingHours?.toString(),
textInputType: TextInputType.number,
onSaved: (value) {
_serviceReport.travelingHours = int.tryParse(value) ?? 0;
},
),
8.height,
AppTextFormField(
initialValue: _serviceReport?.comment,
labelText: context.translation.technicalComment,
alignLabelWithHint: true,
textInputType: TextInputType.multiline,
onSaved: (value) {
_serviceReport.comment = value;
},
),
8.height,
MultiFilesPicker(label: context.translation.attachImage, files: _files),
8.height,
ESignature(
@ -228,6 +308,19 @@ class _CreateServiceReportState extends State<CreateServiceReport> with TickerPr
_serviceReport.localEngSignature = signature;
_serviceReport.engSignature = signature != null ? "${DateTime.now().toIso8601String()}.png|${base64Encode(signature)}" : null;
},
), 8.height,
ESignature(
title: context.translation.nurseSignature,
oldSignature: _serviceReport.nurseSignature,
newSignature: _serviceReport.localNurseSignature,
onSaved: (signature) {
// if (signature == null || signature.isEmpty) {
// setState(() {});
// return;
// }
_serviceReport.localNurseSignature = signature;
_serviceReport.nurseSignature = signature != null ? "${DateTime.now().toIso8601String()}.png|${base64Encode(signature)}" : null;
},
),
24.height,
],

@ -25,12 +25,14 @@ import '../../../../../new_views/common_widgets/app_text_form_field.dart';
import '../../../../../new_views/common_widgets/default_app_bar.dart';
import '../../../../../new_views/common_widgets/single_item_drop_down_menu.dart';
import '../../../../../providers/loading_list_notifier.dart';
import '../../../../../providers/service_request_providers/equipment_status_provider.dart';
import '../../../../../providers/work_order/reason_provider.dart';
import '../../../../../providers/work_order/service_type_provider.dart';
import '../../../../widgets/date_and_time/date_picker.dart';
import '../../../../widgets/e_signature/e_signature.dart';
import '../../../../widgets/images/multi_image_picker.dart';
import '../../../../widgets/status/report/service_report_assistant_employee_menu.dart';
import '../../../../widgets/status/report/service_report_fault_description.dart';
import '../../../../widgets/timer/app_timer.dart';
class EditServiceReport extends StatefulWidget {
@ -142,6 +144,36 @@ class _EditServiceReportState extends State<EditServiceReport> with TickerProvid
},
),
8.height,
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 == _serviceReport.callRequest.assetType,
orElse: () => null,
);
},
child: AppTextFormField(
labelText: context.translation.assetType,
initialValue: _serviceReport?.assetType?.name ?? "NULL",
textAlign: TextAlign.center,
enable: false,
style: Theme.of(context).textTheme.titleMedium,
),
),
8.height,
SingleItemDropDownMenu<Lookup, EquipmentStatusProvider>(
context: context,
title: context.translation.equipmentStatus,
initialValue: _serviceReport.equipmentStatus,
onSelect: (value) {
_serviceReport.equipmentStatus = value;
},
),
8.height,
SingleItemDropDownMenu<Lookup, ReasonProvider>(
context: context,
title: context.translation.reason,
@ -166,6 +198,23 @@ class _EditServiceReportState extends State<EditServiceReport> with TickerProvid
},
),
8.height,
ServiceReportFaultDescription(
requestId: widget.request?.id,
initialValue: _serviceReport.faultDescription,
onSelect: (status) {
_serviceReport.faultDescription = status;
_workPreformedController?.text = _serviceReport.faultDescription?.workPerformed;
},
),
8.height,
AppTextFormField(
labelText: context.translation.solution,
initialValue: _serviceReport?.faultDescription?.workPerformed,
textAlign: TextAlign.center,
enable: false,
controller: _workPreformedController,
),
8.height,
ServiceReportAssistantEmployeeMenu(
title: context.translation.assignAssistant,
assetId: _serviceReport.callRequest?.asset?.id,
@ -199,6 +248,34 @@ class _EditServiceReportState extends State<EditServiceReport> with TickerProvid
},
),
8.height,
AppTextFormField(
labelText: context.translation.travelingExpense,
initialValue: _serviceReport?.travelingExpenses?.toString(),
textInputType: TextInputType.number,
onSaved: (value) {
_serviceReport.travelingExpenses = int.tryParse(value) ?? 0;
},
),
8.height,
AppTextFormField(
labelText: context.translation.travelingHours,
initialValue: _serviceReport?.travelingHours?.toString(),
textInputType: TextInputType.number,
onSaved: (value) {
_serviceReport.travelingHours = int.tryParse(value) ?? 0;
},
),
8.height,
AppTextFormField(
initialValue: _serviceReport?.comment,
labelText: context.translation.technicalComment,
alignLabelWithHint: true,
textInputType: TextInputType.multiline,
onSaved: (value) {
_serviceReport.comment = value;
},
),
8.height,
MultiFilesPicker(label: context.translation.attachImage, files: _files),
8.height,
ESignature(
@ -214,6 +291,20 @@ class _EditServiceReportState extends State<EditServiceReport> with TickerProvid
_serviceReport.engSignature = signature != null ? "${DateTime.now().toIso8601String()}.png|${base64Encode(signature)}" : null;
},
),
8.height,
ESignature(
title: context.translation.nurseSignature,
oldSignature: _serviceReport.nurseSignature,
newSignature: _serviceReport.localNurseSignature,
onSaved: (signature) {
// if (signature == null || signature.isEmpty) {
// setState(() {});
// return;
// }
_serviceReport.localNurseSignature = signature;
_serviceReport.nurseSignature = signature != null ? "${DateTime.now().toIso8601String()}.png|${base64Encode(signature)}" : null;
},
),
24.height,
],
),

@ -78,7 +78,7 @@ class WorkOrderListPage extends StatelessWidget {
],
).expanded,
if (_userProvider.user.type == UsersTypes.engineer && serviceRequest.statusValue != 5 && serviceRequest.statusValue != 3)
context.translation.edit.toSvgAsset(height: 48, width: 48).onPress(() {
"edit".toSvgAsset(height: 48, width: 48).onPress(() {
Navigator.of(context).push(
MaterialPageRoute(builder: (_) => UpdateServiceReport(request: serviceRequest, workOrder: workOrders[index])),
);

@ -3,17 +3,40 @@ 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/extensions/context_extension.dart';
import 'package:test_sa/models/fault_description.dart';
import 'package:test_sa/new_views/common_widgets/single_item_drop_down_menu.dart';
import 'package:test_sa/providers/loading_list_notifier.dart';
import 'package:test_sa/views/widgets/loaders/loading_manager.dart';
import 'package:test_sa/views/widgets/status/report/fault_desc_menu.dart';
class ServiceReportFaultDescription extends StatelessWidget {
class ServiceReportFaultDescription extends StatefulWidget {
final String requestId;
final Function(FaultDescription) onSelect;
final FaultDescription initialValue;
const ServiceReportFaultDescription({Key key, this.requestId, this.onSelect, this.initialValue}) : super(key: key);
@override
State<ServiceReportFaultDescription> createState() => _ServiceReportFaultDescriptionState();
}
class _ServiceReportFaultDescriptionState extends State<ServiceReportFaultDescription> {
@override
void initState() {
super.initState();
if(widget.initialValue == null){
WidgetsFlutterBinding.ensureInitialized()
.addPostFrameCallback((timeStamp) {
ServiceRequestFaultDescriptionProvider menuProvider =
Provider.of<ServiceRequestFaultDescriptionProvider>(context,
listen: false);
menuProvider.reset();
menuProvider.getCallRequestForWorkOrder(requestId: widget.requestId);
});
}
}
@override
Widget build(BuildContext context) {
SettingProvider settingProvider = Provider.of<SettingProvider>(context);
@ -25,13 +48,20 @@ class ServiceReportFaultDescription extends StatelessWidget {
stateCode: menuProvider.stateCode,
onRefresh: () async {
menuProvider.reset();
await menuProvider.getCallRequestForWorkOrder(user: userProvider.user, host: settingProvider.host, requestId: requestId);
await menuProvider.getCallRequestForWorkOrder(user: userProvider.user, host: settingProvider.host, requestId: widget.requestId);
},
child: FaultDescriptionMenu(
initialStatus: initialValue,
statuses: menuProvider.items ?? [],
onSelect: onSelect,
child: SingleItemDropDownMenu<FaultDescription, NullableLoadingProvider>(
context: context,
title: context.translation.faultDescription,
onSelect: widget.onSelect,
initialValue: widget.initialValue,
staticData: menuProvider.items ?? [],
),
// child: FaultDescriptionMenu(
// initialStatus: initialValue,
// statuses: menuProvider.items ?? [],
// onSelect: onSelect,
// ),
);
}
}

@ -8,10 +8,11 @@ import 'package:test_sa/views/widgets/loaders/loading_manager.dart';
import 'package:test_sa/views/widgets/status/single_status_menu.dart';
class ServiceReportRepairLocation extends StatelessWidget {
final String label;
final Lookup initialValue;
final Function(Lookup) onSelect;
const ServiceReportRepairLocation({Key key, this.onSelect, this.initialValue}) : super(key: key);
const ServiceReportRepairLocation({Key key,this.label, this.onSelect, this.initialValue}) : super(key: key);
@override
Widget build(BuildContext context) {
@ -30,6 +31,7 @@ class ServiceReportRepairLocation extends StatelessWidget {
);
},
child: SingleStatusMenu(
title: label,
initialStatus: initialValue,
statuses: _menuProvider.reasons,
onSelect: onSelect,

Loading…
Cancel
Save