active medication

fatima
Fatimah.Alshammari 1 month ago
parent cb56503622
commit de8c7bc605

@ -419,7 +419,7 @@ var GET_WEIGHT_PRESSURE_RESULT_AVERAGE = 'Services/Patients.svc/REST/Patient_Get
var GET_WEIGHT_PRESSURE_RESULT = 'Services/Patients.svc/REST/Patient_GetWeightMeasurementResult';
var ADD_WEIGHT_PRESSURE_RESULT = 'Services/Patients.svc/REST/Patient_AddWeightMeasurementResult';
var ADD_ACTIVE_PRESCRIPTIONS_REPORT_BY_PATIENT_ID = 'Services/Patients.svc/Rest/GetActivePrescriptionReportByPatientID';
// var ADD_ACTIVE_PRESCRIPTIONS_REPORT_BY_PATIENT_ID = 'Services/Patients.svc/Rest/GetActivePrescriptionReportByPatientID';
var GET_CALL_INFO_HOURS_RESULT = 'Services/Doctors.svc/REST/GetCallInfoHoursResult';
var GET_CALL_REQUEST_TYPE_LOV = 'Services/Doctors.svc/REST/GetCallRequestType_LOV';
@ -727,7 +727,7 @@ const FAMILY_FILES= 'Services/Authentication.svc/REST/GetAllSharedRecordsByStatu
class ApiConsts {
static const maxSmallScreen = 660;
static AppEnvironmentTypeEnum appEnvironmentType = AppEnvironmentTypeEnum.prod;
static AppEnvironmentTypeEnum appEnvironmentType = AppEnvironmentTypeEnum.uat;
// static String baseUrl = 'https://uat.hmgwebservices.com/'; // HIS API URL UAT
@ -838,7 +838,7 @@ class ApiConsts {
static final String getAllSharedRecordsByStatus = 'Services/Authentication.svc/REST/GetAllSharedRecordsByStatus';
static final String removeFileFromFamilyMembers = 'Services/Authentication.svc/REST/ActiveDeactive_PatientFile';
static final String acceptAndRejectFamilyFile = 'Services/Authentication.svc/REST/Update_FileStatus';
static final String getActivePrescriptionsDetails = 'Services/Patients.svc/Rest/GetActivePrescriptionReportByPatientID';
// static values for Api
static final double appVersionID = 18.7;

@ -643,7 +643,7 @@ class Utils {
}
/// Widget to build an SVG from network
static Widget buildImgWithNetwork({required String url, required Color iconColor, bool isDisabled = false, double width = 24, double height = 24, BoxFit fit = BoxFit.cover}) {
static Widget buildImgWithNetwork({required String url, bool isDisabled = false, double width = 24, double height = 24, BoxFit fit = BoxFit.cover}) {
return Image.network(
url,
width: width,

@ -0,0 +1,99 @@
import 'package:dartz/dartz.dart';
import 'package:hmg_patient_app_new/features/active_prescriptions/models/active_prescriptions_response_model.dart';
import '../../core/api/api_client.dart';
import '../../core/api_consts.dart';
import '../../core/common_models/generic_api_model.dart';
import '../../core/exceptions/api_failure.dart';
import '../../services/logger_service.dart';
abstract class ActivePrescriptionsRepo {
Future<Either<Failure, GenericApiModel<dynamic>>> getActivePrescriptionsDetails();
}
class ActivePrescriptionsRepoImp implements ActivePrescriptionsRepo {
final ApiClient apiClient;
final LoggerService loggerService;
ActivePrescriptionsRepoImp({required this.loggerService, required this.apiClient});
@override
Future<Either<Failure, GenericApiModel<dynamic>>> getActivePrescriptionsDetails() async
{
try {
GenericApiModel<dynamic>? apiResponse;
Failure? failure;
await apiClient.post(
ApiConsts.getActivePrescriptionsDetails,
body: {},
onFailure: (error, statusCode, {messageStatus, failureType}) {
failure = failureType;
},
onSuccess: (response, statusCode, {messageStatus, errorMessage}) {
try {
// final list = response['GetActivePrescriptionReportByPatientIDList'];
// final prescriptionLists = list.map((item) => ActivePrescriptionsResponseModel.fromJson(item as Map<String, dynamic>)).toList().cast<ActivePrescriptionsResponseModel>();
apiResponse = GenericApiModel<dynamic>(
messageStatus: messageStatus,
statusCode: statusCode,
errorMessage: null,
data: response,
);
return ['List_ActiveGetPrescriptionReportByPatientID'];
//apiResponse;
} catch (e) {
failure = DataParsingFailure(e.toString());
}
},
);
if (failure != null) return Left(failure!);
if (apiResponse == null) return Left(ServerFailure("Unknown error"));
return Right(apiResponse!);
} catch (e) {
return Left(UnknownFailure(e.toString()));
}
}
//
// Future<Either<Failure, GenericApiModel>> getActiveMedications() {
// try {
// GenericApiModel<dynamic>? apiResponse;
// Failure? failure;
// return apiClient.post(
// ApiConsts.getActivePrescriptionsDetails,
// body: patientDeviceDataRequest,
// onFailure: (error, statusCode, {messageStatus, failureType}) {
// failure = failureType;
// },
// onSuccess: (response, statusCode, {messageStatus, errorMessage}) {
// try {
// apiResponse = GenericApiModel<dynamic>(
// messageStatus: messageStatus,
// statusCode: statusCode,
// errorMessage: errorMessage,
// data: response,
// );
// } catch (e) {
// failure = DataParsingFailure(e.toString());
// }
// },
// ).then((_) {
// if (failure != null) return Left(failure!);
// if (apiResponse == null) return Left(ServerFailure("Unknown error"));
// return Right(apiResponse!);
// });
// } catch (e) {
// return Future.value(Left(UnknownFailure(e.toString())));
// }
// }
}

@ -0,0 +1,57 @@
import 'package:flutter/material.dart';
import 'package:hmg_patient_app_new/features/active_prescriptions/models/active_prescriptions_response_model.dart';
import 'package:hmg_patient_app_new/features/active_prescriptions/active_prescriptions_repo.dart';
import 'package:hmg_patient_app_new/services/error_handler_service.dart';
class ActivePrescriptionsViewModel extends ChangeNotifier {
bool isActivePrescriptionsDetailsLoading = false;
late ActivePrescriptionsRepo activePrescriptionsRepo;
late ErrorHandlerService errorHandlerService;
// Prescription Orders Lists
List<ActivePrescriptionsResponseModel> activePrescriptionsDetailsList = [];
initActivePrescriptionsViewModel() {
getActiveMedications();
notifyListeners();
}
setPrescriptionsDetailsLoading() {
isActivePrescriptionsDetailsLoading = true;
// activePrescriptionsDetailsList.clear();
notifyListeners();
}
Future<void> getActiveMedications( {Function(dynamic)? onSuccess, Function(String)? onError})
async {
final result = await activePrescriptionsRepo.getActivePrescriptionsDetails();
result.fold(
(failure) async => await errorHandlerService.handleError(failure: failure),
(apiResponse) {
if (apiResponse.messageStatus == 2) {
// dialogService.showErrorDialog(message: apiResponse.errorMessage!, onOkPressed: () {});
} else if (apiResponse.messageStatus == 1) {
activePrescriptionsDetailsList = apiResponse.data!;
isActivePrescriptionsDetailsLoading = false;
notifyListeners();
if (onSuccess != null) {
onSuccess(apiResponse);
print(activePrescriptionsDetailsList.length);
}
}
},
);
}
}

@ -0,0 +1,149 @@
import 'dart:convert';
class ActivePrescriptionsResponseModel {
dynamic address;
int? appointmentNo;
dynamic clinic;
dynamic companyName;
int? days;
dynamic doctorName;
int? doseDailyQuantity;
String? frequency;
int? frequencyNumber;
dynamic image;
dynamic imageExtension;
dynamic imageSrcUrl;
String? imageString;
dynamic imageThumbUrl;
dynamic isCovered;
String? itemDescription;
int? itemId;
String? orderDate;
int? patientId;
dynamic patientName;
dynamic phoneOffice1;
dynamic prescriptionQr;
int? prescriptionTimes;
dynamic productImage;
String? productImageBase64;
String? productImageString;
int? projectId;
dynamic projectName;
dynamic remarks;
String? route;
String? sku;
int? scaleOffset;
String? startDate;
ActivePrescriptionsResponseModel({
this.address,
this.appointmentNo,
this.clinic,
this.companyName,
this.days,
this.doctorName,
this.doseDailyQuantity,
this.frequency,
this.frequencyNumber,
this.image,
this.imageExtension,
this.imageSrcUrl,
this.imageString,
this.imageThumbUrl,
this.isCovered,
this.itemDescription,
this.itemId,
this.orderDate,
this.patientId,
this.patientName,
this.phoneOffice1,
this.prescriptionQr,
this.prescriptionTimes,
this.productImage,
this.productImageBase64,
this.productImageString,
this.projectId,
this.projectName,
this.remarks,
this.route,
this.sku,
this.scaleOffset,
this.startDate,
});
factory ActivePrescriptionsResponseModel.fromRawJson(String str) => ActivePrescriptionsResponseModel.fromJson(json.decode(str));
String toRawJson() => json.encode(toJson());
factory ActivePrescriptionsResponseModel.fromJson(Map<String, dynamic> json) => ActivePrescriptionsResponseModel(
address: json["Address"],
appointmentNo: json["AppointmentNo"],
clinic: json["Clinic"],
companyName: json["CompanyName"],
days: json["Days"],
doctorName: json["DoctorName"],
doseDailyQuantity: json["DoseDailyQuantity"],
frequency: json["Frequency"],
frequencyNumber: json["FrequencyNumber"],
image: json["Image"],
imageExtension: json["ImageExtension"],
imageSrcUrl: json["ImageSRCUrl"],
imageString: json["ImageString"],
imageThumbUrl: json["ImageThumbUrl"],
isCovered: json["IsCovered"],
itemDescription: json["ItemDescription"],
itemId: json["ItemID"],
orderDate: json["OrderDate"],
patientId: json["PatientID"],
patientName: json["PatientName"],
phoneOffice1: json["PhoneOffice1"],
prescriptionQr: json["PrescriptionQR"],
prescriptionTimes: json["PrescriptionTimes"],
productImage: json["ProductImage"],
productImageBase64: json["ProductImageBase64"],
productImageString: json["ProductImageString"],
projectId: json["ProjectID"],
projectName: json["ProjectName"],
remarks: json["Remarks"],
route: json["Route"],
sku: json["SKU"],
scaleOffset: json["ScaleOffset"],
startDate: json["StartDate"],
);
Map<String, dynamic> toJson() => {
"Address": address,
"AppointmentNo": appointmentNo,
"Clinic": clinic,
"CompanyName": companyName,
"Days": days,
"DoctorName": doctorName,
"DoseDailyQuantity": doseDailyQuantity,
"Frequency": frequency,
"FrequencyNumber": frequencyNumber,
"Image": image,
"ImageExtension": imageExtension,
"ImageSRCUrl": imageSrcUrl,
"ImageString": imageString,
"ImageThumbUrl": imageThumbUrl,
"IsCovered": isCovered,
"ItemDescription": itemDescription,
"ItemID": itemId,
"OrderDate": orderDate,
"PatientID": patientId,
"PatientName": patientName,
"PhoneOffice1": phoneOffice1,
"PrescriptionQR": prescriptionQr,
"PrescriptionTimes": prescriptionTimes,
"ProductImage": productImage,
"ProductImageBase64": productImageBase64,
"ProductImageString": productImageString,
"ProjectID": projectId,
"ProjectName": projectName,
"Remarks": remarks,
"Route": route,
"SKU": sku,
"ScaleOffset": scaleOffset,
"StartDate": startDate,
};
}

@ -8,6 +8,7 @@ import 'package:flutter/services.dart';
import 'package:hmg_patient_app_new/core/app_state.dart';
import 'package:hmg_patient_app_new/core/dependencies.dart';
import 'package:hmg_patient_app_new/core/utils/utils.dart';
import 'package:hmg_patient_app_new/features/active_prescriptions/active_prescriptions_view_model.dart';
import 'package:hmg_patient_app_new/features/authentication/authentication_view_model.dart';
import 'package:hmg_patient_app_new/features/book_appointments/book_appointments_view_model.dart';
import 'package:hmg_patient_app_new/features/doctor_filter/doctor_filter_view_model.dart';
@ -125,6 +126,9 @@ void main() async {
),
ChangeNotifierProvider<DoctorFilterViewModel>(
create: (_) => getIt.get<DoctorFilterViewModel>(),
),
ChangeNotifierProvider<ActivePrescriptionsViewModel>(
create: (_) => getIt.get<ActivePrescriptionsViewModel>(),
)
], child: MyApp()),
),

@ -1,64 +1,72 @@
import 'dart:async';
import 'package:easy_localization/easy_localization.dart';
import 'package:flutter/material.dart';
import 'package:hmg_patient_app_new/core/app_export.dart';
import 'package:hmg_patient_app_new/extensions/string_extensions.dart';
import 'package:hmg_patient_app_new/extensions/widget_extensions.dart';
import '../../core/app_assets.dart';
import '../../core/utils/utils.dart';
// import 'package:sizer/sizer.dart';
import '../../core/dependencies.dart';
import '../../features/active_prescriptions/active_prescriptions_view_model.dart';
import '../../features/active_prescriptions/models/active_prescriptions_response_model.dart';
import '../../generated/locale_keys.g.dart';
import '../../services/dialog_service.dart';
import '../../theme/colors.dart';
import '../../widgets/appbar/app_bar_widget.dart';
import 'package:intl/intl.dart';
import 'package:hmg_patient_app_new/core/utils/utils.dart';
// import 'package:hmg_patient_app_new/core/utils/size_utils.dart';
import '../../widgets/buttons/custom_button.dart';
import '../../widgets/chip/app_custom_chip_widget.dart'; // for date formatting
import 'package:provider/provider.dart';
class ActiveMedicationPage extends StatefulWidget {
//inal List<ActivePrescriptionsResponseModel> activePrescriptionsResponseModel;
ActiveMedicationPage({super.key, });
@override
State<ActiveMedicationPage> createState() => _ActiveMedicationPageState();
}
class _ActiveMedicationPageState extends State<ActiveMedicationPage> {
late DateTime currentDate;
late DateTime selectedDate;
// Info for each day (customizable)
final Map<int, Map<String, dynamic>> dayInfo = {
0: {"text": "Medications", "icon": Icons.medication_outlined, "description": "Affected"},
1: {"text": "Doctor Appointment", "icon": Icons.local_hospital_outlined, "description": "Twice"},
2: {"text": "Rest Day", "icon": Icons.self_improvement_outlined, "description": "Daily"},
3: {"text": "Gym Session", "icon": Icons.fitness_center_outlined, "description": "Affected"},
4: {"text": "Meeting", "icon": Icons.meeting_room_outlined, "description": "Twice"},
5: {"text": "Shopping", "icon": Icons.shopping_bag_outlined, "description": "Daily"},
6: {"text": "Family Time", "icon": Icons.family_restroom_outlined, "description": "Affected"},
};
ActivePrescriptionsViewModel? activePreVM;
@override
void initState() {
activePreVM = Provider.of<ActivePrescriptionsViewModel>(context, listen: false);
activePreVM?.getActiveMedications();
print(activePreVM?.activePrescriptionsDetailsList);
super.initState();
currentDate = DateTime.now();
selectedDate = currentDate;
}
// Generate today + next 6 days
List<DateTime> getUpcomingDays() {
return List.generate(7, (index) => currentDate.add(Duration(days: index)));
}
// on/off toggle
bool isOn = true;
get index => null;
@override
Widget build(BuildContext context) {
// activePreVM = Provider.of<ActivePrescriptionsViewModel>(context, listen: false);
List<DateTime> days = getUpcomingDays();
int dayIndex = selectedDate.difference(currentDate).inDays;
String dateText =
"${selectedDate.day}${getSuffix(selectedDate.day)} ${DateFormat.MMMM().format(selectedDate)} ";
String infoMed = dayInfo[dayIndex]?["text"] ?? "No Info";
IconData infoImg= dayInfo[dayIndex]?["icon"] ?? Icons.info_outline;
String medDetails = dayInfo[dayIndex]?["description"] ?? "No Info";
String dateText = "${selectedDate.day}${getSuffix(selectedDate.day)} ${DateFormat.MMMM().format(selectedDate)} ";
return Scaffold(
backgroundColor: AppColors.scaffoldBgColor,
appBar: CustomAppBar(
@ -74,10 +82,11 @@ class _ActiveMedicationPageState extends State<ActiveMedicationPage> {
crossAxisAlignment: CrossAxisAlignment.start,
children: [
SizedBox(
height: 65,
height: 65.h,
child: ListView.builder(
scrollDirection: Axis.horizontal,
itemCount: days.length,
itemCount: days.length,
// itemCount: widget.details.length,
itemBuilder: (context, index) {
DateTime day = days[index];
String label = DateFormat('E').format(day); // Mon, Tue
@ -88,23 +97,22 @@ class _ActiveMedicationPageState extends State<ActiveMedicationPage> {
},
),
),
const SizedBox(height: 20),
SizedBox(height: 20.h),
// Show full date text
Text(
dateText,
style: TextStyle(
color: AppColors.textColor,
fontSize: 16,
fontSize: 16.fSize,
fontWeight: FontWeight.w500),
),
const Text(
"Medications",
Text(
"Medications".needTranslation,
style: TextStyle(
color: AppColors.primaryRedBorderColor,fontSize: 12, fontWeight: FontWeight.w500),
color: AppColors.primaryRedBorderColor,fontSize: 12.fSize, fontWeight: FontWeight.w500),
),
const SizedBox(height: 16),
SizedBox(height: 16.h),
Container(
decoration: RoundedRectangleBorder().toSmoothCornerDecoration(color: AppColors.whiteColor, borderRadius: 24,
hasShadow: true,),
@ -119,61 +127,64 @@ class _ActiveMedicationPageState extends State<ActiveMedicationPage> {
ClipRRect(
borderRadius: BorderRadius.circular(1),
child: Container(
width: 59,
height: 59,
width: 59.h,
height: 59.h,
decoration: BoxDecoration(
border: Border.all(
color: AppColors.spacerLineColor,// Border color
width: 1.0, ),
width: 1.0.h, ),
borderRadius: BorderRadius.circular(30),// Border width
),
child:
Icon(infoImg, size: 26),
// Utils.buildSvgWithAssets(icon: AppAssets.home_calendar_icon,width: 30.h, height: 30.h)
Utils.buildImgWithNetwork(url: activePreVM!.activePrescriptionsDetailsList[index].productImageString.toString(),width: 26.h,)
),
),
const SizedBox(width: 12),
SizedBox(width: 12.h),
Text(
infoMed,
activePreVM!.activePrescriptionsDetailsList[index].itemDescription.toString(),
style: TextStyle(
fontSize: 16,
height: 1.2,
fontSize: 16.fSize,
height: 1.2.h,
fontWeight: FontWeight.w700,
color: Colors.black87),
),
],
),
const SizedBox(height: 12),
SizedBox(height: 12.h),
activePreVM!.activePrescriptionsDetailsList.length > 0 ?
Wrap(
direction: Axis.horizontal,
spacing: 4.h,
runSpacing: 4.h,
children: [
AppCustomChipWidget(
labelText: "Route: $medDetails",
labelText: "Route: ${activePreVM?.activePrescriptionsDetailsList[index].route}",
),
AppCustomChipWidget(
labelText: "Frequency: $medDetails",
labelText: "Frequency: ${activePreVM?.activePrescriptionsDetailsList[index].frequency}".needTranslation,
),
AppCustomChipWidget(
labelText: "Daily Does $medDetails",
labelText: "Daily Does ${activePreVM?.activePrescriptionsDetailsList[index].doseDailyQuantity}".needTranslation,
),
AppCustomChipWidget(
labelText: "Duration: $medDetails ",
labelText: "Duration: ${activePreVM?.activePrescriptionsDetailsList[index].days} ".needTranslation,
),
],
):
Container(
child: Text("no data"),
),
const SizedBox(height: 12),
SizedBox(height: 12.h),
Row(
crossAxisAlignment: CrossAxisAlignment.start,
children: [
Icon(Icons.info_outline, color: Colors.grey,),
const SizedBox(width: 8),
SizedBox(width: 8.h),
Expanded(
child: Text(
"Remark: some remarks about the prescription will be here",
"Remark: some remarks about the prescription will be here".needTranslation,
style: TextStyle(
fontSize: 10,
fontSize: 10.fSize,
color: AppColors.greyTextColor,
fontWeight: FontWeight.w500,
),
@ -194,41 +205,96 @@ class _ActiveMedicationPageState extends State<ActiveMedicationPage> {
Row(
mainAxisAlignment: MainAxisAlignment.spaceBetween,
children: [
Row(
children: [
Container(
width: 40,
height: 40,
decoration: BoxDecoration(
color: AppColors.greyColor,
borderRadius: BorderRadius.circular(10),// Border width
),
child: Icon(Icons.notifications_sharp, color: AppColors.greyTextColor)),
const SizedBox(width: 8),
Column(
crossAxisAlignment: CrossAxisAlignment.start,
children: [
const Text(
"Set Reminder",
style: TextStyle(fontWeight: FontWeight.w600, fontSize: 14,
color: AppColors.textColor),
),
const Text(
"Notify me before the consumption time",
style: TextStyle(fontWeight: FontWeight.w500, fontSize: 12,
color: AppColors.textColorLight),
),
],
Container(
width: 40.h,
height: 40.h,
decoration: BoxDecoration(
color: AppColors.greyColor,
borderRadius: BorderRadius.circular(10),// Border width
),
],
child: Icon(Icons.notifications_sharp, color: AppColors.greyTextColor)
// MedicalFileCard(
// label: "Vaccine Info".needTranslation,
// textColor: AppColors.blackColor,
// backgroundColor: AppColors.whiteColor,
// svgIcon: AppAssets..bell,
// isLargeText: true,
// iconSize: 36.h,
// )
),
SizedBox(width: 8.h),
Expanded(
child: Column(
crossAxisAlignment: CrossAxisAlignment.start,
children: [
Text(
"Set Reminder",
style: TextStyle(fontWeight: FontWeight.w600, fontSize: 14.fSize,
color: AppColors.textColor),
),
Text(
"Notify me before the consumption time",
style: TextStyle(fontWeight: FontWeight.w500, fontSize: 12.fSize,
color: AppColors.textColorLight),
),
],
).onPress(() {
DialogService dialogService = getIt.get<DialogService>();
dialogService.showReminderBottomSheetWithoutHWithChild(
label: "Set the timer for reminder".needTranslation,
message: "",
child: ReminderTimerDialog(),
onOkPressed: () {},
);
}),
),
GestureDetector(
onTap: () {
setState(() {
isOn = !isOn;
});
},
child: AnimatedContainer(
duration: const Duration(milliseconds: 200),
width: 50.h,
height: 28.h,
decoration: BoxDecoration(
borderRadius: BorderRadius.circular(20),
color: isOn ? AppColors.lightGreenColor: AppColors.greyColor,
),
child: AnimatedAlign(
duration: const Duration(milliseconds: 200),
alignment: isOn ? Alignment.centerRight : Alignment.centerLeft,
child: Padding(
padding: const EdgeInsets.all(3),
child: Container(
width: 22.h,
height: 22.h,
decoration: BoxDecoration(
shape: BoxShape.circle,
color: isOn ? AppColors.textGreenColor : AppColors.greyTextColor,
),
),
),
),
),
),
SizedBox(width: 2.h),
// Switch(
// value: isActiveReminder,
// onChanged: (_) {},
// activeColor: Colors.green,
// value: isOn,
// onChanged: (value){
// setState(() {
// isOn = value;
// });
// },
// activeColor: AppColors.lightGreenColor,
// activeTrackColor: AppColors.lightGreenColor,
// activeThumbColor: AppColors.textGreenColor,
// inactiveThumbColor: AppColors.greyTextColor,
// inactiveTrackColor: AppColors.greyColor,
// ),
],
).paddingOnly(left:16, right: 16),
).paddingAll(16),
const Divider(
indent: 0,
endIndent: 0,
@ -242,7 +308,7 @@ class _ActiveMedicationPageState extends State<ActiveMedicationPage> {
Expanded(
child: CustomButton(
text: LocaleKeys.checkAvailability.tr(),
fontSize: 14,
fontSize: 14.fSize,
onPressed: () async {
},
backgroundColor: AppColors.secondaryLightRedColor,
@ -250,11 +316,11 @@ class _ActiveMedicationPageState extends State<ActiveMedicationPage> {
textColor: AppColors.errorColor,
),
),
const SizedBox(width: 12),
SizedBox(width: 12.h),
Expanded(
child: CustomButton(
text: LocaleKeys.readInstructions.tr(),
fontSize: 14,
fontSize: 14.fSize,
onPressed: () async {
},
backgroundColor: AppColors.primaryRedColor,
@ -267,186 +333,15 @@ class _ActiveMedicationPageState extends State<ActiveMedicationPage> {
],
),
)
// Expanded(
// child: ListView(
// children: [
// Container(
// decoration: RoundedRectangleBorder().toSmoothCornerDecoration(color: AppColors.whiteColor, borderRadius: 24,
// hasShadow: true,),
// child: Column(
// crossAxisAlignment: CrossAxisAlignment.start,
// children: [
// Column(
// crossAxisAlignment: CrossAxisAlignment.start,
// children: [
// Row(
// children: [
// ClipRRect(
// borderRadius: BorderRadius.circular(1),
// child: Container(
// width: 59,
// height: 59,
// decoration: BoxDecoration(
// border: Border.all(
// color: AppColors.spacerLineColor,// Border color
// width: 1.0, ),
// borderRadius: BorderRadius.circular(30),// Border width
// ),
// child:
// Utils.buildSvgWithAssets(icon: AppAssets.home_calendar_icon,width: 30.h, height: 30.h)
// ),
// ),
// const SizedBox(width: 12),
// const Expanded(
// child: Text(
// "Diclofenac Diethylamine 1% Topical Gel",
// style: TextStyle(
// fontSize: 16,
// height: 1.2,
// fontWeight: FontWeight.w700,
// color: Colors.black87),
// ),
// ),
// ],
// ),
// const SizedBox(height: 12),
// Wrap(
// direction: Axis.horizontal,
// spacing: 4.h,
// runSpacing: 4.h,
// children: [
// AppCustomChipWidget(
// labelText: "Route: Affected Area ",
// ),
// AppCustomChipWidget(
// labelText: "Route: Affected Area ",
// ),
// AppCustomChipWidget(
// labelText: "Daily Does 2",
// ),
// AppCustomChipWidget(
// labelText: "Route: Affected Area ",
// ),
// ],
// ),
// const SizedBox(height: 12),
// Row(
// crossAxisAlignment: CrossAxisAlignment.start,
// children: [
// Icon(Icons.info_outline, color: Colors.grey,),
// const SizedBox(width: 8),
// Expanded(
// child: Text(
// "Remark: some remarks about the prescription will be here",
// style: TextStyle(
// fontSize: 10,
// color: AppColors.greyTextColor,
// fontWeight: FontWeight.w500,
// ),
// overflow: TextOverflow.visible,
// ),
// )
// ],
// ),
// ],
// ).paddingAll(16),
// const Divider(
// indent: 0,
// endIndent: 0,
// thickness: 1,
// color: AppColors.greyColor,
// ),
// // Reminder Row
// Row(
// mainAxisAlignment: MainAxisAlignment.spaceBetween,
// children: [
// Row(
// children: [
// Container(
// width: 40,
// height: 40,
// decoration: BoxDecoration(
// color: AppColors.greyColor,
// borderRadius: BorderRadius.circular(10),// Border width
// ),
// child: Icon(Icons.notifications_sharp, color: AppColors.greyTextColor)),
// const SizedBox(width: 8),
// Column(
// crossAxisAlignment: CrossAxisAlignment.start,
// children: [
// const Text(
// "Set Reminder",
// style: TextStyle(fontWeight: FontWeight.w600, fontSize: 14,
// color: AppColors.textColor),
// ),
// const Text(
// "Notify me before the consumption time",
// style: TextStyle(fontWeight: FontWeight.w500, fontSize: 12,
// color: AppColors.textColorLight),
// ),
// ],
// ),
// ],
// ),
// // Switch(
// // value: isActiveReminder,
// // onChanged: (_) {},
// // activeColor: Colors.green,
// // ),
// ],
// ).paddingOnly(left:16, right: 16),
// const Divider(
// indent: 0,
// endIndent: 0,
// thickness: 1,
// color: AppColors.greyColor,
// ),
//
// // Buttons
// Row(
// children: [
// Expanded(
// child: CustomButton(
// text: LocaleKeys.checkAvailability.tr(),
// fontSize: 14,
// onPressed: () async {
// },
// backgroundColor: AppColors.secondaryLightRedColor,
// borderColor: AppColors.secondaryLightRedColor,
// textColor: AppColors.errorColor,
// ),
// ),
// const SizedBox(width: 12),
// Expanded(
// child: CustomButton(
// text: LocaleKeys.readInstructions.tr(),
// fontSize: 14,
// onPressed: () async {
// },
// backgroundColor: AppColors.primaryRedColor,
// borderColor: AppColors.primaryRedColor,
// textColor: AppColors.whiteColor,
// ),
// ),
// ],
// ).paddingAll(16),
// ],
// ),
// )
// // MedicationCard(),
// // SizedBox(height: 16),
// // MedicationCard(isActiveReminder: true),
// ],
// ),
// ),
]
),
),
),
);
}
Widget buildDayCard(String label, DateTime date) {
Widget buildDayCard(String label, DateTime date,) {
bool isSelected = selectedDate.day == date.day &&
selectedDate.month == date.month &&
selectedDate.year == date.year;
@ -458,14 +353,14 @@ class _ActiveMedicationPageState extends State<ActiveMedicationPage> {
});
},
child: Container(
width: 57,
height: 65,
width: 57.h,
height: 65.h,
decoration: BoxDecoration(
borderRadius: BorderRadius.circular(12),
color: isSelected ? AppColors.secondaryLightRedBorderColor: AppColors.transparent,
border: Border.all(
color: isSelected ? AppColors.primaryRedBorderColor : AppColors.spacerLineColor,
width: 1.0,
width: 1.0.h,
),
),
child: Padding(
@ -474,18 +369,18 @@ class _ActiveMedicationPageState extends State<ActiveMedicationPage> {
mainAxisAlignment: MainAxisAlignment.center,
children: [
Text(
date.day == currentDate.day ? "Today" : label,
date.day == currentDate.day ? "Today".needTranslation : label,
style: TextStyle(
color: isSelected ? AppColors.primaryRedBorderColor : AppColors.greyTextColor,
fontSize: 12,
fontSize: 12.fSize,
fontWeight: FontWeight.w500,
),
),
const SizedBox(height: 5),
SizedBox(height: 5.h),
Text(
date.day.toString(),
style: TextStyle(
fontSize: 16,
fontSize: 16.fSize,
fontWeight: FontWeight.bold,
color: isSelected ? AppColors.primaryRedBorderColor : AppColors.textColor,
),
@ -503,180 +398,167 @@ class _ActiveMedicationPageState extends State<ActiveMedicationPage> {
if (day == 3 || day == 23) return "rd";
return "th";
}
// Widget manageReminder(){
// NavigationService navigationService = getIt<NavigationService>();
// return Container(
// width: 59,
// height: 59,
// decoration: BoxDecoration(
// border: Border.all(
// color: AppColors.spacerLineColor,// Border color
// width: 1.0, ),
// borderRadius: BorderRadius.circular(30),// Border width
// ),
// child:
// Utils.buildSvgWithAssets(icon: AppAssets.home_calendar_icon,width: 30.h, height: 30.h)
// );
// }
}
class ReminderTimerDialog extends StatefulWidget {
// final Function()? onSetReminderPress;
// final String message;
//
// const ReminderTimerDialog(this.onSetReminderPress, this.message, {super.key});
const ReminderTimerDialog({super.key});
@override
State<ReminderTimerDialog> createState() => _ReminderTimerDialogState();
}
class MedicationCard extends StatelessWidget {
final bool isActiveReminder;
const MedicationCard({super.key, this.isActiveReminder = false});
class _ReminderTimerDialogState extends State<ReminderTimerDialog> {
final List<String> options = ["Morning", "Afternoon", "Evening", "Midnight"];
final List<String> selectedTimes = ["Morning"]; // Default selection
Color get primaryRed => const Color(0xFFE84B3A);
@override
Widget build(BuildContext context) {
return
Container(
decoration: RoundedRectangleBorder().toSmoothCornerDecoration(color: AppColors.whiteColor, borderRadius: 24,
hasShadow: true,),
child: Column(
crossAxisAlignment: CrossAxisAlignment.start,
return //
Column(
children: [
Column(
crossAxisAlignment: CrossAxisAlignment.start,
children: [
Row(
children: [
ClipRRect(
borderRadius: BorderRadius.circular(1),
child: Container(
width: 59,
height: 59,
decoration: BoxDecoration(
border: Border.all(
color: AppColors.spacerLineColor,// Border color
width: 1.0, ),
borderRadius: BorderRadius.circular(30),// Border width
),
child:
Utils.buildSvgWithAssets(icon: AppAssets.home_calendar_icon,width: 30.h, height: 30.h)
),
),
const SizedBox(width: 12),
const Expanded(
child: Text(
"Diclofenac Diethylamine 1% Topical Gel",
Container(
decoration: RoundedRectangleBorder().toSmoothCornerDecoration(color: AppColors.whiteColor, borderRadius: 24,
hasShadow: true,),
child: Column(
mainAxisSize: MainAxisSize.min,
crossAxisAlignment: CrossAxisAlignment.start,
// Checkboxes list
children: options.map((time) => buildCircleCheckbox(time)).toList(),
).paddingAll(16),
),
SizedBox(height: 25.h),
// Buttons Row
Row(
children: [
Expanded(
child: ElevatedButton.icon(
onPressed: () => Navigator.pop(context),
icon: const Icon(Icons.close, color: AppColors.errorColor),
label: Text(
LocaleKeys.cancel.tr(),
style: TextStyle(
fontSize: 16,
height: 1.2,
fontWeight: FontWeight.w700,
color: Colors.black87),
color: AppColors.errorColor,
fontWeight: FontWeight.w500,
fontSize: 14.fSize
),
),
style: ElevatedButton.styleFrom(
backgroundColor: AppColors.secondaryLightRedColor,
elevation: 0,
padding: const EdgeInsets.symmetric(vertical: 14),
shape: RoundedRectangleBorder(
borderRadius: BorderRadius.circular(12),
),
),
),
],
),
const SizedBox(height: 12),
Wrap(
direction: Axis.horizontal,
spacing: 4.h,
runSpacing: 4.h,
children: [
AppCustomChipWidget(
labelText: "Route: Affected Area ",
),
AppCustomChipWidget(
labelText: "Route: Affected Area ",
),
AppCustomChipWidget(
labelText: "Daily Does 2",
),
AppCustomChipWidget(
labelText: "Route: Affected Area ",
),
],
),
const SizedBox(height: 12),
Row(
crossAxisAlignment: CrossAxisAlignment.start,
children: [
Icon(Icons.info_outline, color: Colors.grey,),
const SizedBox(width: 8),
Expanded(
child: Text(
"Remark: some remarks about the prescription will be here",
),
SizedBox(width: 12.h),
Expanded(
child: ElevatedButton.icon(
onPressed: () {
Navigator.pop(context, selectedTimes);
},
icon: const Icon(Icons.notifications_rounded),
label: Text(
LocaleKeys.setReminder.tr(),
style: TextStyle(
fontSize: 10,
color: AppColors.greyTextColor,
fontWeight: FontWeight.w500,
fontWeight: FontWeight.w500,
fontSize: 14.fSize
),
overflow: TextOverflow.visible,
),
)
],
),
],
).paddingAll(16),
const Divider(
indent: 0,
endIndent: 0,
thickness: 1,
color: AppColors.greyColor,
),
// Reminder Row
Row(
mainAxisAlignment: MainAxisAlignment.spaceBetween,
children: [
Row(
children: [
Container(
width: 40,
height: 40,
decoration: BoxDecoration(
color: AppColors.greyColor,
borderRadius: BorderRadius.circular(10),// Border width
),
child: Icon(Icons.notifications_sharp, color: AppColors.greyTextColor)),
const SizedBox(width: 8),
Column(
crossAxisAlignment: CrossAxisAlignment.start,
children: [
const Text(
"Set Reminder",
style: TextStyle(fontWeight: FontWeight.w600, fontSize: 14,
color: AppColors.textColor),
),
const Text(
"Notify me before the consumption time",
style: TextStyle(fontWeight: FontWeight.w500, fontSize: 12,
color: AppColors.textColorLight),
),
],
style: ElevatedButton.styleFrom(
backgroundColor: AppColors.successColor,
foregroundColor: AppColors.whiteColor,
elevation: 0,
padding: const EdgeInsets.symmetric(vertical: 14),
shape: RoundedRectangleBorder(
borderRadius: BorderRadius.circular(12),
),
],
),
Switch(
value: isActiveReminder,
onChanged: (_) {},
activeColor: Colors.green,
),
),
],
).paddingOnly(left:16, right: 16),
const Divider(
indent: 0,
endIndent: 0,
thickness: 1,
color: AppColors.greyColor,
),
],
),
SizedBox(height: 30.h),
],
);
}
// Buttons
Row(
children: [
Expanded(
child: CustomButton(
text: LocaleKeys.checkAvailability.tr(),
fontSize: 14,
onPressed: () async {
},
backgroundColor: AppColors.secondaryLightRedColor,
borderColor: AppColors.secondaryLightRedColor,
textColor: AppColors.errorColor,
),
),
const SizedBox(width: 12),
Expanded(
child: CustomButton(
text: LocaleKeys.readInstructions.tr(),
fontSize: 14,
onPressed: () async {
},
backgroundColor: AppColors.primaryRedColor,
borderColor: AppColors.primaryRedColor,
textColor: AppColors.whiteColor,
),
Widget buildCircleCheckbox(String label) {
final bool isSelected = selectedTimes.contains(label);
return InkWell(
onTap: () {
setState(() {
if (isSelected) {
selectedTimes.remove(label);
} else {
selectedTimes.add(label);
}
});
},
borderRadius: BorderRadius.circular(25),
child: Padding(
padding: const EdgeInsets.symmetric(vertical: 8.0),
child: Row(
children: [
// Custom circle checkbox
Container(
width: 15.h,
height: 15.h,
decoration: BoxDecoration(
shape: BoxShape.circle,
border: Border.all(
color: isSelected ? AppColors.spacerLineColor: AppColors.spacerLineColor,
width: 1.h,
),
],
).paddingAll(16),
],
color: isSelected ? AppColors.errorColor: AppColors.transparent,
),
),
SizedBox(width: 12.h),
// Label text
Text(
label,
style: TextStyle(fontSize: 16.fSize, color: Colors.black87),
),
],
),
),
);
}
void showCircleCheckboxDialog(BuildContext context) async {
final selected = await showDialog<List<String>>(
context: context,
builder: (context) => const ReminderTimerDialog(),
);
if (selected != null && selected.isNotEmpty) {
ScaffoldMessenger.of(context).showSnackBar(
SnackBar(content: Text('Reminders set for: ${selected.join(', ').needTranslation}')),
);
}
}
}

@ -463,12 +463,6 @@ class _LandingPageState extends State<LandingPage> {
Row(
children: [
"View all services".toText12(color: AppColors.primaryRedColor).onPress(() {
Navigator.of(context)
.push(
CustomPageRoute(
page: ActiveMedicationPage(),
),
);
}),
SizedBox(width: 2.h),
Icon(Icons.arrow_forward_ios, color: AppColors.primaryRedColor, size: 10.h),

@ -12,6 +12,7 @@ import 'package:hmg_patient_app_new/core/utils/size_utils.dart';
import 'package:hmg_patient_app_new/core/utils/utils.dart';
import 'package:hmg_patient_app_new/extensions/string_extensions.dart';
import 'package:hmg_patient_app_new/extensions/widget_extensions.dart';
import 'package:hmg_patient_app_new/features/active_prescriptions/models/active_prescriptions_response_model.dart';
import 'package:hmg_patient_app_new/features/book_appointments/book_appointments_view_model.dart';
import 'package:hmg_patient_app_new/features/book_appointments/models/resp_models/doctors_list_response_model.dart';
import 'package:hmg_patient_app_new/features/insurance/insurance_view_model.dart';
@ -23,6 +24,7 @@ import 'package:hmg_patient_app_new/features/my_appointments/models/resp_models/
import 'package:hmg_patient_app_new/features/my_appointments/my_appointments_view_model.dart';
import 'package:hmg_patient_app_new/features/prescriptions/prescriptions_view_model.dart';
import 'package:hmg_patient_app_new/generated/locale_keys.g.dart';
import 'package:hmg_patient_app_new/presentation/active_medication/active_medication_page.dart';
import 'package:hmg_patient_app_new/presentation/appointments/my_appointments_page.dart';
import 'package:hmg_patient_app_new/presentation/appointments/my_doctors_page.dart';
import 'package:hmg_patient_app_new/presentation/book_appointment/book_appointment_page.dart';
@ -56,6 +58,7 @@ import 'package:hmg_patient_app_new/widgets/routes/custom_page_route.dart';
import 'package:hmg_patient_app_new/widgets/shimmer/movies_shimmer_widget.dart';
import 'package:provider/provider.dart';
import '../../features/active_prescriptions/active_prescriptions_view_model.dart';
import '../prescriptions/prescription_detail_page.dart';
import 'widgets/medical_file_appointment_card.dart';
@ -73,6 +76,7 @@ class _MedicalFilePageState extends State<MedicalFilePage> {
late MedicalFileViewModel medicalFileViewModel;
late BookAppointmentsViewModel bookAppointmentsViewModel;
late LabViewModel labViewModel;
late ActivePrescriptionsViewModel activePrescriptionsViewModel;
int currentIndex = 0;
@ -98,6 +102,7 @@ class _MedicalFilePageState extends State<MedicalFilePage> {
myAppointmentsViewModel = Provider.of<MyAppointmentsViewModel>(context, listen: false);
medicalFileViewModel = Provider.of<MedicalFileViewModel>(context, listen: false);
bookAppointmentsViewModel = Provider.of<BookAppointmentsViewModel>(context, listen: false);
NavigationService navigationService = getIt.get<NavigationService>();
return CollapsingListView(
title: "Medical File".needTranslation,
@ -528,7 +533,13 @@ class _MedicalFilePageState extends State<MedicalFilePage> {
Expanded(
child: CustomButton(
text: "All Medications".needTranslation,
onPressed: () {},
onPressed: () {
Navigator.of(context).push(
CustomPageRoute(
page: ActiveMedicationPage(),
),
);
},
backgroundColor: AppColors.secondaryLightRedColor,
borderColor: AppColors.secondaryLightRedColor,
textColor: AppColors.primaryRedColor,

@ -14,6 +14,8 @@ import 'package:hmg_patient_app_new/widgets/buttons/custom_button.dart';
import 'package:hmg_patient_app_new/widgets/common_bottom_sheet.dart';
import 'package:hmg_patient_app_new/widgets/family_files/family_file_add_widget.dart';
import '../widgets/medication_reminder/reminder_timer_dialog.dart';
abstract class DialogService {
Future<void> showErrorBottomSheet({String title = "", required String message, Function()? onOkPressed, Function()? onCancelPressed});
@ -29,6 +31,8 @@ abstract class DialogService {
Future<void> showPhoneNumberPickerSheet({String? label, String? message, required Function() onSMSPress, required Function() onWhatsappPress});
Future<void> showAddFamilyFileSheet({String? label, String? message, required Function() onVerificationPress});
Future<void> showReminderBottomSheetWithoutHWithChild({String? label, required String message, Widget? child, required Function() onOkPressed, Function()? onCancelPressed});
// TODO : Need to be Fixed showPhoneNumberPickerSheet ( From Login ADn Signup Bottom Sheet Move Here
}
@ -133,6 +137,18 @@ class DialogServiceImp implements DialogService {
);
}
@override
Future<void> showReminderBottomSheetWithoutHWithChild({String? label, required String message, Widget? child, required Function() onOkPressed, Function()? onCancelPressed}) async {
final context = navigationService.navigatorKey.currentContext;
if (context == null) return;
showCommonBottomSheetWithoutHeight(
context,
title: label ?? "",
child: child ?? SizedBox(),
callBackFunc: () {},
);
}
@override
Future<void> showPhoneNumberPickerSheet({String? label, String? message, required Function() onSMSPress, required Function() onWhatsappPress}) async {
final context = navigationService.navigatorKey.currentContext;

@ -0,0 +1,155 @@
// import 'package:easy_localization/easy_localization.dart';
// import 'package:flutter/material.dart';
// import 'package:hmg_patient_app_new/extensions/widget_extensions.dart';
//
// import '../../generated/locale_keys.g.dart';
// import '../../theme/colors.dart';
//
// class ReminderTimerDialog extends StatefulWidget {
// final Function()? onSetReminderPress;
// final String message;
//
// const ReminderTimerDialog(this.onSetReminderPress, this.message, {super.key});
//
//
// @override
// State<ReminderTimerDialog> createState() => _ReminderTimerDialogState();
// }
//
// class _ReminderTimerDialogState extends State<ReminderTimerDialog> {
// final List<String> options = ["Morning", "Afternoon", "Evening", "Midnight"];
// final List<String> selectedTimes = ["Morning"]; // Default selection
//
//
// @override
// Widget build(BuildContext context) {
// return //
// Column(
// children: [
// Container(
// decoration: RoundedRectangleBorder().toSmoothCornerDecoration(color: AppColors.whiteColor, borderRadius: 24,
// hasShadow: true,),
// child: Column(
// mainAxisSize: MainAxisSize.min,
// crossAxisAlignment: CrossAxisAlignment.start,
// // Checkboxes list
// children: options.map((time) => buildCircleCheckbox(time)).toList(),
// ).paddingAll(16),
// ),
// const SizedBox(height: 25),
// // Buttons Row
// Row(
// children: [
// Expanded(
// child: ElevatedButton.icon(
// onPressed: () => Navigator.pop(context),
// icon: const Icon(Icons.close, color: AppColors.errorColor),
// label: Text(
// LocaleKeys.cancel.tr(),
// style: TextStyle(
// color: AppColors.errorColor,
// fontWeight: FontWeight.w500,
// fontSize: 14
// ),
// ),
// style: ElevatedButton.styleFrom(
// backgroundColor: AppColors.secondaryLightRedColor,
// elevation: 0,
// padding: const EdgeInsets.symmetric(vertical: 14),
// shape: RoundedRectangleBorder(
// borderRadius: BorderRadius.circular(12),
// ),
// ),
// ),
// ),
// const SizedBox(width: 12),
// Expanded(
// child: ElevatedButton.icon(
// onPressed: () {
// Navigator.pop(context, selectedTimes);
// },
// icon: const Icon(Icons.notifications_rounded),
// label: Text(
// LocaleKeys.setReminder.tr(),
// style: TextStyle(
// fontWeight: FontWeight.w500,
// fontSize: 14
// ),
// ),
// style: ElevatedButton.styleFrom(
// backgroundColor: AppColors.successColor,
// foregroundColor: AppColors.whiteColor,
// elevation: 0,
// padding: const EdgeInsets.symmetric(vertical: 14),
// shape: RoundedRectangleBorder(
// borderRadius: BorderRadius.circular(12),
// ),
// ),
// ),
// ),
// ],
// ),
// const SizedBox(height: 30),
// ],
// );
// }
//
// Widget buildCircleCheckbox(String label) {
// final bool isSelected = selectedTimes.contains(label);
// return InkWell(
// onTap: () {
// setState(() {
// if (isSelected) {
// selectedTimes.remove(label);
// } else {
// selectedTimes.add(label);
// }
// });
// },
// borderRadius: BorderRadius.circular(25),
// child: Padding(
// padding: const EdgeInsets.symmetric(vertical: 8.0),
// child: Row(
// children: [
// // Custom circle checkbox
// Container(
// width: 15,
// height: 15,
// decoration: BoxDecoration(
// shape: BoxShape.circle,
// border: Border.all(
// color: isSelected ? AppColors.spacerLineColor: AppColors.spacerLineColor,
// width: 1,
// ),
// color: isSelected ? AppColors.errorColor: AppColors.transparent,
// ),
// ),
// const SizedBox(width: 12),
// // Label text
// Text(
// label,
// style: const TextStyle(fontSize: 16, color: Colors.black87),
// ),
// ],
// ),
// ),
// );
// }
//
//
// void showCircleCheckboxDialog(BuildContext context) async {
// final selected = await showDialog<List<String>>(
// context: context,
// builder: (context) => const ReminderTimerDialog(),
// );
//
// if (selected != null && selected.isNotEmpty) {
// ScaffoldMessenger.of(context).showSnackBar(
// SnackBar(content: Text('Reminders set for: ${selected.join(', ')}')),
// );
// }
// }
// }
//
//
//
Loading…
Cancel
Save