diff --git a/lib/controllers/api_routes/urls.dart b/lib/controllers/api_routes/urls.dart index aac9b8b5..39818fc7 100644 --- a/lib/controllers/api_routes/urls.dart +++ b/lib/controllers/api_routes/urls.dart @@ -11,7 +11,7 @@ class URLs { // static String _baseUrl = "$_host/mobile"; // static final String _baseUrl = "$_host/v2/mobile"; // new V2 apis - static final String _baseUrl = "$_host/v6/mobile"; // for asset delivery module + static final String _baseUrl = "$_host/v3/mobile"; // for asset delivery module // static final String _baseUrl = "$_host/mobile"; // host local UAT and for internal audit dev // static final String _baseUrl = "$_host/v3/mobile"; // v3 for production CM,PM,TM // static final String _baseUrl = "$_host/v5/mobile"; // v5 for data segregation @@ -394,7 +394,6 @@ class URLs { static get addLoan => '$_baseUrl/Loan/AddLoan'; //Asset Delivery Module - //AssetDeliveryExternal/GetAssetDeliveryExternalById static get getAssetDeliveryDetailsById => '$_baseUrl/AssetDeliveryExternal/GetAssetDeliveryExternalById'; static get getAssetDeliveryTableListById => '$_baseUrl/AssetDeliveryExternalDelivery/GetDeliveriesByMasterId'; @@ -432,4 +431,17 @@ class URLs { static get saveEndUserAssetData => "$_baseUrl/AssetDeliveryEndUserAcceptance/SaveDetail"; static get endUserStatusLookup => "$_baseUrl/Lookups/GetLookup?lookupEnum=534"; static get endUserRejectionReasonLookup => "$_baseUrl/Lookups/GetLookup?lookupEnum=5007"; + + //Medical Gas Request.. +// 4004 + static get orderTypeLookUp => "$_baseUrl/Lookups/GetLookup?lookupEnum=4004"; + static get itemTypeLookUp => "$_baseUrl/Lookups/GetLookup?lookupEnum=4005"; + static get getMedicalGasSupplierList => "$_baseUrl/MedicalGas/GetMedicalGasSupplierAsync"; + static get getMedicalGasInfoBySupplier => "$_baseUrl/MedicalGas/GetMedicalGasInfoBySupplierAsync"; + static get addMedicalGasRequest => "$_baseUrl/MedicalGas/AddUpdateMedicalGasRequestAsync"; + static get getMedicalGasById => "$_baseUrl/MedicalGas/GetMedicalGasRequestByIdAsync"; + static get updateDeliveryNote => "$_baseUrl/MedicalGas/MedicalGasRequestDeliveryNotesAsync"; + + + } diff --git a/lib/main.dart b/lib/main.dart index ceff381d..6592c495 100644 --- a/lib/main.dart +++ b/lib/main.dart @@ -46,6 +46,10 @@ import 'package:test_sa/modules/loan_module/pages/create_loan_request_page.dart' import 'package:test_sa/modules/loan_module/provider/loan_period_provider.dart'; import 'package:test_sa/modules/loan_module/provider/loan_provider.dart'; import 'package:test_sa/modules/loan_module/provider/medical_department_provider.dart'; +import 'package:test_sa/modules/medical_gas_inspection/create_medical_gas_request_page.dart'; +import 'package:test_sa/modules/medical_gas_inspection/providers/item_type_provider.dart'; +import 'package:test_sa/modules/medical_gas_inspection/providers/medical_gas_inspection_provider.dart'; +import 'package:test_sa/modules/medical_gas_inspection/providers/order_type_provider.dart'; import 'package:test_sa/modules/tm_module/gas_refill/create_gas_refill_request.dart'; import 'package:test_sa/modules/tm_module/gas_refill/update_gas_refill_request.dart'; import 'package:test_sa/modules/traf_module/create_traf_request_page.dart'; @@ -114,6 +118,7 @@ import 'dashboard_latest/dashboard_provider.dart'; import 'modules/internal_audit_module/pages/equipment_internal_audit/update_equipment_internal_audit_page.dart'; import 'modules/internal_audit_module/provider/internal_audit_checklist_provider.dart'; import 'modules/cx_module/survey/survey_provider.dart'; +import 'modules/medical_gas_inspection/providers/medical_gas_supplier_provider.dart'; import 'modules/tm_module/device_transfer/create_device_transfer_request.dart'; import 'modules/tm_module/device_transfer/device_filter_screen.dart'; import 'modules/tm_module/device_transfer/device_search_screen.dart'; @@ -326,6 +331,10 @@ class MyApp extends StatelessWidget { ChangeNotifierProvider(create: (_) => PowerSupplyTypeProvider()), ChangeNotifierProvider(create: (_) => EndUserStatusLookupProvider()), ChangeNotifierProvider(create: (_) => EndUserRejectionReasonLookupProvider()), + ChangeNotifierProvider(create: (_) => MedicalGasOrderTypeProvider()), + ChangeNotifierProvider(create: (_) => MedicalGasItemTypeProvider()), + ChangeNotifierProvider(create: (_) => MedicalGasInspectionProvider()), + ChangeNotifierProvider(create: (_) => MedicalGasSupplierProvider()), ], child: GestureDetector( onTap: () { @@ -393,6 +402,7 @@ class MyApp extends StatelessWidget { UpdateEquipmentInternalAuditPage.id: (_) => UpdateEquipmentInternalAuditPage(), UpdateSystemInternalAuditPage.id: (_) => UpdateSystemInternalAuditPage(), CreateLoanRequestPage.id: (_) => CreateLoanRequestPage(), + CreateMedicalGasRequestPage.id: (_) => CreateMedicalGasRequestPage(), // SwipeSuccessView.routeName: (_) => const SwipeSuccessView(), // SwipeHistoryView.routeName: (_) => const SwipeHistoryView(), }, diff --git a/lib/models/new_models/dashboard_detail.dart b/lib/models/new_models/dashboard_detail.dart index 7c39d4ce..93c868a1 100644 --- a/lib/models/new_models/dashboard_detail.dart +++ b/lib/models/new_models/dashboard_detail.dart @@ -55,6 +55,7 @@ class Data { String? assetNumber; String? requestTypeName; String? requestNo; + String? requestType; String? poInternal; String? poExternal; int? transactionNo; @@ -77,6 +78,7 @@ class Data { this.assetNumber, this.requestTypeName, this.requestNo, + this.requestType, this.poExternal, this.poInternal, this.transactionNo}); @@ -90,6 +92,7 @@ class Data { isHighPriority = json['isHighPriority']; assetName = json['assetName']; sessionType = json['sessionType']; + requestType = json['requestType']; numberOfSites = json['numberOfSites']; numberOfAssets = json['numberOfAssets']; assetNumber = json['assetNumber']; diff --git a/lib/modules/asset_delivery_module/pages/delivery_inspection/delivery_inspection_form_view.dart b/lib/modules/asset_delivery_module/pages/delivery_inspection/delivery_inspection_form_view.dart index 40a4f61c..36faf4bf 100644 --- a/lib/modules/asset_delivery_module/pages/delivery_inspection/delivery_inspection_form_view.dart +++ b/lib/modules/asset_delivery_module/pages/delivery_inspection/delivery_inspection_form_view.dart @@ -161,7 +161,7 @@ class _DeliveryInspectionFormViewState extends State return Consumer(builder: (context, provider, child) { List linesList = provider.deliveryLinesList; return provider.isDeliveryLineListLoading - ? SizedBox(height: 200.toScreenHeight, child: const CircularProgressIndicator(color: AppColor.primary10).center) + ? SizedBox.expand(child: const CircularProgressIndicator(color: AppColor.primary10).center) : linesList.isEmpty ? const NoDataFound().center : ListView.separated( diff --git a/lib/modules/asset_delivery_module/pages/technical_inpection/update_child_asset_view.dart b/lib/modules/asset_delivery_module/pages/technical_inpection/update_child_asset_view.dart index bb0b6ca9..c95dd194 100644 --- a/lib/modules/asset_delivery_module/pages/technical_inpection/update_child_asset_view.dart +++ b/lib/modules/asset_delivery_module/pages/technical_inpection/update_child_asset_view.dart @@ -330,12 +330,12 @@ class _UpdateChildAssetViewState extends State { child: child!, ); }, - ).then((selectedTime) { - if (selectedTime != null) { - model.installationDate = DateTime(selectedDate.year, selectedDate.month, selectedDate.day, selectedTime.hour, selectedTime.minute); - setState(() {}); - } - }); + ).then((selectedTime) { + if (selectedTime != null) { + model.installationDate = DateTime(selectedDate.year, selectedDate.month, selectedDate.day, selectedTime.hour, selectedTime.minute); + setState(() {}); + } + }); }, ), 8.height, diff --git a/lib/modules/medical_gas_inspection/create_medical_gas_request_page.dart b/lib/modules/medical_gas_inspection/create_medical_gas_request_page.dart new file mode 100644 index 00000000..d8c017ff --- /dev/null +++ b/lib/modules/medical_gas_inspection/create_medical_gas_request_page.dart @@ -0,0 +1,295 @@ + +import 'package:flutter/material.dart'; +import 'package:provider/provider.dart'; +import 'package:test_sa/extensions/context_extension.dart'; +import 'package:test_sa/extensions/int_extensions.dart'; +import 'package:test_sa/extensions/string_extensions.dart'; +import 'package:test_sa/extensions/text_extensions.dart'; +import 'package:test_sa/extensions/widget_extensions.dart'; +import 'package:test_sa/models/generic_attachment_model.dart'; +import 'package:test_sa/models/lookup.dart'; +import 'package:test_sa/models/new_models/site.dart'; +import 'package:test_sa/models/new_models/task_request/task_type_model.dart'; +import 'package:test_sa/modules/cm_module/views/components/action_button/footer_action_button.dart'; +import 'package:test_sa/modules/medical_gas_inspection/models/medical_gas_data_model.dart'; +import 'package:test_sa/modules/medical_gas_inspection/models/medical_gas_form_model.dart'; +import 'package:test_sa/modules/medical_gas_inspection/models/medical_gas_supplier_model.dart'; +import 'package:test_sa/modules/medical_gas_inspection/providers/item_type_provider.dart'; +import 'package:test_sa/modules/medical_gas_inspection/providers/medical_gas_inspection_provider.dart'; +import 'package:test_sa/modules/medical_gas_inspection/providers/medical_gas_supplier_provider.dart'; +import 'package:test_sa/modules/medical_gas_inspection/providers/order_type_provider.dart'; +import 'package:test_sa/new_views/app_style/app_color.dart'; +import 'package:test_sa/new_views/common_widgets/app_filled_button.dart'; +import 'package:test_sa/new_views/common_widgets/app_lazy_loading.dart'; +import 'package:test_sa/new_views/common_widgets/app_text_form_field.dart'; +import 'package:test_sa/new_views/common_widgets/single_item_drop_down_menu.dart'; +import 'package:test_sa/providers/gas_request_providers/site_provider.dart'; +import '../../../../../../new_views/common_widgets/default_app_bar.dart'; + +class CreateMedicalGasRequestPage extends StatefulWidget { + static const String id = "/create-medical-gas"; + final MedicalGasDataModel? dataModel; + + CreateMedicalGasRequestPage({Key? key, this.dataModel}) : super(key: key); + + @override + _CreateMedicalGasRequestPageState createState() => _CreateMedicalGasRequestPageState(); +} + +class _CreateMedicalGasRequestPageState extends State with TickerProviderStateMixin { + final List attachments = []; + final GlobalKey _formKey = GlobalKey(); + final GlobalKey _scaffoldKey = GlobalKey(); + TaskType? selectedType; + MedicalGasFormModel _medicalGasFormModel = MedicalGasFormModel(); + MedicalGasSupplierModel? medicalGasInfo; + late MedicalGasInspectionProvider medicalGasInspectionProvider; + bool isGasInfoLoading = false; + + @override + void initState() { + super.initState(); + // Provider.of(context, listen: false).reset(); + medicalGasInspectionProvider = Provider.of(context, listen: false); + _populateFormData(); + } + + _populateFormData() { + if (widget.dataModel != null) { + MedicalGasDataModel dataModel = widget.dataModel!; + _medicalGasFormModel = MedicalGasFormModel( + id: dataModel.id, + orderType: Lookup(id: dataModel.requestOrderTypeId, name: dataModel.requestOrderType), + itemType: Lookup(id: dataModel.itemTypeId, name: dataModel.itemType), + site: Site(id: dataModel.siteId, custName: dataModel.site), + supplier: MedicalGasSupplierModel(id: dataModel.supplierId, supplier: dataModel.supplier), + ); + List attributeInfo = []; + dataModel.requestDetailDtos.forEach((v) { + attributeInfo.add(AttributeInfo.fromJson(v.toJson())); + }); + medicalGasInfo = MedicalGasSupplierModel( + supplierContact: dataModel.contact, + supplierEmail: dataModel.email, + attributeInfo: attributeInfo, + ); + setState(() {}); + } + } + + @override + Widget build(BuildContext context) { + return Scaffold( + key: _scaffoldKey, + appBar: DefaultAppBar(title: 'Medical Gas Inspection'.addTranslation), + body: Form( + key: _formKey, + child: Column( + children: [ + SingleChildScrollView( + padding: const EdgeInsets.all(16), + child: Column( + crossAxisAlignment: CrossAxisAlignment.start, + mainAxisSize: MainAxisSize.min, + children: [ + SingleItemDropDownMenu( + context: context, + title: "Order Type", + validator: (value) { + if (value == null) return "Mandatory"; + return null; + }, + initialValue: _medicalGasFormModel.orderType, + showShadow: false, + backgroundColor: AppColor.fieldBgColor(context), + showAsBottomSheet: true, + onSelect: (value) { + _medicalGasFormModel.orderType = value; + }, + ), + 8.height, + SingleItemDropDownMenu( + context: context, + title: "Item Type", + validator: (value) { + if (value == null) return "Mandatory"; + return null; + }, + initialValue: _medicalGasFormModel.itemType, + showShadow: false, + backgroundColor: AppColor.fieldBgColor(context), + showAsBottomSheet: true, + onSelect: (value) { + _medicalGasFormModel.itemType = value; + setState(() {}); + setGasInfo(); + }, + ), + 8.height, + SingleItemDropDownMenu( + context: context, + title: context.translation.site, + initialValue: _medicalGasFormModel.site, + showShadow: false, + validator: (value) { + if (value == null) return "Please select a site"; + return null; + }, + backgroundColor: AppColor.fieldBgColor(context), + showAsBottomSheet: true, + onSelect: (value) { + _medicalGasFormModel.site = value; + setState(() {}); + setGasInfo(); + }, + ), + 8.height, + // 8.height, + // SingleItemDropDownMenu( + // context: context, + // title: context.translation.department, + // showShadow: false, + // validator: (value) { + // if (value == null) return "Please select a department"; + // return null; + // }, + // showAsBottomSheet: true, + // initialValue: _medicalGasFormModel.department, + // requestById: context.userProvider.user?.clientId, + // backgroundColor: AppColor.fieldBgColor(context), + // onSelect: (value) { + // _medicalGasFormModel.department = value; + // setState(() {}); + // }, + // ), + // 8.height, + SingleItemDropDownMenu( + context: context, + title: context.translation.supplier, + initialValue: _medicalGasFormModel.supplier, + showAsBottomSheet: true, + backgroundColor: AppColor.fieldBgColor(context), + showShadow: false, + onSelect: (value) { + setState(() { + _medicalGasFormModel.supplier = value; + }); + setGasInfo(); + }, + ), + + if (medicalGasInfo != null) medicalGasInfoWidget(), + ], + ).toShadowContainer(context, borderRadius: 20), + ).expanded, + FooterActionButton.footerContainer( + context: context, + child: Row( + children: [ + AppFilledButton( + buttonColor: AppColor.primary10, + label: 'Save'.addTranslation, + onPressed: () { + _update(isSubmitted: false); + }, + // buttonColor: AppColor.primary10, + ).expanded, + 8.width, + AppFilledButton( + buttonColor: AppColor.primary10, + label: 'Submit'.addTranslation, + onPressed: () { + _update(isSubmitted: true); + }, + // buttonColor: AppColor.primary10, + ).expanded, + ], + ), + ), + ], + ), + ), + ); + } + + void setGasInfo() async { + if (_medicalGasFormModel.itemType != null && _medicalGasFormModel.site != null && _medicalGasFormModel.supplier != null) { + setState(() { + isGasInfoLoading = true; + }); + medicalGasInfo = + await medicalGasInspectionProvider.getMedicalGasInfo(itemTypeId: _medicalGasFormModel.itemType!.id, supplierId: _medicalGasFormModel.supplier!.id, siteId: _medicalGasFormModel.site!.id); + setState(() { + isGasInfoLoading = false; + }); + } + } + + Widget medicalGasInfoWidget() { + return isGasInfoLoading + ? const CircularProgressIndicator(color: AppColor.primary10).center + : Column( + crossAxisAlignment: CrossAxisAlignment.start, + children: [ + 8.height, + 'Supplier Contact: ${medicalGasInfo?.supplierContact ?? "-"}'.bodyText(context).custom(color: AppColor.black10), + 8.height, + 'Supplier Email: ${medicalGasInfo?.supplierEmail ?? "-"}'.bodyText(context).custom(color: AppColor.black10), + 8.height, + 'Items'.addTranslation.bodyText(context).custom(color: AppColor.textColor(context)), + 8.height, + // MedicalGasItemsListView( + // itemsList: medicalGasInfo?.attributeInfo ?? [], + // ), + if (medicalGasInfo!.attributeInfo!.isNotEmpty) + ListView.separated( + separatorBuilder: (_, __) => 12.height, + itemCount: medicalGasInfo!.attributeInfo!.length, + shrinkWrap: true, + physics: const NeverScrollableScrollPhysics(), + itemBuilder: (context, index) { + AttributeInfo model = medicalGasInfo!.attributeInfo![index]; + return AppTextFormField( + labelText: model.itemName, + hintText: 'Enter Quantity'.addTranslation, + backgroundColor: AppColor.fieldBgColor(context), + initialValue: model.requestedQuantity != null ? model.requestedQuantity.toString() : '', + textAlign: TextAlign.center, + enable: true, + textInputType: TextInputType.number, + labelStyle: AppTextStyles.textFieldLabelStyle, + showShadow: false, + onChange: (value) { + if (value.isNotEmpty) { + model.requestedQuantity = int.tryParse(value); + } + }, + style: Theme.of(context).textTheme.titleMedium, + ); + }, + ) + ], + ); + } + + Future _update({bool isSubmitted = false}) async { + if (medicalGasInfo != null && medicalGasInfo!.attributeInfo!.isNotEmpty) { + _medicalGasFormModel.gasRequestDetail = []; + for (var item in medicalGasInfo!.attributeInfo!) { + _medicalGasFormModel.gasRequestDetail?.add(MedicalGasFormDetailModel( + id: widget.dataModel != null ? item.id : 0, + medicalGasAttributeId: item.medicalGasAttributeId ?? item.id, + requestedQuantity: item.requestedQuantity, + )); + } + } + _medicalGasFormModel.isSubmitted = isSubmitted; + showDialog(context: context, barrierDismissible: false, builder: (context) => const AppLazyLoading()); + await medicalGasInspectionProvider.saveMedicalGas(model: _medicalGasFormModel).then((status) async { + Navigator.pop(context); + if (status) { + Navigator.pop(context, true); + } + }); + } +} diff --git a/lib/modules/medical_gas_inspection/medical_gas_inspection_detail_page.dart b/lib/modules/medical_gas_inspection/medical_gas_inspection_detail_page.dart new file mode 100644 index 00000000..e55e3274 --- /dev/null +++ b/lib/modules/medical_gas_inspection/medical_gas_inspection_detail_page.dart @@ -0,0 +1,152 @@ +import 'package:flutter/material.dart'; +import 'package:provider/provider.dart'; +import 'package:test_sa/controllers/api_routes/urls.dart'; +import 'package:test_sa/extensions/context_extension.dart'; +import 'package:test_sa/extensions/int_extensions.dart'; +import 'package:test_sa/extensions/string_extensions.dart'; +import 'package:test_sa/extensions/text_extensions.dart'; +import 'package:test_sa/extensions/widget_extensions.dart'; +import 'package:test_sa/modules/cm_module/views/components/action_button/footer_action_button.dart'; +import 'package:test_sa/modules/medical_gas_inspection/create_medical_gas_request_page.dart'; +import 'package:test_sa/modules/medical_gas_inspection/models/medical_gas_data_model.dart'; +import 'package:test_sa/modules/medical_gas_inspection/providers/medical_gas_inspection_provider.dart'; +import 'package:test_sa/modules/medical_gas_inspection/update_delivery_notes_page.dart'; +import 'package:test_sa/new_views/app_style/app_color.dart'; +import 'package:test_sa/new_views/common_widgets/app_filled_button.dart'; +import 'package:test_sa/new_views/common_widgets/default_app_bar.dart'; +import 'package:test_sa/views/widgets/images/files_list.dart'; +import 'package:test_sa/views/widgets/loaders/no_data_found.dart'; +import 'package:test_sa/views/widgets/requests/request_status.dart'; + +class MedicalGasInspectionDetailPage extends StatefulWidget { + static const String id = "/medical-gas-inspection-detail-page"; + final int inspectionId; + final String? prority; + + MedicalGasInspectionDetailPage({Key? key, required this.inspectionId, this.prority}) : super(key: key); + + @override + State createState() => _MedicalGasInspectionDetailPageState(); +} + +class _MedicalGasInspectionDetailPageState extends State { + @override + void initState() { + super.initState(); + WidgetsBinding.instance.addPostFrameCallback((_) { + _loadData(); + }); + } + + MedicalGasDataModel? model; + bool _isLoading = true; + + Future _loadData() async { + final result = await context.read().getMedicalGasById(requestId: widget.inspectionId); + setState(() { + model = result; + _isLoading = false; + }); + } + + @override + Widget build(BuildContext context) { + return Scaffold( + appBar: const DefaultAppBar(title: "Request Details"), + body: SafeArea( + child: _isLoading + ? SizedBox.expand(child: const CircularProgressIndicator(color: AppColor.primary10).center) + : model == null + ? const NoDataFound().center + : Column( + children: [ + ListView( + padding: const EdgeInsets.all(16), + children: [ + Column( + crossAxisAlignment: CrossAxisAlignment.start, + children: [ + //Need to return the status form api backend + Row( + children: [ + if (widget.prority != null) ...[ + StatusLabel( + label: widget.prority, + textColor: AppColor.getRequestStatusTextColorByName(context, widget.prority), + backgroundColor: AppColor.getRequestStatusColorByName(context, widget.prority), + ), + 8.width, + ], + StatusLabel( + label: model?.requestStatus?.name, + textColor: AppColor.getHistoryLogStatusTextColorByName(model?.requestStatus?.name ?? ''), + backgroundColor: AppColor.getHistoryLogStatusColorByName(model?.requestStatus?.name ?? ''), + ), + 1.width.expanded, + Text(model!.requestedDate!.toServiceRequestCardFormat, + textAlign: TextAlign.end, style: AppTextStyles.tinyFont.copyWith(color: context.isDark ? AppColor.neutral10 : AppColor.neutral50)) + ], + ), + 8.height, + Text("Request Details", style: AppTextStyles.heading4.copyWith(color: context.isDark ? AppColor.neutral30 : AppColor.neutral50)), + '${context.translation.requestNo}: ${model?.requestNumber ?? '-'}'.bodyText(context), + 'Order Type: ${model?.requestOrderType ?? '-'}'.bodyText(context), + 'Item Type: ${model?.itemType ?? '-'}'.bodyText(context), + 'Site: ${model?.site ?? '-'}'.bodyText(context), + 'Supplier Name: ${model?.supplier ?? '-'}'.bodyText(context), + 'Supplier Contact: ${model?.contact ?? '-'}'.bodyText(context), + 'Supplier Email: ${model?.email ?? '-'}'.bodyText(context), + if (model!.deliveryNoteAttachmentDto.isNotEmpty) ...[ + const Divider().defaultStyle(context), + Text( + "Attachments".addTranslation, + style: AppTextStyles.heading4.copyWith(color: context.isDark ? AppColor.neutral30 : AppColor.neutral50), + ), + FilesList(images: model!.deliveryNoteAttachmentDto.map((e) => URLs.getFileUrl(e.name ?? '') ?? '').toList() ?? []), + ], + ], + ).toShadowContainer(context, padding: 12), + ], + ).expanded, + if (model?.requestStatus?.value != null && model!.requestStatus!.value! < 3) + FooterActionButton.footerContainer( + context: context, + child: AppFilledButton( + buttonColor: AppColor.primary10, + label: model?.isSubmitted == true ? "Upload Delivery Note" : 'Update', + onPressed: () async { + if (model?.isSubmitted == true) { + bool? isRefresh = await Navigator.of(context).push(MaterialPageRoute(builder: (_) => UpdateDeliveryNotes(dataModel: model))); + if (isRefresh == true) { + _loadData(); + } + return; + } + bool? isRefresh = await Navigator.of(context).push(MaterialPageRoute( + builder: (_) => CreateMedicalGasRequestPage( + dataModel: model, + ))); + if (isRefresh == true) { + _loadData(); + } + }), + ), + ], + ), + )); + } + + Widget labelValueText(BuildContext context, String label, String? value) { + if (value == null || value.isEmpty) return const SizedBox.shrink(); + + return Padding( + padding: const EdgeInsets.only(bottom: 4), + child: Text( + '$label: $value', + style: AppTextStyles.bodyText.copyWith( + color: context.isDark ? AppColor.neutral30 : AppColor.neutral120, + ), + ), + ); + } +} diff --git a/lib/modules/medical_gas_inspection/medical_gas_inspection_item_view.dart b/lib/modules/medical_gas_inspection/medical_gas_inspection_item_view.dart new file mode 100644 index 00000000..e03fc500 --- /dev/null +++ b/lib/modules/medical_gas_inspection/medical_gas_inspection_item_view.dart @@ -0,0 +1,130 @@ +import 'dart:developer'; + +import 'package:flutter/material.dart'; +import 'package:test_sa/extensions/context_extension.dart'; +import 'package:test_sa/extensions/int_extensions.dart'; +import 'package:test_sa/extensions/string_extensions.dart'; +import 'package:test_sa/extensions/text_extensions.dart'; +import 'package:test_sa/extensions/widget_extensions.dart'; +import 'package:test_sa/models/all_requests_and_count_model.dart'; +import 'package:test_sa/models/new_models/dashboard_detail.dart'; +import 'package:test_sa/modules/medical_gas_inspection/medical_gas_inspection_detail_page.dart'; +import 'package:test_sa/new_views/app_style/app_color.dart'; +import 'package:test_sa/views/widgets/requests/request_status.dart'; + +class MedicalGasInspectionItemView extends StatelessWidget { + final Data? requestData; + final RequestsDetails? requestDetails; + final bool showShadow; + + const MedicalGasInspectionItemView({Key? key, this.requestData, this.requestDetails, this.showShadow = true}) : super(key: key); + + @override + Widget build(BuildContext context) { + if (requestData != null) { + return Column( + crossAxisAlignment: CrossAxisAlignment.start, + children: [ + Row( + crossAxisAlignment: CrossAxisAlignment.start, + children: [ + if (requestData!.priorityName != null) ...[ + StatusLabel( + label: requestData!.priorityName!, + textColor: AppColor.getRequestStatusTextColorByName(context, requestData!.priorityName!), + backgroundColor: AppColor.getRequestStatusColorByName(context, requestData!.priorityName!), + ), + 8.width, + ], + StatusLabel( + label: requestData!.statusName!, + textColor: AppColor.getHistoryLogStatusTextColorByName(requestData!.statusName!), + backgroundColor: AppColor.getHistoryLogStatusColorByName(requestData!.statusName!), + ), + 1.width.expanded, + Text(requestData!.transactionDate!.toServiceRequestCardFormat, + textAlign: TextAlign.end, style: AppTextStyles.tinyFont.copyWith(color: context.isDark ? AppColor.neutral10 : AppColor.neutral50)), + ], + ), + (requestData?.typeTransaction ?? 'Medical Gas Request').heading5(context), + infoWidget(label: 'Request Number'.addTranslation, value: requestData?.requestNo ?? '-', context: context), + infoWidget(label: 'Request Type'.addTranslation, value: requestData?.requestType ?? '-', context: context), + // infoWidget(label: 'Site'.addTranslation, value: requestData?.si ?? '-', context: context), + // infoWidget(label: 'Gas Type'.addTranslation, value: requestDetails?.gasType ?? '-', context: context), + 8.height, + Row( + mainAxisSize: MainAxisSize.min, + children: [ + Text( + context.translation.viewDetails, + style: AppTextStyles.bodyText.copyWith(color: AppColor.blueStatus(context)), + ), + 4.width, + Icon(Icons.arrow_forward, color: AppColor.blueStatus(context), size: 14) + ], + ), + ], + ).toShadowContainer(context, withShadow: showShadow).onPress(() async { + Navigator.of(context).push(MaterialPageRoute( + builder: (_) => MedicalGasInspectionDetailPage( + inspectionId: requestData!.id!, + prority: requestData?.priorityName, + ))); + }); + } + return Column( + crossAxisAlignment: CrossAxisAlignment.start, + children: [ + Row( + crossAxisAlignment: CrossAxisAlignment.start, + children: [ + if (requestDetails!.priority != null) ...[ + StatusLabel( + label: requestDetails!.priority!, + textColor: AppColor.getRequestStatusTextColorByName(context, requestDetails!.priority!), + backgroundColor: AppColor.getRequestStatusColorByName(context, requestDetails!.priority!), + ), + 8.width, + ], + StatusLabel( + label: requestDetails!.status!, + textColor: AppColor.getHistoryLogStatusTextColorByName(requestDetails!.status!), + backgroundColor: AppColor.getHistoryLogStatusColorByName(requestDetails!.status!), + ), + 1.width.expanded, + Text(requestDetails!.date!.toServiceRequestCardFormat, textAlign: TextAlign.end, style: AppTextStyles.tinyFont.copyWith(color: context.isDark ? AppColor.neutral10 : AppColor.neutral50)), + ], + ), + (requestDetails?.nameOfType ?? 'Medical Gas Request').heading5(context), + infoWidget(label: 'Request Number'.addTranslation, value: requestDetails?.requestNo ?? '-', context: context), + infoWidget(label: 'Request Type'.addTranslation, value: requestDetails?.requestType ?? '-', context: context), + infoWidget(label: 'Site'.addTranslation, value: requestDetails?.site ?? '-', context: context), + 8.height, + Row( + mainAxisSize: MainAxisSize.min, + children: [ + Text( + context.translation.viewDetails, + style: AppTextStyles.bodyText.copyWith(color: AppColor.blueStatus(context)), + ), + 4.width, + Icon(Icons.arrow_forward, color: AppColor.blueStatus(context), size: 14) + ], + ), + ], + ).toShadowContainer(context, withShadow: showShadow).onPress(() async { + Navigator.of(context).push(MaterialPageRoute( + builder: (_) => MedicalGasInspectionDetailPage( + inspectionId: requestDetails!.id!, + prority: requestDetails?.priority, + ))); + }); + } + + Widget infoWidget({required String label, String? value, required BuildContext context}) { + if (value != null && value.isNotEmpty) { + return '$label: $value'.bodyText(context); + } + return const SizedBox(); + } +} diff --git a/lib/modules/medical_gas_inspection/medical_gas_item_list_view.dart b/lib/modules/medical_gas_inspection/medical_gas_item_list_view.dart new file mode 100644 index 00000000..7b399233 --- /dev/null +++ b/lib/modules/medical_gas_inspection/medical_gas_item_list_view.dart @@ -0,0 +1,94 @@ +// import 'dart:developer'; +// +// import 'package:flutter/material.dart'; +// import 'package:provider/provider.dart'; +// import 'package:test_sa/extensions/context_extension.dart'; +// import 'package:test_sa/extensions/enum_extensions.dart'; +// import 'package:test_sa/extensions/int_extensions.dart'; +// import 'package:test_sa/extensions/string_extensions.dart'; +// import 'package:test_sa/extensions/text_extensions.dart'; +// import 'package:test_sa/extensions/widget_extensions.dart'; +// import 'package:test_sa/models/lookup.dart'; +// import 'package:test_sa/modules/asset_delivery_module/models/cost_center_model.dart'; +// import 'package:test_sa/modules/asset_delivery_module/provider/asset_delivery_provider.dart'; +// import 'package:test_sa/modules/asset_delivery_module/provider/cost_center_provider.dart'; +// import 'package:test_sa/modules/cm_module/views/components/action_button/footer_action_button.dart'; +// import 'package:test_sa/modules/medical_gas_inspection/models/medical_gas_supplier_model.dart'; +// import 'package:test_sa/new_views/app_style/app_color.dart'; +// import 'package:test_sa/new_views/common_widgets/app_filled_button.dart'; +// import 'package:test_sa/new_views/common_widgets/app_lazy_loading.dart'; +// import 'package:test_sa/new_views/common_widgets/app_text_form_field.dart'; +// import 'package:test_sa/new_views/common_widgets/default_app_bar.dart'; +// import 'package:test_sa/new_views/common_widgets/single_item_drop_down_menu.dart'; +// +// class MedicalGasItemsListView extends StatelessWidget { +// final List itemsList; +// +// MedicalGasItemsListView({ +// super.key, +// required this.itemsList, +// }); +// +// late AssetDeliveryProvider assetDeliveryProvider; +// +// @override +// Widget build(BuildContext context) { +// // return ListView.separated( +// // separatorBuilder: (_, __) => 12.height, +// // itemCount: itemsList.length, +// // shrinkWrap: true, +// // itemBuilder: (context, index) { +// // AttributeInfo model = itemsList[index]; +// // return AppTextFormField( +// // labelText: model.itemName, +// // hintText: 'Enter Quantity'.addTranslation, +// // backgroundColor: AppColor.fieldBgColor(context), +// // initialValue: model.requestedQuantity != null ? model.requestedQuantity.toString() : '', +// // textAlign: TextAlign.center, +// // enable: true, +// // textInputType: TextInputType.number, +// // labelStyle: AppTextStyles.textFieldLabelStyle, +// // showShadow: false, +// // onChange: (value) { +// // if (value.isNotEmpty) { +// // model.requestedQuantity = int.tryParse(value); +// // } +// // }, +// // style: Theme.of(context).textTheme.titleMedium, +// // ); +// // }, +// // ); +// } +// } +// +// // class ItemCard extends StatelessWidget { +// // final AttributeInfo model; +// // final int index; +// // +// // const ItemCard({ +// // super.key, +// // required this.model, +// // required this.index, +// // }); +// // +// // @override +// // Widget build(BuildContext context) { +// // return AppTextFormField( +// // labelText: model.itemName, +// // hintText: 'Enter Quantity'.addTranslation, +// // backgroundColor: AppColor.fieldBgColor(context), +// // initialValue: model.requestedQuantity != null ? model.requestedQuantity.toString() : '', +// // textAlign: TextAlign.center, +// // enable: true, +// // textInputType: TextInputType.number, +// // labelStyle: AppTextStyles.textFieldLabelStyle, +// // showShadow: false, +// // onChange: (value) { +// // if (value.isNotEmpty) { +// // model.requestedQuantity = int.tryParse(value); +// // } +// // }, +// // style: Theme.of(context).textTheme.titleMedium, +// // ); +// // } +// // } diff --git a/lib/modules/medical_gas_inspection/models/delivery_notes_form_model.dart b/lib/modules/medical_gas_inspection/models/delivery_notes_form_model.dart new file mode 100644 index 00000000..5b86859c --- /dev/null +++ b/lib/modules/medical_gas_inspection/models/delivery_notes_form_model.dart @@ -0,0 +1,92 @@ +import 'package:test_sa/models/generic_attachment_model.dart'; +import 'package:test_sa/modules/medical_gas_inspection/models/medical_gas_data_model.dart'; + +class DeliveryNotesFormModel { + int? id; + DateTime? deliveredDate; + String? deliveryNoteNumber; + bool? isPressureChecked; + bool? isInspectedGasLeak; + bool? isSubmitted; + + List gasDeliveredQuantityDtos = []; + List deliveredItemList = []; + List attachments = []; + + DeliveryNotesFormModel({ + this.id, + this.deliveredDate, + this.deliveryNoteNumber, + this.isPressureChecked, + this.isInspectedGasLeak, + this.isSubmitted, + List? gasDeliveredQuantityDtos, + List? deliveredItemList, + List? attachments, + }) { + this.gasDeliveredQuantityDtos = gasDeliveredQuantityDtos ?? []; + this.deliveredItemList = deliveredItemList ?? []; + this.attachments = attachments ?? []; + } + + DeliveryNotesFormModel.fromJson(Map json) { + id = json['id']; + deliveredDate = json['deliveredDate'] != null ? DateTime.parse(json['deliveredDate']) : null; + deliveryNoteNumber = json['deliveryNoteNumber']; + isPressureChecked = json['isPressureChecked']; + isInspectedGasLeak = json['isInspectedGasLeak']; + isSubmitted = json['isSubmitted']; + if (json['gasDeliveredQuantityDtos'] != null) { + gasDeliveredQuantityDtos = []; + json['gasDeliveredQuantityDtos'].forEach((v) { + gasDeliveredQuantityDtos.add(GasDeliveredQuantityModel.fromJson(v)); + }); + } + + if (json['cUMedicalGasDeliveryNoteAttachmentDtos'] != null) { + attachments = []; + json['cUMedicalGasDeliveryNoteAttachmentDtos'].forEach((v) { + attachments.add(GenericAttachmentModel.fromJson(v)); + }); + } + } + + Map toJson() { + return { + 'id': id, + 'deliveredDate': deliveredDate?.toIso8601String(), + 'deliveryNoteNumber': deliveryNoteNumber, + 'isPressureChecked': isPressureChecked, + 'isInspectedGasLeak': isInspectedGasLeak, + 'isSubmitted': isSubmitted, + 'gasDeliveredQuantityDtos': gasDeliveredQuantityDtos.map((e) => e.toJson()).toList(), + 'cUMedicalGasDeliveryNoteAttachmentDtos': attachments.map((e) => e.toJson()).toList(), + }; + } +} + +class GasDeliveredQuantityModel { + int? id; + num? medicalGasAttributeId; + num? deliveredQuantity; + + GasDeliveredQuantityModel({ + this.id, + this.medicalGasAttributeId, + this.deliveredQuantity, + }); + + GasDeliveredQuantityModel.fromJson(Map json) { + id = json['id']; + medicalGasAttributeId = json['medicalGasAttributeId']; + deliveredQuantity = json['deliveredQuantity']; + } + + Map toJson() { + return { + 'id': id, + 'medicalGasAttributeId': medicalGasAttributeId, + 'deliveredQuantity': deliveredQuantity, + }; + } +} diff --git a/lib/modules/medical_gas_inspection/models/medical_gas_data_model.dart b/lib/modules/medical_gas_inspection/models/medical_gas_data_model.dart new file mode 100644 index 00000000..01dc4a7b --- /dev/null +++ b/lib/modules/medical_gas_inspection/models/medical_gas_data_model.dart @@ -0,0 +1,169 @@ +import 'package:test_sa/models/base.dart'; +import 'package:test_sa/models/generic_attachment_model.dart'; +import 'package:test_sa/models/lookup.dart'; + +class MedicalGasDataModel { + int? id; + String? requestNumber; + String? requestedBy; + String? requestedDate; + int? requestOrderTypeId; + String? requestOrderType; + int? itemTypeId; + String? itemType; + int? siteId; + String? site; + int? supplierId; + String? supplier; + String? contact; + String? email; + bool? isSubmitted; + String? requestOrderStatus; + bool? isPressureChecked; + bool? isInspectedGasLeak; + Lookup? requestStatus; + DateTime? deliveredDate; + String? deliveryNote; + + /// ✅ non-nullable lists + List requestDetailDtos = []; + List deliveryNoteAttachmentDto = []; + + MedicalGasDataModel({ + this.id, + this.requestNumber, + this.requestedBy, + this.requestedDate, + this.requestOrderTypeId, + this.requestOrderType, + this.itemTypeId, + this.itemType, + this.siteId, + this.site, + this.requestStatus, + this.supplierId, + this.supplier, + this.contact, + this.email, + this.isSubmitted, + this.requestOrderStatus, + this.isPressureChecked, + this.isInspectedGasLeak, + this.deliveredDate, + this.deliveryNote, + List? requestDetailDtos, + List? deliveryNoteAttachmentDto, + }) { + this.requestDetailDtos = requestDetailDtos ?? []; + this.deliveryNoteAttachmentDto = deliveryNoteAttachmentDto ?? []; + } + + MedicalGasDataModel.fromJson(Map json) { + id = json['id']; + requestNumber = json['requestNumber']; + requestedBy = json['requestedBy']; + requestedDate = json['requestedDate']; + requestOrderTypeId = json['requestOrderTypeId']; + requestOrderType = json['requestOrderType']; + itemTypeId = json['itemTypeId']; + itemType = json['itemType']; + siteId = json['siteId']; + site = json['site']; + supplierId = json['supplierId']; + supplier = json['supplier']; + contact = json['contact']; + email = json['email']; + isSubmitted = json['isSubmitted']; + deliveryNote = json['deliveryNote']; + requestOrderStatus = json['requestOrderStatus']; + isPressureChecked = json['isPressureChecked']; + isInspectedGasLeak = json['isInspectedGasLeak']; + deliveredDate = json['deliveredDate'] != null ? DateTime.parse(json['deliveredDate']) : null; + requestStatus = json['requestOrderStatusDto'] != null ? Lookup.fromJson(json['requestOrderStatusDto']) : null; + if (json['requestDetailDtos'] != null) { + requestDetailDtos = []; + json['requestDetailDtos'].forEach((v) { + requestDetailDtos.add(MedicalGasRequestDetailModel.fromJson(v)); + }); + } + + if (json['deliveryNoteAttachmentDto'] != null) { + deliveryNoteAttachmentDto = []; + json['deliveryNoteAttachmentDto'].forEach((v) { + deliveryNoteAttachmentDto.add(GenericAttachmentModel.fromJson(v)); + }); + } + } + + Map toJson() { + return { + 'id': id, + 'requestNumber': requestNumber, + 'requestedBy': requestedBy, + 'requestedDate': requestedDate, + 'requestOrderTypeId': requestOrderTypeId, + 'requestOrderType': requestOrderType, + 'itemTypeId': itemTypeId, + 'itemType': itemType, + 'siteId': siteId, + 'site': site, + 'supplierId': supplierId, + 'deliveryNote': deliveryNote, + 'supplier': supplier, + 'contact': contact, + 'email': email, + 'isSubmitted': isSubmitted, + 'requestOrderStatus': requestOrderStatus, + 'isPressureChecked': isPressureChecked, + 'isInspectedGasLeak': isInspectedGasLeak, + 'deliveredDate': deliveredDate?.toIso8601String(), + 'requestDetailDtos': requestDetailDtos.map((e) => e.toJson()).toList(), + 'requestOrderStatusDto': requestStatus?.toJson(), + 'deliveryNoteAttachmentDto': deliveryNoteAttachmentDto.map((e) => e.toJson()).toList(), + }; + } +} + +class MedicalGasRequestDetailModel extends Base { + int? id; + int? medicalGasAttributeId; + String? itemName; + String? oracleName; + String? oracleCode; + num? requestedQuantity; + num? deliveredQuantity; + + MedicalGasRequestDetailModel({ + this.id, + this.medicalGasAttributeId, + this.itemName, + this.oracleName, + this.oracleCode, + this.requestedQuantity, + this.deliveredQuantity, + }) : super(identifier: id?.toString(), name: itemName); + + MedicalGasRequestDetailModel.fromJson(Map json) { + id = json['id']; + medicalGasAttributeId = json['medicalGasAttributeId']; + itemName = json['itemName']; + identifier = id.toString(); + name = itemName; + oracleName = json['oracleName']; + oracleCode = json['oracleCode']; + requestedQuantity = json['requestedQuantity']; + deliveredQuantity = json['deliveredQuantity']; + } + + Map toJson() { + return { + 'id': id, + 'medicalGasAttributeId': medicalGasAttributeId, + 'itemName': itemName, + 'oracleName': oracleName, + 'oracleCode': oracleCode, + 'requestedQuantity': requestedQuantity, + 'deliveredQuantity': deliveredQuantity, + }; + } +} diff --git a/lib/modules/medical_gas_inspection/models/medical_gas_form_model.dart b/lib/modules/medical_gas_inspection/models/medical_gas_form_model.dart new file mode 100644 index 00000000..a3f08ac1 --- /dev/null +++ b/lib/modules/medical_gas_inspection/models/medical_gas_form_model.dart @@ -0,0 +1,87 @@ +import 'package:test_sa/models/lookup.dart'; +import 'package:test_sa/models/new_models/site.dart'; +import 'package:test_sa/modules/loan_module/models/medical_department_model.dart'; +import 'package:test_sa/modules/medical_gas_inspection/models/medical_gas_supplier_model.dart'; + +class MedicalGasFormModel { + int? id; + int? requestOrderTypeId; + Lookup? orderType; + Lookup? itemType; + int? itemTypeId; + int? siteId; + Site? site; + MedicalDepartmentModel? department; + MedicalGasSupplierModel? supplier; + int? supplierId; + bool? isSubmitted; + List? gasRequestDetail; + + MedicalGasFormModel({ + this.id, + this.requestOrderTypeId, + this.itemTypeId, + this.siteId, + this.supplierId, + this.supplier, + this.isSubmitted, + this.orderType, + this.itemType, + this.site, + this.department, + this.gasRequestDetail, + }); + + MedicalGasFormModel.fromJson(Map json) { + id = json['id']; + requestOrderTypeId = json['requestOrderTypeId']; + itemTypeId = json['itemTypeId']; + siteId = json['siteId']; + supplierId = json['supplierId']; + isSubmitted = json['isSubmitted']; + if (json['gasRequestDetailDtos'] != null) { + gasRequestDetail = []; + json['gasRequestDetailDtos'].forEach((v) { + gasRequestDetail!.add(MedicalGasFormDetailModel.fromJson(v)); + }); + } + } + + Map toJson() { + return { + 'id': id ?? 0, + 'requestOrderTypeId': orderType?.id, + 'itemTypeId': itemType?.id, + 'siteId': site?.id, + 'supplierId': supplier?.id, + 'isSubmitted': isSubmitted, + 'gasRequestDetailDtos': gasRequestDetail?.map((e) => e.toJson()).toList(), + }; + } +} + +class MedicalGasFormDetailModel { + int? id; + int? medicalGasAttributeId; + num? requestedQuantity; + + MedicalGasFormDetailModel({ + this.id, + this.medicalGasAttributeId, + this.requestedQuantity, + }); + + MedicalGasFormDetailModel.fromJson(Map json) { + id = json['id']; + medicalGasAttributeId = json['medicalGasAttributeId']; + requestedQuantity = json['requestedQuantity']; + } + + Map toJson() { + return { + 'id': id, + 'medicalGasAttributeId': medicalGasAttributeId, + 'requestedQuantity': requestedQuantity??0, + }; + } +} diff --git a/lib/modules/medical_gas_inspection/models/medical_gas_supplier_model.dart b/lib/modules/medical_gas_inspection/models/medical_gas_supplier_model.dart new file mode 100644 index 00000000..17ca804f --- /dev/null +++ b/lib/modules/medical_gas_inspection/models/medical_gas_supplier_model.dart @@ -0,0 +1,72 @@ + + +import 'package:test_sa/models/base.dart'; + +class MedicalGasSupplierModel extends Base { + int? id; + String? supplier; + String? supplierEmail; + String? supplierContact; + List? attributeInfo; + + MedicalGasSupplierModel({this.id, this.supplier, this.supplierContact, this.supplierEmail, this.attributeInfo}) : super(identifier: id?.toString() ?? '', name: supplier); + + MedicalGasSupplierModel.fromJson(Map json) { + id = json['id']; + identifier = id?.toString() ?? ''; + supplier = json['supplier']; + name=supplier; + supplierEmail = json['supplierEmail']; + supplierContact = json['supplierContact']; + if (json['attributeInfoDtos'] != null) { + attributeInfo = []; + json['attributeInfoDtos'].forEach((v) { + attributeInfo!.add(AttributeInfo.fromJson(v)); + }); + } + } + + Map toJson() { + return { + 'id': id, + 'supplier': supplier, + 'supplierEmail': supplierEmail, + 'supplierContact': supplierContact, + 'attributeInfoDtos': attributeInfo?.map((e) => e.toJson()).toList(), + }; + } +} + +class AttributeInfo { + int? id; + int? medicalGasAttributeId; + num? requestedQuantity; + String? itemName; + String? oracleName; + String? oracleCode; + + AttributeInfo({this.id, this.medicalGasAttributeId, this.requestedQuantity, this.itemName, this.oracleName, this.oracleCode}); + + AttributeInfo.fromJson(Map json) { + id = json['id']; + medicalGasAttributeId = json['medicalGasAttributeId']; + requestedQuantity = json['requestedQuantity']; + itemName = json['itemName']; + oracleName = json['oracleName']; + oracleCode = json['oracleCode']; + } + + Map toJson() { + //{ + // "id": 0, + // "medicalGasAttributeId": 0, + // "requestedQuantity": 0 + // } + return { + 'id': id, + 'medicalGasAttributeId': medicalGasAttributeId, + 'requestedQuantity': requestedQuantity, + // 'oracleCode': oracleCode, + }; + } +} diff --git a/lib/modules/medical_gas_inspection/providers/item_type_provider.dart b/lib/modules/medical_gas_inspection/providers/item_type_provider.dart new file mode 100644 index 00000000..e7c38208 --- /dev/null +++ b/lib/modules/medical_gas_inspection/providers/item_type_provider.dart @@ -0,0 +1,33 @@ +import 'dart:convert'; +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/lookup.dart'; +import 'package:test_sa/providers/loading_list_notifier.dart'; + +class MedicalGasItemTypeProvider extends LoadingListNotifier { + @override + Future getData({int? id}) async { + if (loading == true) return -2; + loading = true; + notifyListeners(); + loading = true; + notifyListeners(); + try { + Response response = await ApiManager.instance.get(URLs.itemTypeLookUp); + stateCode = response.statusCode; + if (response.statusCode >= 200 && response.statusCode < 300) { + 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; + } + } +} diff --git a/lib/modules/medical_gas_inspection/providers/medical_gas_inspection_provider.dart b/lib/modules/medical_gas_inspection/providers/medical_gas_inspection_provider.dart new file mode 100644 index 00000000..a28c76ee --- /dev/null +++ b/lib/modules/medical_gas_inspection/providers/medical_gas_inspection_provider.dart @@ -0,0 +1,119 @@ +import 'dart:convert'; +import 'dart:developer'; +import 'package:flutter/material.dart'; +import 'package:test_sa/controllers/api_routes/api_manager.dart'; +import 'package:test_sa/controllers/api_routes/urls.dart'; +import 'package:test_sa/modules/medical_gas_inspection/models/delivery_notes_form_model.dart'; +import 'package:test_sa/modules/medical_gas_inspection/models/medical_gas_data_model.dart'; +import 'package:test_sa/modules/medical_gas_inspection/models/medical_gas_form_model.dart'; +import 'package:test_sa/modules/medical_gas_inspection/models/medical_gas_supplier_model.dart'; + +class MedicalGasInspectionProvider extends ChangeNotifier { + final pageItemNumber = 10; + final searchPageItemNumber = 10; + int pageNo = 1; + + void reset() { + pageNo = 1; + stateCode = null; + } + + int? stateCode; + bool isDetailLoading = false; + bool nextPage = false; + bool isLoading = false; + bool isGasInfoLoading = false; + + Future getMedicalGasById({int? requestId}) async { + MedicalGasDataModel? assetDeliveryDataModel = MedicalGasDataModel(); + + try { + isLoading = true; + notifyListeners(); + final response = await ApiManager.instance.get(URLs.getMedicalGasById + "?medicalGasRequestId=$requestId"); + stateCode = response.statusCode; + if (response.statusCode >= 200 && response.statusCode < 300) { + assetDeliveryDataModel = MedicalGasDataModel.fromJson(json.decode(response.body)["data"]); + } else { + assetDeliveryDataModel = null; + } + isLoading = false; + notifyListeners(); + return assetDeliveryDataModel; + } catch (e) { + log("getMedicalGas details [error] : $e"); + isLoading = false; + assetDeliveryDataModel = null; + notifyListeners(); + return assetDeliveryDataModel; + } + } + + Future saveMedicalGas({ + required MedicalGasFormModel model, + }) async { + isLoading = true; + try { + final response = await ApiManager.instance.post(URLs.addMedicalGasRequest, body: model.toJson()); + stateCode = response.statusCode; + if (response.statusCode >= 200 && response.statusCode < 300) { + isLoading = false; + notifyListeners(); + return true; + } else { + isLoading = false; + notifyListeners(); + return false; + } + } catch (error) { + isLoading = false; + notifyListeners(); + return false; + } + } + + Future getMedicalGasInfo({int? supplierId, int? itemTypeId, num? siteId}) async { + MedicalGasSupplierModel? supplierInfo; + Map payload = {"supplierId": supplierId, "itemTypeId": itemTypeId, "siteId": siteId}; + try { + isGasInfoLoading = true; + notifyListeners(); + final response = await ApiManager.instance.post("${URLs.getMedicalGasInfoBySupplier}", body: payload); + stateCode = response.statusCode; + if (response.statusCode >= 200 && response.statusCode < 300) { + final jsonData = json.decode(response.body)["data"]; + supplierInfo = MedicalGasSupplierModel.fromJson(jsonData); + } + isGasInfoLoading = false; + notifyListeners(); + return supplierInfo; + } catch (e) { + log("get Supplier List [error] : $e"); + isGasInfoLoading = false; + notifyListeners(); + return supplierInfo; + } + } + Future updatedDeliveryNotes({ + required DeliveryNotesFormModel model, + }) async { + isLoading = true; + try { + final response = await ApiManager.instance.post(URLs.updateDeliveryNote, body: model.toJson()); + stateCode = response.statusCode; + if (response.statusCode >= 200 && response.statusCode < 300) { + isLoading = false; + notifyListeners(); + return true; + } else { + isLoading = false; + notifyListeners(); + return false; + } + } catch (error) { + isLoading = false; + notifyListeners(); + return false; + } + } +} diff --git a/lib/modules/medical_gas_inspection/providers/medical_gas_supplier_provider.dart b/lib/modules/medical_gas_inspection/providers/medical_gas_supplier_provider.dart new file mode 100644 index 00000000..d7127726 --- /dev/null +++ b/lib/modules/medical_gas_inspection/providers/medical_gas_supplier_provider.dart @@ -0,0 +1,34 @@ +import 'dart:convert'; +import 'dart:developer'; + +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/lookup.dart'; +import 'package:test_sa/modules/medical_gas_inspection/models/medical_gas_supplier_model.dart'; +import 'package:test_sa/providers/loading_list_notifier.dart'; + +class MedicalGasSupplierProvider extends LoadingListNotifier { + @override + Future getData({int? id}) async { + loading = true; + notifyListeners(); + Response response; + try { + response = await ApiManager.instance.get(URLs.getMedicalGasSupplierList); + } catch (error) { + loading = false; + stateCode = -1; + notifyListeners(); + return -1; + } + stateCode = response.statusCode; + if (response.statusCode >= 200 && response.statusCode < 300) { + List listJson = json.decode(response.body)["data"]; + items = listJson.map((supplier) => MedicalGasSupplierModel.fromJson(supplier)).toList(); + } + loading = false; + notifyListeners(); + return response.statusCode; + } +} diff --git a/lib/modules/medical_gas_inspection/providers/order_type_provider.dart b/lib/modules/medical_gas_inspection/providers/order_type_provider.dart new file mode 100644 index 00000000..32d19716 --- /dev/null +++ b/lib/modules/medical_gas_inspection/providers/order_type_provider.dart @@ -0,0 +1,33 @@ +import 'dart:convert'; +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/lookup.dart'; +import 'package:test_sa/providers/loading_list_notifier.dart'; + +class MedicalGasOrderTypeProvider extends LoadingListNotifier { + @override + Future getData({int? id}) async { + if (loading == true) return -2; + loading = true; + notifyListeners(); + loading = true; + notifyListeners(); + try { + Response response = await ApiManager.instance.get(URLs.orderTypeLookUp); + stateCode = response.statusCode; + if (response.statusCode >= 200 && response.statusCode < 300) { + 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; + } + } +} diff --git a/lib/modules/medical_gas_inspection/update_delivery_notes_page.dart b/lib/modules/medical_gas_inspection/update_delivery_notes_page.dart new file mode 100644 index 00000000..c87e511e --- /dev/null +++ b/lib/modules/medical_gas_inspection/update_delivery_notes_page.dart @@ -0,0 +1,288 @@ +import 'package:flutter/material.dart'; +import 'package:provider/provider.dart'; +import 'package:test_sa/extensions/context_extension.dart'; +import 'package:test_sa/extensions/int_extensions.dart'; +import 'package:test_sa/extensions/string_extensions.dart'; +import 'package:test_sa/extensions/text_extensions.dart'; +import 'package:test_sa/extensions/widget_extensions.dart'; +import 'package:test_sa/modules/cm_module/views/components/action_button/footer_action_button.dart'; +import 'package:test_sa/modules/medical_gas_inspection/models/delivery_notes_form_model.dart'; +import 'package:test_sa/modules/medical_gas_inspection/models/medical_gas_data_model.dart'; +import 'package:test_sa/modules/medical_gas_inspection/providers/medical_gas_inspection_provider.dart'; +import 'package:test_sa/new_views/app_style/app_color.dart'; +import 'package:test_sa/new_views/common_widgets/app_filled_button.dart'; +import 'package:test_sa/new_views/common_widgets/app_lazy_loading.dart'; +import 'package:test_sa/new_views/common_widgets/app_text_form_field.dart'; +import 'package:test_sa/new_views/common_widgets/default_app_bar.dart'; +import 'package:test_sa/new_views/common_widgets/multiple_item_drop_down_menu.dart'; +import 'package:test_sa/providers/loading_list_notifier.dart'; +import 'package:test_sa/views/widgets/date_and_time/date_picker.dart'; +import 'package:test_sa/views/widgets/images/multi_image_picker.dart'; + +class UpdateDeliveryNotes extends StatefulWidget { + final MedicalGasDataModel? dataModel; + + UpdateDeliveryNotes({Key? key, required this.dataModel}) : super(key: key); + + @override + _UpdateDeliveryNotesState createState() { + return _UpdateDeliveryNotesState(); + } +} + +class _UpdateDeliveryNotesState extends State { + DeliveryNotesFormModel formModel = DeliveryNotesFormModel(); + late MedicalGasInspectionProvider medicalGasInspectionProvider; + bool pressureTestAcknowledgement = false; + bool leakTestAcknowledgement = false; + List selectedItemList = []; + + @override + void initState() { + super.initState(); + medicalGasInspectionProvider = Provider.of(context, listen: false); + _populateFormData(); + } + + @override + void dispose() { + super.dispose(); + } + + _populateFormData() { + if (widget.dataModel != null) { + MedicalGasDataModel dataModel = widget.dataModel!; + formModel = DeliveryNotesFormModel( + id: dataModel.id, + deliveredItemList: dataModel.requestDetailDtos, + isInspectedGasLeak: dataModel.isInspectedGasLeak, + isPressureChecked: dataModel.isPressureChecked, + deliveredDate: dataModel.deliveredDate, + attachments: dataModel.deliveryNoteAttachmentDto, + isSubmitted: dataModel.isSubmitted, + deliveryNoteNumber: dataModel.deliveryNote); + //Need to Confirm this condition + selectedItemList = dataModel.requestDetailDtos.where((item) => item.deliveredQuantity != null && item.deliveredQuantity! > 0).toList(); + setState(() {}); + } + } + + @override + Widget build(BuildContext context) { + return Scaffold( + appBar: const DefaultAppBar( + title: "Upload Delivery Note", + // onWillPopScope: () { + // _update(context: context); + // }, + ), + body: SafeArea( + child: Column( + children: [ + ListView( + padding: const EdgeInsets.all(16), + children: [ + Column( + crossAxisAlignment: CrossAxisAlignment.start, + children: [ + ADatePicker( + label: "Delivered Date", + hideShadow: true, + backgroundColor: AppColor.fieldBgColor(context), + from: DateTime.now().subtract(const Duration(days: 365 * 3)), + date: formModel.deliveredDate, + formatDateWithTime: true, + onDatePicker: (selectedDate) { + showTimePicker( + context: context, + initialTime: TimeOfDay.now(), + ).then((selectedTime) { + if (selectedTime != null) { + formModel.deliveredDate = DateTime(selectedDate.year, selectedDate.month, selectedDate.day, selectedTime.hour, selectedTime.minute); + setState(() {}); + } + }); + }, + ), + 16.height, + MultipleItemDropDownMenu( + context: context, + showAsBottomSheet: true, + backgroundColor: AppColor.neutral100, + showShadow: false, + showCancel: true, + requestById: context.userProvider.user?.clientId, + title: 'Delivered Items'.addTranslation, + staticData: formModel.deliveredItemList, + initialValue: selectedItemList, + onSelect: (value) { + if ((value ?? []).isNotEmpty) { + WidgetsBinding.instance.addPostFrameCallback((_) { + if (!mounted) return; + setState(() { + selectedItemList = value ?? []; + }); + }); + } + }, + ), + if (selectedItemList.isNotEmpty) ...[ + 8.height, + ListView.separated( + separatorBuilder: (_, __) => 12.height, + itemCount: selectedItemList.length, + shrinkWrap: true, + physics: const NeverScrollableScrollPhysics(), + itemBuilder: (context, index) { + MedicalGasRequestDetailModel model = selectedItemList[index]; + return AppTextFormField( + labelText: '${model.name} (Req Qty =${model.requestedQuantity})', + hintText: 'Enter Delivered Quantity'.addTranslation, + backgroundColor: AppColor.fieldBgColor(context), + initialValue: model.deliveredQuantity != null ? model.deliveredQuantity?.toInt().toString() : '', + textAlign: TextAlign.center, + enable: true, + textInputType: TextInputType.number, + labelStyle: AppTextStyles.textFieldLabelStyle, + showShadow: false, + onChange: (value) { + if (value.isNotEmpty) { + model.deliveredQuantity = double.tryParse(value); + } + }, + style: Theme.of(context).textTheme.titleMedium, + ); + }, + ) + ], + 16.height, + AppTextFormField( + initialValue: formModel.deliveryNoteNumber, + labelText: "Delivery Notes", + validator: (value) { + if ((value ?? "").isEmpty) return "Mandatory"; + return null; + }, + backgroundColor: AppColor.fieldBgColor(context), + labelStyle: AppTextStyles.textFieldLabelStyle.copyWith(color: AppColor.textColor(context)), + floatingLabelStyle: AppTextStyles.textFieldLabelStyle.copyWith(color: AppColor.textColor(context)), + showShadow: false, + textInputType: TextInputType.multiline, + makeMultiLinesNull: true, + onChange: (value) { + formModel.deliveryNoteNumber = value; + }, + ), + 16.height, + AttachmentPicker( + label: 'Upload Attachment', + attachment: formModel.attachments, + buttonColor: AppColor.primary10, + // showAsListView: true, + onlyImages: false, + buttonIcon: 'attachment_icon'.toSvgAsset( + color: AppColor.primary10, + ), + ), + 16.height, + //should create a reusable widget. + Row( + children: [ + Checkbox( + value: formModel.isPressureChecked, + visualDensity: const VisualDensity(horizontal: -4.0, vertical: -4.0), + activeColor: AppColor.blueStatus(context), + materialTapTargetSize: MaterialTapTargetSize.shrinkWrap, + onChanged: (value) { + setState(() { + formModel.isPressureChecked = value!; + }); + }), + 12.width, + "I Acknowledge that the received medical gases cylinders have been tested for pressure." + .addTranslation + .bodyText(context) + .custom(color: context.isDark ? AppColor.primary50 : AppColor.neutral120) + .expanded, + ], + ), + 8.height, + Row( + // mainAxisAlignment: MainAxisAlignment.start, + crossAxisAlignment: CrossAxisAlignment.start, + children: [ + Checkbox( + value: formModel.isInspectedGasLeak, + visualDensity: const VisualDensity(horizontal: -4.0, vertical: -4.0), + activeColor: AppColor.blueStatus(context), + materialTapTargetSize: MaterialTapTargetSize.shrinkWrap, + onChanged: (value) { + setState(() { + formModel.isInspectedGasLeak = value!; + }); + }), + 12.width, + "I Acknowledge that the received medical gases cylinders have been inspected for leak test." + .addTranslation + .bodyText(context) + .custom(color: context.isDark ? AppColor.primary50 : AppColor.neutral120) + .expanded, + ], + ), + ], + ).toShadowContainer(context, padding: 12), + ], + ).expanded, + FooterActionButton.footerContainer( + context: context, + child: Row( + children: [ + AppFilledButton( + buttonColor: AppColor.primary10, + label: 'Save'.addTranslation, + onPressed: () { + _update(context: context); + }, + // buttonColor: AppColor.primary10, + ).expanded, + 8.width, + AppFilledButton( + buttonColor: AppColor.primary10, + label: 'Submit'.addTranslation, + onPressed: () { + _update(context: context, isSubmitted: true); + }, + // buttonColor: AppColor.primary10, + ).expanded, + ], + ), + ), + ], + ), + )); + // .handlePopScope( + // cxt: context, + // onSave: () { + // _update(context: context); + // }); + } + + void _update({required BuildContext context, bool isSubmitted = false}) async { + formModel.gasDeliveredQuantityDtos = []; + formModel.isSubmitted = isSubmitted; + for (var item in selectedItemList) { + formModel.gasDeliveredQuantityDtos.add(GasDeliveredQuantityModel( + id: widget.dataModel != null ? item.id : 0, + medicalGasAttributeId: item.medicalGasAttributeId ?? item.id, + deliveredQuantity: item.deliveredQuantity, + )); + } + showDialog(context: context, barrierDismissible: false, builder: (context) => const AppLazyLoading()); + await medicalGasInspectionProvider.updatedDeliveryNotes(model: formModel).then((status) async { + Navigator.pop(context); + if (status) { + Navigator.pop(context, true); + } + }); + } +} diff --git a/lib/new_views/app_style/app_color.dart b/lib/new_views/app_style/app_color.dart index 8adc321d..8f2ab1c6 100644 --- a/lib/new_views/app_style/app_color.dart +++ b/lib/new_views/app_style/app_color.dart @@ -1,3 +1,5 @@ +import 'dart:developer'; + import 'package:flutter/material.dart'; import 'package:test_sa/extensions/context_extension.dart'; @@ -119,6 +121,8 @@ class AppColor { return orange60; case "high priority": return white10; + case "emergency": + return white10; case "yes": return white10; case "low priority": @@ -134,6 +138,8 @@ class AppColor { switch ((status).toLowerCase()) { case "in progress": return white936; + case "waiting for delivery": + return white936; case "new": return primary63; case "open": @@ -193,6 +199,14 @@ class AppColor { return red30; case "returned": return red30; + case "waiting for delivery": + return orange30; + case "waiting for medical gas specialist review": + return orange30; + case "reviewed": + return orange30; + case "returned for correction": + return orange30; default: return Colors.white; } @@ -210,6 +224,8 @@ class AppColor { return greenStatus(context); case "high priority": return redStatus(context); + case "emergency": + return redStatus(context); case "yes": return redStatus(context); case "low priority": diff --git a/lib/new_views/pages/land_page/create_request_type_bottom_sheet.dart b/lib/new_views/pages/land_page/create_request_type_bottom_sheet.dart index 030b2895..0bd10a54 100644 --- a/lib/new_views/pages/land_page/create_request_type_bottom_sheet.dart +++ b/lib/new_views/pages/land_page/create_request_type_bottom_sheet.dart @@ -13,6 +13,7 @@ import 'package:test_sa/modules/cm_module/create_cm_request.dart'; import 'package:test_sa/modules/internal_audit_module/pages/equipment_internal_audit/create_equipment_internal_audit_form.dart'; import 'package:test_sa/modules/internal_audit_module/pages/system_internal_audit/create_system_internal_audit_form.dart'; import 'package:test_sa/modules/loan_module/pages/create_loan_request_page.dart'; +import 'package:test_sa/modules/medical_gas_inspection/create_medical_gas_request_page.dart'; import 'package:test_sa/modules/tm_module/device_transfer/create_device_transfer_request.dart'; import 'package:test_sa/modules/tm_module/tasks/create_task_view.dart'; import 'package:test_sa/modules/traf_module/create_traf_request_page.dart'; @@ -121,8 +122,13 @@ class CreateRequestModel { if (Provider.of(context, listen: false).engineerCanCreateCM) { list.add(CreateRequestModel(context.translation.correctiveMaintenance, "add_icon", CreateCMRequest.id)); } + //TODO uncommit this to enable task. list.add(CreateRequestModel(context.translation.task, "add_icon", CreateTaskView.id)); + //Need to add check from permission Api. + // if (Provider.of(context, listen: false).engineerCanCreateCM) { + list.add(CreateRequestModel('Medical Gas'.addTranslation, "add_icon", CreateMedicalGasRequestPage.id)); + // } } else { list.add(CreateRequestModel(context.translation.correctiveMaintenance, "add_icon", CreateCMRequest.id)); list.add(CreateRequestModel(context.translation.gasRefill, "add_icon", GasRefillRequestForm.routeName)); diff --git a/lib/new_views/pages/land_page/my_request/my_requests_page.dart b/lib/new_views/pages/land_page/my_request/my_requests_page.dart index d482356e..1823b10a 100644 --- a/lib/new_views/pages/land_page/my_request/my_requests_page.dart +++ b/lib/new_views/pages/land_page/my_request/my_requests_page.dart @@ -70,6 +70,7 @@ class _MyRequestsPageState extends State { requestsList.add(Request(11, 'System Internal Audit')); //Need to be added for new user role commissioning engineer requestsList.add(Request(13, "Asset Delivery")); + requestsList.add(Request(14, "Medical Gas Inspection")); } requestsList.add(Request(12, "Loan Equipment")); diff --git a/lib/new_views/pages/land_page/requests/request_paginated_listview.dart b/lib/new_views/pages/land_page/requests/request_paginated_listview.dart index 62580009..f4d83656 100644 --- a/lib/new_views/pages/land_page/requests/request_paginated_listview.dart +++ b/lib/new_views/pages/land_page/requests/request_paginated_listview.dart @@ -6,6 +6,7 @@ import 'package:test_sa/modules/internal_audit_module/pages/equipment_internal_a import 'package:test_sa/modules/internal_audit_module/pages/system_internal_audit/system_internal_audit_item_view.dart'; import 'package:test_sa/modules/asset_inventory_module/pages/inventory_session_item_view.dart'; import 'package:test_sa/modules/loan_module/pages/loan_equipment_item_view.dart'; +import 'package:test_sa/modules/medical_gas_inspection/medical_gas_inspection_item_view.dart'; import 'package:test_sa/modules/tm_module/tasks/task_request_item_view.dart'; import 'package:test_sa/modules/traf_module/traf_request_item_view.dart'; import 'package:test_sa/new_views/app_style/app_color.dart'; @@ -78,6 +79,8 @@ class RequestPaginatedListview extends StatelessWidget { return LoanEquipmentItemView(requestData: request); case 13: return AssetDeliveryItemView(requestData: request); + case 14: + return MedicalGasInspectionItemView(requestData: request); default: return Container( height: 100, diff --git a/lib/new_views/pages/land_page/widgets/request_item_view_list.dart b/lib/new_views/pages/land_page/widgets/request_item_view_list.dart index 946cb7ba..10339da7 100644 --- a/lib/new_views/pages/land_page/widgets/request_item_view_list.dart +++ b/lib/new_views/pages/land_page/widgets/request_item_view_list.dart @@ -11,6 +11,7 @@ import 'package:test_sa/modules/internal_audit_module/pages/equipment_internal_a import 'package:test_sa/modules/internal_audit_module/pages/system_internal_audit/system_internal_audit_item_view.dart'; import 'package:test_sa/modules/asset_inventory_module/pages/inventory_session_item_view.dart'; import 'package:test_sa/modules/loan_module/pages/loan_equipment_item_view.dart'; +import 'package:test_sa/modules/medical_gas_inspection/medical_gas_inspection_item_view.dart'; import 'package:test_sa/modules/tm_module/tasks/task_request_item_view.dart'; import 'package:test_sa/modules/traf_module/traf_request_item_view.dart'; import 'package:test_sa/new_views/app_style/app_color.dart'; @@ -74,6 +75,8 @@ class RequestItemViewList extends StatelessWidget { return LoanEquipmentItemView(requestDetails: list[index]); case 13: return AssetDeliveryItemView(requestDetails: list[index]); + case 14: + return MedicalGasInspectionItemView(requestDetails: list[index]); default: Container(