import 'dart:convert'; import 'dart:developer'; import 'dart:io'; import 'package:diplomaticquarterapp/config/shared_pref_kay.dart'; import 'package:diplomaticquarterapp/core/enum/PayfortEnums.dart'; import 'package:diplomaticquarterapp/core/viewModels/project_view_model.dart'; import 'package:diplomaticquarterapp/models/Appointments/AppoimentAllHistoryResultList.dart'; import 'package:diplomaticquarterapp/models/Appointments/DoctorListResponse.dart'; import 'package:diplomaticquarterapp/models/Appointments/PatientShareResposne.dart'; import 'package:diplomaticquarterapp/models/Appointments/toDoCountProviderModel.dart'; import 'package:diplomaticquarterapp/models/Authentication/authenticated_user.dart'; import 'package:diplomaticquarterapp/models/LiveCare/ApplePayInsertRequest.dart'; import 'package:diplomaticquarterapp/models/header_model.dart'; import 'package:diplomaticquarterapp/pages/ToDoList/payment_method_select.dart'; import 'package:diplomaticquarterapp/pages/ToDoList/widgets/paymentDialog.dart'; import 'package:diplomaticquarterapp/pages/insurance/insurance_update_screen.dart'; import 'package:diplomaticquarterapp/pages/landing/landing_page.dart'; import 'package:diplomaticquarterapp/routes.dart'; import 'package:diplomaticquarterapp/services/appointment_services/GetDoctorsList.dart'; import 'package:diplomaticquarterapp/services/clinic_services/get_clinic_service.dart'; import 'package:diplomaticquarterapp/services/livecare_services/livecare_provider.dart'; import 'package:diplomaticquarterapp/services/payfort_services/payfort_project_details_resp_model.dart'; import 'package:diplomaticquarterapp/services/payfort_services/payfort_view_model.dart'; import 'package:diplomaticquarterapp/theme/colors.dart'; import 'package:diplomaticquarterapp/uitl/app_shared_preferences.dart'; import 'package:diplomaticquarterapp/uitl/app_toast.dart'; import 'package:diplomaticquarterapp/uitl/date_uitl.dart'; import 'package:diplomaticquarterapp/uitl/gif_loader_dialog_utils.dart'; import 'package:diplomaticquarterapp/uitl/translations_delegate_base.dart'; import 'package:diplomaticquarterapp/uitl/utils.dart'; import 'package:diplomaticquarterapp/uitl/utils_new.dart'; import 'package:diplomaticquarterapp/widgets/buttons/custom_text_button.dart'; import 'package:diplomaticquarterapp/widgets/dialogs/confirm_dialog.dart'; import 'package:diplomaticquarterapp/widgets/in_app_browser/InAppBrowser.dart'; import 'package:diplomaticquarterapp/widgets/new_design/doctor_header.dart'; import 'package:diplomaticquarterapp/widgets/others/app_scaffold_widget.dart'; import 'package:diplomaticquarterapp/widgets/transitions/fade_page.dart'; import 'package:flutter/material.dart'; import 'package:intl/intl.dart'; import 'package:provider/provider.dart'; import '../../models/Appointments/PatientPackageComponent.dart'; import 'book_reminder_page.dart'; import 'components/DocAvailableAppointments.dart'; class BookConfirm extends StatefulWidget { DoctorList doctor; String selectedDate; String selectedTime; String appoDateFormatted = ""; String appoTimeFormatted = ""; bool isLiveCareAppointment; int initialSlotDuration; bool isWalkinAppointment = false; BookConfirm( {required this.doctor, required this.selectedDate, required this.isLiveCareAppointment, required this.selectedTime, required this.initialSlotDuration, required this.isWalkinAppointment}); late DoctorsListService service; late PatientShareResponse patientShareResponse; // AuthenticatedUser authUser; @override _BookConfirmState createState() => _BookConfirmState(); } class _BookConfirmState extends State { late ProjectViewModel projectViewModel; late ToDoCountProviderModel toDoProvider; AppSharedPreferences sharedPref = new AppSharedPreferences(); bool isInsured = false; bool isEligible = false; bool isCash = false; String? selectedPaymentMethod = ""; String? selectedInstallments = ""; String? tamaraPaymentStatus; String? tamaraOrderID; String? transID; late MyInAppBrowser browser; @override void initState() { // widget.authUser = new AuthenticatedUser(); // getPatientData(); widget.service = new DoctorsListService(); widget.patientShareResponse = new PatientShareResponse(); super.initState(); } @override Widget build(BuildContext context) { toDoProvider = Provider.of(context); projectViewModel = Provider.of(context); return AppScaffold( appBarTitle: widget.doctor.doctorTitle! + " " + widget.doctor.name!, isShowDecPage: false, isShowAppBar: true, showNewAppBarTitle: true, showNewAppBar: true, backgroundColor: CustomColors.appBackgroudGreyColor, body: SingleChildScrollView( child: Column( crossAxisAlignment: CrossAxisAlignment.start, mainAxisSize: MainAxisSize.max, children: [ DoctorHeader( headerModel: HeaderModel( widget.doctor.name!, widget.doctor.doctorID!, widget.doctor.doctorImageURL!, widget.doctor.speciality!, "", widget.doctor.projectName!, null, null, widget.doctor.nationalityFlagURL ?? "", widget.doctor.doctorRate, null, widget.doctor.noOfPatientsRate, "", ), isNeedToShowButton: false, ), Padding( padding: const EdgeInsets.all(20.0), child: Column( crossAxisAlignment: CrossAxisAlignment.start, children: [ Text( TranslationBase.of(context).confirmAppoHeading, textAlign: TextAlign.center, style: TextStyle( fontSize: 16.0, letterSpacing: -0.64, fontWeight: FontWeight.w600, ), ), mHeight(20), Container( decoration: cardRadius(12), margin: EdgeInsets.zero, child: Padding( padding: const EdgeInsets.fromLTRB(16, 20, 16, 20), child: Column( crossAxisAlignment: CrossAxisAlignment.start, children: [ Text( TranslationBase.of(context).appoInfo, style: TextStyle( fontSize: 14.0, color: Colors.black, letterSpacing: -0.36, fontWeight: FontWeight.w600, ), ), mHeight(16), Column( crossAxisAlignment: CrossAxisAlignment.start, mainAxisSize: MainAxisSize.max, children: [ if (!widget.isLiveCareAppointment) showInfo(TranslationBase.of(context).hospital, widget.doctor.projectName!), showInfo(TranslationBase.of(context).clinic, widget.doctor.clinicName!), showInfo(TranslationBase.of(context).date, getDate()), showInfo(TranslationBase.of(context).time, widget.selectedTime) ], ), ], ), ), ), mHeight(12), Container( decoration: cardRadius(12), margin: EdgeInsets.zero, child: Padding( padding: const EdgeInsets.fromLTRB(16, 20, 16, 20), child: Column( crossAxisAlignment: CrossAxisAlignment.start, children: [ Text( TranslationBase.of(context).patientInfo, style: TextStyle( fontSize: 14.0, color: Colors.black, letterSpacing: -0.36, fontWeight: FontWeight.w600, ), ), mHeight(16), Column( crossAxisAlignment: CrossAxisAlignment.start, mainAxisSize: MainAxisSize.max, children: [ showInfo(TranslationBase.of(context).name, projectViewModel.user!.firstName! + " " + projectViewModel.user!.lastName!), showInfo(TranslationBase.of(context).gender, projectViewModel.user!.genderDescription!), showInfo(TranslationBase.of(context).age, projectViewModel.user!.age.toString()) ], ), ], ), ), ), ], ), ), SizedBox( height: 120.0, ), ], ), ), bottomSheet: Container( color: CustomColors.appBackgroudGreyColor, child: Container( width: MediaQuery.of(context).size.width, height: 45.0, margin: EdgeInsets.all(16), child: ButtonTheme( shape: RoundedRectangleBorder( borderRadius: BorderRadius.circular(10.0), ), minWidth: MediaQuery.of(context).size.width * 0.7, height: 40.0, child: CustomTextButton( backgroundColor: CustomColors.green, disabledForegroundColor: new Color(0xFFbcc2c4).withOpacity(0.38), disabledBackgroundColor: new Color(0xFFbcc2c4).withOpacity(0.12), elevation: 0, onPressed: () async { bool isLiveCareSchedule = await this.sharedPref.getBool(IS_LIVECARE_APPOINTMENT) ?? false; if (widget.isWalkinAppointment) { getWalkinAppointmentPatientShare(); } else { if (isLiveCareSchedule) { insertLiveCareScheduledAppointment(context, widget.doctor); } else { checkPatientHasDermaPackage(widget.doctor, projectViewModel.user.patientID!); } } }, child: Text(widget.isWalkinAppointment ? TranslationBase.of(context).addToWaitingList : TranslationBase.of(context).bookAppo, style: TextStyle(fontSize: 16.0, letterSpacing: -0.48, color: Colors.white)), ), ), ), ), ); } getWalkinAppointmentPatientShare() { String errorMsg = ""; AppoitmentAllHistoryResultList appo = new AppoitmentAllHistoryResultList(); GifLoaderDialogUtils.showMyDialog(context); appo.doctorTitle = widget.doctor.doctorTitle; appo.doctorNameObj = widget.doctor.name; appo.appointmentDate = DateUtil.convertDateToString(DateTime.now()); appo.projectName = widget.doctor.projectName; widget.service .getPatientShareForWalkInAppointment( widget.doctor.clinicID!, widget.doctor.projectID!, widget.doctor.doctorID!, ) .then((res) { widget.patientShareResponse = new PatientShareResponse.fromJson(res["OnlineCheckInAppointmentsWalkInModel"]); GifLoaderDialogUtils.hideDialog(context); isInsured = res["IsInsured"]; isEligible = res["IsEligible"]; isCash = res["IsCash"]; if (isCash) { if (widget.patientShareResponse.patientShareWithTax != 0 || widget.patientShareResponse.patientShareWithTax != 0.0) { openPaymentDialog(appo, widget.patientShareResponse!); } else { insertWalkInAppointment(context, widget.doctor, widget.initialSlotDuration, null); } } else { if (isInsured && isEligible) { if (widget.patientShareResponse.patientShareWithTax != 0 || widget.patientShareResponse.patientShareWithTax != 0.0) { openPaymentDialog(appo, widget.patientShareResponse!); } else { insertWalkInAppointment(context, widget.doctor, widget.initialSlotDuration, null); } } else { if (isInsured && !isEligible) { errorMsg = TranslationBase.of(context).invalidEligibility; } else { errorMsg = TranslationBase.of(context).invalidInsurance; } ConfirmDialog dialog = new ConfirmDialog( isDissmissable: false, context: context, confirmMessage: errorMsg, okText: TranslationBase.of(context).updateInsuranceText, cancelText: TranslationBase.of(context).continueCash, okFunction: () => {openUpdateInsurance()}, cancelFunction: () => {continueAsCashForWalkIn(widget.doctor.projectID!)}); dialog.showAlertDialog(context); } } // widget.patientShareResponse = new PatientShareResponse.fromJson(res["OnlineCheckInAppointmentsWalkInModel"]); // GifLoaderDialogUtils.hideDialog(context); // if (widget.patientShareResponse.patientShareWithTax != 0 || widget.patientShareResponse.patientShareWithTax != 0.0) { // openPaymentDialog(appo, widget.patientShareResponse!); // } else { // insertWalkInAppointment(context, widget.doctor, widget.initialSlotDuration, null); // } }).catchError((err) { GifLoaderDialogUtils.hideDialog(context); AppToast.showErrorToast(message: err); print(err); }); } openPaymentDialog(AppoitmentAllHistoryResultList appo, PatientShareResponse patientShareResponse) { showGeneralDialog( barrierColor: Colors.black.withOpacity(0.5), transitionBuilder: (context, a1, a2, widget) { final curvedValue = Curves.easeInOutBack.transform(a1.value) - 1.0; return Transform( transform: Matrix4.translationValues(0.0, curvedValue * 200, 0.0), child: Opacity( opacity: a1.value, child: PaymentDialog( appo: appo, patientShareResponse: patientShareResponse, isCashPatient: isCash, onPaymentMethodSelected: () {}, ), ), ); }, transitionDuration: Duration(milliseconds: 500), barrierDismissible: false, barrierLabel: '', context: context, pageBuilder: (context, animation1, animation2) => SizedBox()).then((value) { print(value); if (value != null) { navigateToPaymentMethod(context, value as PatientShareResponse); // projectViewModel.analytics.todoList.to_do_list_confirm_payment_details(appo); } else { // projectViewModel.analytics.todoList.to_do_list_cancel_payment_details(appo); } }); } Future navigateToPaymentMethod(context, PatientShareResponse patientShareResponse) async { AppoitmentAllHistoryResultList appo = new AppoitmentAllHistoryResultList(); appo.projectID = widget.doctor.projectID; appo.clinicID = widget.doctor.clinicID; appo.clinicName = widget.doctor.clinicName; appo.projectName = widget.doctor.projectName; appo.appointmentNo = DateTime.now().millisecondsSinceEpoch; appo.isLiveCareAppointment = false; appo.doctorID = widget.doctor.doctorID; appo.appointmentDate = DateUtil.convertDateToString(DateTime.now()); //widget.patientShareResponse.appointmentDate; appo.serviceID = widget.patientShareResponse.serviceID; Navigator.push( context, FadePage( page: PaymentMethod( onSelectedMethod: (String metohd, [String? selectedInstallmentPlan]) { setState(() {}); }, patientShare: widget.patientShareResponse.patientShareWithTax))) .then((value) { selectedPaymentMethod = value[0]; if (value != null) { if (selectedPaymentMethod == "ApplePay") { if (projectViewModel.havePrivilege(103)) { startApplePay(appo, patientShareResponse); } else { openPayment(value, projectViewModel.user, double.parse(patientShareResponse.patientShareWithTax.toString()), patientShareResponse, appo); } } else { openPayment(value, projectViewModel.user, double.parse(patientShareResponse.patientShareWithTax.toString()), patientShareResponse, appo); } projectViewModel.analytics.appointment.payment_method(appointment_type: 'Walk-In', clinic: widget.doctor.clinicName, payment_method: value[0], payment_type: 'appointment'); } }); } void startApplePay(AppoitmentAllHistoryResultList appo, PatientShareResponse patientShareResponse) async { transID = Utils.getAppointmentTransID(appo.projectID, appo.clinicID, appo.appointmentNo); print("TransactionID: $transID"); GifLoaderDialogUtils.showMyDialog(context); LiveCareService service = new LiveCareService(); ApplePayInsertRequest applePayInsertRequest = new ApplePayInsertRequest(); PayfortProjectDetailsRespModel? payfortProjectDetailsRespModel; await context.read().getProjectDetailsForPayfort(projectId: appo.projectID, serviceId: ServiceTypeEnum.appointmentPayment.getIdFromServiceEnum()).then((value) { payfortProjectDetailsRespModel = value!; }); applePayInsertRequest.clientRequestID = transID; applePayInsertRequest.clinicID = appo.clinicID; applePayInsertRequest.currency = projectViewModel.user.outSA == 1 ? "AED" : "SAR"; // applePayInsertRequest.customerEmail = projectViewModel.authenticatedUserObject.user.emailAddress; applePayInsertRequest.customerEmail = "CustID_${projectViewModel.user.patientID}@HMG.com"; applePayInsertRequest.customerID = projectViewModel.user.patientID; applePayInsertRequest.customerName = projectViewModel.user.firstName! + " " + projectViewModel.user.lastName!; applePayInsertRequest.deviceToken = await AppSharedPreferences().getString(PUSH_TOKEN); applePayInsertRequest.voipToken = await AppSharedPreferences().getString(ONESIGNAL_APNS_TOKEN); applePayInsertRequest.doctorID = appo.doctorID; applePayInsertRequest.projectID = appo.projectID.toString(); applePayInsertRequest.serviceID = ServiceTypeEnum.appointmentPayment.getIdFromServiceEnum().toString(); applePayInsertRequest.channelID = 3; applePayInsertRequest.patientID = projectViewModel.user.patientID; applePayInsertRequest.patientTypeID = projectViewModel.user.patientType; applePayInsertRequest.patientOutSA = projectViewModel.user.outSA; applePayInsertRequest.appointmentDate = appo.appointmentDate; applePayInsertRequest.appointmentNo = appo.appointmentNo; applePayInsertRequest.orderDescription = "Appointment Payment"; applePayInsertRequest.liveServiceID = "0"; applePayInsertRequest.latitude = "0.0"; applePayInsertRequest.longitude = "0.0"; applePayInsertRequest.amount = patientShareResponse.patientShareWithTax.toString(); applePayInsertRequest.isSchedule = appo.isLiveCareAppointment! ? "1" : "0"; applePayInsertRequest.language = projectViewModel.isArabic ? 'ar' : 'en'; applePayInsertRequest.languageID = projectViewModel.isArabic ? 1 : 2; applePayInsertRequest.userName = projectViewModel.user.patientID; applePayInsertRequest.responseContinueURL = "http://hmg.com/Documents/success.html"; applePayInsertRequest.backClickUrl = "http://hmg.com/Documents/success.html"; applePayInsertRequest.paymentOption = "ApplePay"; applePayInsertRequest.isMobSDK = true; applePayInsertRequest.merchantReference = transID; applePayInsertRequest.merchantIdentifier = payfortProjectDetailsRespModel!.merchantIdentifier!; applePayInsertRequest.commandType = "PURCHASE"; applePayInsertRequest.signature = payfortProjectDetailsRespModel!.signature; applePayInsertRequest.accessCode = payfortProjectDetailsRespModel!.accessCode; applePayInsertRequest.shaRequestPhrase = payfortProjectDetailsRespModel!.shaRequest; applePayInsertRequest.shaResponsePhrase = payfortProjectDetailsRespModel!.shaResponse; applePayInsertRequest.returnURL = ""; service.applePayInsertRequest(applePayInsertRequest, context).then((res) async { if (res["MessageStatus"] == 1) { await context.read().initiateApplePayWithPayfort( customerName: projectViewModel.user.firstName! + " " + projectViewModel.user.lastName!, // customerEmail: projectViewModel.authenticatedUserObject.user.emailAddress, customerEmail: "CustID_${projectViewModel.user.patientID}@HMG.com", orderDescription: "Walk-In appointment payment", orderAmount: double.parse(patientShareResponse.patientShareWithTax.toString()), merchantReference: transID, payfortProjectDetailsRespModel: payfortProjectDetailsRespModel, currency: projectViewModel.user.outSA == 1 ? "AED" : "SAR", onFailed: (failureResult) async { log("failureResult: ${failureResult.toString()}"); AppToast.showErrorToast(message: failureResult.toString()); }, onSuccess: (successResult) async { log("Payfort: ${successResult.responseMessage}"); await context.read().addPayfortApplePayResponse(projectViewModel.user.patientID!, result: successResult); checkPaymentStatus(appo); }, projectId: appo.projectID, serviceTypeEnum: ServiceTypeEnum.appointmentPayment, ); } else { GifLoaderDialogUtils.hideDialog(context); AppToast.showErrorToast(message: "An error occurred while processing your request"); } }).catchError((err) { print(err); GifLoaderDialogUtils.hideDialog(context); AppToast.showErrorToast(message: err); }); } openPayment(List paymentMethod, AuthenticatedUser authenticatedUser, num amount, PatientShareResponse patientShareResponse, AppoitmentAllHistoryResultList appo) async { browser = new MyInAppBrowser(onExitCallback: onBrowserExit, appo: appo, onLoadStartCallback: onBrowserLoadStart, context: context); selectedPaymentMethod = paymentMethod[0]; selectedInstallments = paymentMethod[1]; transID = Utils.getAppointmentTransID(appo.projectID, appo.clinicID, appo.appointmentNo); browser.openPaymentBrowser( amount, "Walk-In appointment payment", transID!, appo.projectID.toString(), authenticatedUser.emailAddress!, paymentMethod[0]!, authenticatedUser.patientType, authenticatedUser.firstName!, authenticatedUser.patientID, authenticatedUser, browser, widget.patientShareResponse.isLiveCareAppointment!, "2", widget.patientShareResponse.isLiveCareAppointment! ? widget.patientShareResponse.clinicID.toString() : "", context, widget.patientShareResponse.appointmentDate, widget.patientShareResponse.appointmentNo, widget.patientShareResponse.clinicID, widget.patientShareResponse.doctorID, paymentMethod[1]); // } } onBrowserLoadStart(String url) { if (selectedPaymentMethod == "TAMARA") { if (Platform.isAndroid) { Uri uri = new Uri.dataFromString(url); tamaraPaymentStatus = uri.queryParameters['status']; tamaraOrderID = uri.queryParameters['AuthorizePaymentId']; } else { Uri uri = new Uri.dataFromString(url); tamaraPaymentStatus = uri.queryParameters['paymentStatus']; tamaraOrderID = uri.queryParameters['orderId']; } } MyInAppBrowser.successURLS.forEach((element) { if (url.contains(element)) { if (browser.isOpened()) browser.close(); MyInAppBrowser.isPaymentDone = true; return; } }); MyInAppBrowser.errorURLS.forEach((element) { if (url.contains(element)) { if (browser.isOpened()) browser.close(); MyInAppBrowser.isPaymentDone = false; return; } }); } onBrowserExit(AppoitmentAllHistoryResultList appo, bool isPaymentMade) { try { if (selectedPaymentMethod == "TAMARA") { checkTamaraPaymentStatus(transID!, appo); // if (tamaraPaymentStatus != null && tamaraPaymentStatus!.toLowerCase() == "approved") { // updateTamaraRequestStatus("success", "14", Utils.getAppointmentTransID(appo.projectID, appo.clinicID, appo.appointmentNo), tamaraOrderID!, num.parse(selectedInstallments!), appo); // } else { // updateTamaraRequestStatus( // "Failed", "00", Utils.getAppointmentTransID(appo.projectID, appo.clinicID, appo.appointmentNo), tamaraOrderID! != null ? tamaraOrderID! : "", num.parse(selectedInstallments!), appo); // } } else { checkPaymentStatus(appo); } } catch (err) { print(err); } } checkTamaraPaymentStatus(String orderID, AppoitmentAllHistoryResultList appo) { GifLoaderDialogUtils.showMyDialog(context); DoctorsListService service = new DoctorsListService(); service.getTamaraPaymentStatus(orderID).then((res) { GifLoaderDialogUtils.hideDialog(context); if (res["status"].toString().toLowerCase() == "success") { updateTamaraRequestStatus("success", "14", orderID, tamaraOrderID!, int.parse(selectedInstallments!), appo); } else { updateTamaraRequestStatus( "Failed", "00", Utils.getAppointmentTransID(appo.projectID!, appo.clinicID!, appo.appointmentNo!), tamaraOrderID != null ? tamaraOrderID! : "", int.parse(selectedInstallments!), appo); } }).catchError((err) { GifLoaderDialogUtils.hideDialog(context); AppToast.showErrorToast(message: err); print(err); }); } updateTamaraRequestStatus(String responseMessage, String status, String clientRequestID, String tamaraOrderID, num selectedInstallments, AppoitmentAllHistoryResultList appo) { GifLoaderDialogUtils.showMyDialog(context); try { DoctorsListService service = new DoctorsListService(); service.updateTamaraRequestStatus(responseMessage, status, clientRequestID, tamaraOrderID, selectedInstallments).then((res) { GifLoaderDialogUtils.hideDialog(context); if (tamaraPaymentStatus!.toLowerCase() == "approved") { insertWalkInAppointment(context, widget.doctor, widget.initialSlotDuration, tamaraOrderID); } }).catchError((err) { print(err); AppToast.showErrorToast(message: err); GifLoaderDialogUtils.hideDialog(context); }); } catch (err) { print(err); } } addAdvancedNumberRequestTamara(String advanceNumber, String paymentReference, String appointmentID, AppoitmentAllHistoryResultList appo) { DoctorsListService service = new DoctorsListService(); service.addAdvancedNumberRequest(advanceNumber, paymentReference, appointmentID, context).then((res) {}).catchError((err) { GifLoaderDialogUtils.hideDialog(context); AppToast.showErrorToast(message: err); print(err); }); } markAppointmentForTamara(AppoitmentAllHistoryResultList appo) { GifLoaderDialogUtils.showMyDialog(context); DoctorsListService service = new DoctorsListService(); service.markAppointmentForTamara(appo.projectID!, appo.appointmentNo.toString()).then((res) { GifLoaderDialogUtils.hideDialog(context); sendNfcCheckInRequest(projectViewModel.waitingAppointmentNFCCode, 2, int.parse(appo.appointmentNo), projectViewModel.waitingAppointmentProjectID, appo.clinicID); }).catchError((err) { print(err); AppToast.showErrorToast(message: err); GifLoaderDialogUtils.hideDialog(context); }); } checkPaymentStatus(AppoitmentAllHistoryResultList appo) { String txn_ref; num amount; String payment_method; final currency = projectViewModel.user!.outSA == 0 ? "sar" : 'aed'; GifLoaderDialogUtils.showMyDialog(context); DoctorsListService service = new DoctorsListService(); service.checkPaymentStatus(transID!, false, context).then((res) { String paymentInfo = res['Response_Message']; if (paymentInfo == 'Success') { txn_ref = res['Merchant_Reference']; amount = res['Amount']; payment_method = res['PaymentMethod']; GifLoaderDialogUtils.hideDialog(context); insertWalkInAppointment(context, widget.doctor, widget.initialSlotDuration, res); projectViewModel.analytics.appointment.payment_success( appointment_type: 'Walk-In', payment_method: payment_method, clinic: appo.clinicName, hospital: appo.projectName, txn_amount: "$amount", txn_currency: currency, txn_number: txn_ref); } else { GifLoaderDialogUtils.hideDialog(context); AppToast.showErrorToast(message: res['Response_Message']); projectViewModel.analytics.appointment.payment_fail( appointment_type: 'Walk-In', payment_method: selectedPaymentMethod, clinic: appo.clinicName, hospital: appo.projectName, txn_amount: widget.patientShareResponse.patientShareWithTax.toString(), txn_currency: currency, error_type: res['Response_Message']); } }).catchError((err) { GifLoaderDialogUtils.hideDialog(context); AppToast.showErrorToast(message: err.toString()); print(err); }); } Widget showInfo(String title, String des) { return Container( child: Row( children: [ Text( title + ": ", style: TextStyle( fontSize: 14, fontWeight: FontWeight.w600, color: Color(0xFF575757), letterSpacing: -0.4, ), ), Text( des, style: TextStyle( fontSize: 14, fontWeight: FontWeight.w600, color: Colors.black, letterSpacing: -0.48, ), ), ], ), ); } cancelAppointment(DoctorList docObject, AppoitmentAllHistoryResultList appo, BuildContext context, {int? invoiceNumber, int? lineItemNo, String? invoiceNoVP}) async { ConfirmDialog.closeAlertDialog(context); GifLoaderDialogUtils.showMyDialog(context, barrierDismissible: false); DoctorsListService service = new DoctorsListService(); bool isLiveCareSchedule = await this.sharedPref.getBool(IS_LIVECARE_APPOINTMENT) ?? false; service.cancelAppointment(appo, context, isReschedule: true).then((res) { GifLoaderDialogUtils.hideDialog(context); if (res['MessageStatus'] == 1) { Future.delayed(Duration(milliseconds: 500), () async { if (isLiveCareSchedule != null && isLiveCareSchedule) { insertLiveCareScheduledAppointment(context, widget.doctor); } else { insertAppointment(context, widget.doctor, widget.initialSlotDuration, invoiceNumber: invoiceNumber, lineItemNo: lineItemNo, invoiceNoVP: invoiceNoVP); } }); } else { AppToast.showErrorToast(message: res['ErrorEndUserMessage']); } }).catchError((err) { GifLoaderDialogUtils.hideDialog(context); }); } checkPatientNphiesEligibility(DoctorList docObject, String appointmentNo, BuildContext context) { widget.service.checkPatientNphiesEligibility(docObject.projectID!).then((res) { GifLoaderDialogUtils.hideDialog(context); if (res["isNphiesMatchedWithVida"]) { getPatientShare(context, appointmentNo, docObject.clinicID!, docObject.projectID!, docObject); getToDoCount(); } else { ConfirmDialog dialog = ConfirmDialog( isDissmissable: false, context: context, confirmMessage: res['ErrorEndUserMessage'], okText: "Update insurance", cancelText: "Continue as cash", okFunction: () => {openUpdateInsurance()}, cancelFunction: () => {continueAsCash(docObject, appointmentNo, false)}); dialog.showAlertDialog(context); } }).catchError((err) { GifLoaderDialogUtils.hideDialog(context); print(err); }); } void openUpdateInsurance() { Navigator.pushAndRemoveUntil(context, MaterialPageRoute(builder: (context) => LandingPage()), (Route r) => false); Navigator.push(context, FadePage(page: InsuranceUpdate())); } void continueAsCash(DoctorList docObject, String appointmentNo, bool isLiveCareAppointment) { GifLoaderDialogUtils.showMyDialog(context); widget.service.convertPatientToCash(docObject.projectID!).then((res) { GifLoaderDialogUtils.hideDialog(context); if (res["MessageStatus"] == 1) { if (isLiveCareAppointment) { getLiveCareAppointmentPatientShare(context, appointmentNo, docObject!.clinicID!, docObject.projectID!, docObject); } else { getPatientShare(context, appointmentNo, docObject.clinicID!, docObject.projectID!, docObject); } getToDoCount(); } else { AppToast.showErrorToast(message: res["ErrorEndUserMessage"]); } }).catchError((err) { GifLoaderDialogUtils.hideDialog(context); AppToast.showErrorToast(message: err); print(err); }); } void continueAsCashForWalkIn(int projectID) { GifLoaderDialogUtils.showMyDialog(context); widget.service.convertPatientToCash(projectID).then((res) { GifLoaderDialogUtils.hideDialog(context); if (res["MessageStatus"] == 1) { getWalkinAppointmentPatientShare(); } else { AppToast.showErrorToast(message: res["ErrorEndUserMessage"]); } }).catchError((err) { GifLoaderDialogUtils.hideDialog(context); AppToast.showErrorToast(message: err); print(err); }); } insertWalkInAppointment(context, DoctorList docObject, int initialSlotDuration, paymentRes) async { GifLoaderDialogUtils.showMyDialog( context, ); AppoitmentAllHistoryResultList appo = new AppoitmentAllHistoryResultList(); appo.doctorID = docObject.doctorID; appo.clinicID = docObject.clinicID; appo.projectID = docObject.projectID; widget.service .insertWalkInAppointment( docObject.doctorID!, docObject.clinicID!, docObject.projectID!, widget.selectedTime, widget.selectedDate, initialSlotDuration, projectViewModel.isArabic ? 1 : 2, context) .then((res) { if (res['MessageStatus'] == 1) { GifLoaderDialogUtils.hideDialog(context); AppToast.showSuccessToast(message: TranslationBase.of(context).bookedSuccess); appo.appointmentNo = res["AppointmentNo"]; // Add appointment No to the appointment project Future.delayed(Duration(milliseconds: 500), () { if (selectedPaymentMethod == "TAMARA") { markAppointmentForTamara(appo); addAdvancedNumberRequestTamara("Tamara-Advance-0000", paymentRes, res["AppointmentNo"].toString(), appo); } else { if (widget.patientShareResponse.patientShareWithTax != 0 || widget.patientShareResponse.patientShareWithTax != 0.0) { createAdvancePayment(paymentRes, appo); } else { sendNfcCheckInRequest(projectViewModel.waitingAppointmentNFCCode, 2, int.parse(res["AppointmentNo"]), projectViewModel.waitingAppointmentProjectID, appo.clinicID); } } }); } else { GifLoaderDialogUtils.hideDialog(context); AppToast.showErrorToast(message: res['ErrorEndUserMessage']); } }).catchError((err) { GifLoaderDialogUtils.hideDialog(context); AppToast.showErrorToast(message: err); }); } createAdvancePayment(res, AppoitmentAllHistoryResultList appo) { GifLoaderDialogUtils.showMyDialog( context, ); DoctorsListService service = new DoctorsListService(); String paymentReference = res['Fort_id'].toString(); service.createAdvancePayment(appo, appo.projectID.toString(), res['Amount'], res['Fort_id'], res['PaymentMethod'], context).then((res) { GifLoaderDialogUtils.hideDialog(context); addAdvancedNumberRequest( Utils.isVidaPlusProject(projectViewModel, appo.projectID!) ? res['OnlineCheckInAppointments'][0]['AdvanceNumber_VP'].toString() : res['OnlineCheckInAppointments'][0]['AdvanceNumber'].toString(), paymentReference, appo.appointmentNo.toString(), appo); }).catchError((err) { GifLoaderDialogUtils.hideDialog(context); AppToast.showErrorToast(message: err); print(err); }); } addAdvancedNumberRequest(String advanceNumber, String paymentReference, String appointmentID, AppoitmentAllHistoryResultList appo) { GifLoaderDialogUtils.showMyDialog( context, ); DoctorsListService service = new DoctorsListService(); service.addAdvancedNumberRequest(advanceNumber, paymentReference, appointmentID, context).then((res) { GifLoaderDialogUtils.hideDialog(context); sendNfcCheckInRequest(projectViewModel.waitingAppointmentNFCCode, 2, int.parse(appointmentID), projectViewModel.waitingAppointmentProjectID, appo.clinicID); }).catchError((err) { GifLoaderDialogUtils.hideDialog(context); AppToast.showErrorToast(message: err); print(err); }); } sendNfcCheckInRequest(String nfcId, int checkInBy, int appoNo, int projectID, int clinicID) { GifLoaderDialogUtils.showMyDialog(context); DoctorsListService service = new DoctorsListService(); service.sendCheckinNfcRequest(appoNo, nfcId, projectID, checkInBy, clinicID, context).then((res) { GifLoaderDialogUtils.hideDialog(context); _showMyDialog(res["SuccessMsg"], this.context); }).catchError((err) { GifLoaderDialogUtils.hideDialog(context); print(err); _showMyDialog(err, this.context); }); } checkPatientHasDermaPackage(DoctorList doctor, int patientID) { GifLoaderDialogUtils.showMyDialog(context); widget.service .checkPatientHasDermaPackage( patientID!, doctor.clinicID!, doctor.projectID!, doctor.doctorID!, projectViewModel.isArabic ? 1 : 2, context, ) .then((res) { GifLoaderDialogUtils.hideDialog(context); if (res['MessageStatus'] == 1 && res['PatientPackageComponent']['Message'] == 'Success') { PatientPackageComponent package = PatientPackageComponent.fromJson(res['PatientPackageComponent']); ConfirmDialog dialog = ConfirmDialog( context: context, confirmMessage: "${TranslationBase.of(context).existingPackage} ${package.patientPackageComponents![0].procedureName}, ${TranslationBase.of(context).continueOrbookNew}", okText: TranslationBase.of(context).proceedPackage, cancelText: TranslationBase.of(context).newAppointment, okFunction: () => { ConfirmDialog.closeAlertDialog(context), insertAppointment(context, widget.doctor, widget.initialSlotDuration, invoiceNumber: package.patientPackageComponents![0].invoiceNo, lineItemNo: package.patientPackageComponents![0].lineItemNo, invoiceNoVP: package.patientPackageComponents![0].invoiceNo_VP.toString()) }, cancelFunction: () => {insertAppointment(context, widget.doctor, widget.initialSlotDuration)}, ); dialog.showAlertDialog(context); } else { insertAppointment(context, widget.doctor, widget.initialSlotDuration); } }).onError((error, stackTrace) { insertAppointment(context, widget.doctor, widget.initialSlotDuration); }); } insertAppointment(context, DoctorList docObject, int initialSlotDuration, {int? invoiceNumber, int? lineItemNo, String? invoiceNoVP}) async { final timeSlot = DocAvailableAppointments.selectedAppoDateTime; String logs = await sharedPref.getString('selectedLogSlots'); List decodedLogs = json.decode(logs); GifLoaderDialogUtils.showMyDialog(context, barrierDismissible: false); AppoitmentAllHistoryResultList appo; widget.service // .insertAppointment(docObject.doctorID!, docObject.clinicID!, docObject.projectID!, widget.selectedTime, widget.selectedDate, initialSlotDuration, context, 'null', null, null, projectViewModel) .insertAppointment(docObject.doctorID!, docObject.clinicID!, docObject.projectID!, widget.selectedTime, widget.selectedDate, initialSlotDuration, projectViewModel.isArabic ? 1 : 2, context, null, null, null, projectViewModel, invoiceNumber, lineItemNo, invoiceNoVP) .then((res) { if (res['MessageStatus'] == 1) { AppToast.showSuccessToast(message: TranslationBase.of(context).bookedSuccess); Future.delayed(Duration(milliseconds: 500), () { // checkPatientNphiesEligibility(docObject, res['AppointmentNo'], context); getToDoCount(); getPatientShare(context, res['AppointmentNo'], docObject.clinicID!, docObject.projectID!, docObject); }); widget.service.logDoctorFreeSlots(docObject.doctorID!, docObject.clinicID!, docObject.projectID!, decodedLogs, res['AppointmentNo'], context).then((res) { if (res['MessageStatus'] == 1) { print("Logs Saved"); } else { print("Error Saving logs"); } }); projectViewModel.analytics.appointment.book_appointment_confirmation_success(appointment_type: 'regular', dateTime: timeSlot!, doctor: widget.doctor); } else { GifLoaderDialogUtils.hideDialog(context); appo = AppoitmentAllHistoryResultList(); appo.appointmentNo = res['SameClinicApptList'][0]['AppointmentNo']; appo.clinicID = res['SameClinicApptList'][0]['DoctorID']; appo.projectID = res['SameClinicApptList'][0]['ProjectID']; appo.endTime = res['SameClinicApptList'][0]['EndTime']; appo.startTime = res['SameClinicApptList'][0]['StartTime']; appo.doctorID = res['SameClinicApptList'][0]['DoctorID']; appo.isLiveCareAppointment = false; appo.originalClinicID = 0; appo.originalProjectID = 0; appo.appointmentDate = res['SameClinicApptList'][0]['AppointmentDate']; ConfirmDialog dialog = ConfirmDialog( context: context, confirmMessage: res['ErrorEndUserMessage'], okText: TranslationBase.of(context).confirm, cancelText: TranslationBase.of(context).cancel_nocaps, okFunction: () => {cancelAppointment(docObject, appo, context, invoiceNumber: invoiceNumber, lineItemNo: lineItemNo)}, cancelFunction: () => {}, ); dialog.showAlertDialog(context); } }).catchError((err) { GifLoaderDialogUtils.hideDialog(context); AppToast.showErrorToast(message: err, localContext: context); }); projectViewModel.analytics.appointment.book_appointment_click_confirm(appointment_type: 'regular', dateTime: timeSlot!, doctor: widget.doctor); } insertLiveCareScheduledAppointment(context, DoctorList docObject) { final timeSlot = DocAvailableAppointments.selectedAppoDateTime; widget.selectedDate = timeSlot!.toUtc().add(Duration(hours: 3)).toString().split(" ")[0]; widget.selectedTime = timeSlot.toUtc().add(Duration(hours: 3)).toString().split(" ")[1].substring(0, 5); GifLoaderDialogUtils.showMyDialog(context, barrierDismissible: false); AppoitmentAllHistoryResultList appo; widget.service .insertLiveCareScheduleAppointment( docObject!.doctorID!, docObject.clinicID!, docObject.projectID!, docObject.serviceID, widget.selectedTime, widget.selectedDate, projectViewModel.isArabic ? 1 : 2, context) .then((res) { if (res['MessageStatus'] == 1) { AppToast.showSuccessToast(message: TranslationBase.of(context).bookedSuccess); print(res['AppointmentNo']); Future.delayed(new Duration(milliseconds: 500), () { getLiveCareAppointmentPatientShare(context, res['AppointmentNo'], docObject!.clinicID!, docObject.projectID!, docObject); getToDoCount(); }); projectViewModel.analytics.appointment.book_appointment_confirmation_success(appointment_type: 'livecare', dateTime: timeSlot, doctor: widget.doctor); } else { GifLoaderDialogUtils.hideDialog(context); appo = new AppoitmentAllHistoryResultList(); appo.appointmentNo = res['SameClinicApptList'][0]['AppointmentNo']; appo.clinicID = res['SameClinicApptList'][0]['DoctorID']; appo.projectID = res['SameClinicApptList'][0]['ProjectID']; appo.endTime = res['SameClinicApptList'][0]['EndTime']; appo.startTime = res['SameClinicApptList'][0]['StartTime']; appo.doctorID = res['SameClinicApptList'][0]['DoctorID']; appo.isLiveCareAppointment = true; appo.originalClinicID = 0; appo.originalProjectID = 0; appo.appointmentDate = res['SameClinicApptList'][0]['AppointmentDate']; ConfirmDialog dialog = new ConfirmDialog( context: context, confirmMessage: res['ErrorEndUserMessage'], okText: TranslationBase.of(context).confirm, cancelText: TranslationBase.of(context).cancel_nocaps, okFunction: () => {cancelAppointment(docObject, appo, context)}, cancelFunction: () => {}); dialog.showAlertDialog(context); } }).catchError((err) { GifLoaderDialogUtils.hideDialog(context); AppToast.showErrorToast(message: err); print(err); }); projectViewModel.analytics.appointment.book_appointment_click_confirm(appointment_type: 'livecare', dateTime: timeSlot, doctor: widget.doctor); } getToDoCount() { toDoProvider.setState(0, 0, true, toDoProvider.notificationsCount); ClinicListService service = new ClinicListService(); service.getActiveAppointmentNo(context).then((res) { print(res['AppointmentActiveNumber']); if (res['MessageStatus'] == 1) { toDoProvider.setState(res['AppointmentActiveNumber'], res['AncillaryOrderListCount'], true, toDoProvider.notificationsCount); // toDoProvider.setState(res['AppointmentActiveNumber'], true, toDoProvider.notificationsCount); } else {} }).catchError((err) { print(err); }); } getPatientShare(context, String appointmentNo, int clinicID, int projectID, DoctorList docObject) { int languageID = projectViewModel.isArabic ? 1 : 2; String errorMsg = ""; GifLoaderDialogUtils.showMyDialog(context, barrierDismissible: false); widget.service.getPatientShare(appointmentNo, clinicID, projectID, languageID, context).then((res) { projectViewModel.selectedBodyPartList.clear(); projectViewModel.laserSelectionDuration = 0; if (res['OnlineCheckInAppointments'].length != 0) { widget.patientShareResponse = new PatientShareResponse.fromJson(res['OnlineCheckInAppointments'][0]); } isInsured = res["IsInsured"]; isEligible = res["IsEligible"]; isCash = res["IsCash"]; if (isCash) { navigateToBookSuccess(context, docObject, widget.patientShareResponse, isCash); } else { if (isInsured && isEligible) { navigateToBookSuccess(context, docObject, widget.patientShareResponse, isCash); } else { if (isInsured && !isEligible) { errorMsg = TranslationBase.of(context).invalidEligibility; } else { errorMsg = TranslationBase.of(context).invalidInsurance; } ConfirmDialog dialog = new ConfirmDialog( isDissmissable: false, context: context, confirmMessage: errorMsg, okText: TranslationBase.of(context).updateInsuranceText, cancelText: TranslationBase.of(context).continueCash, okFunction: () => {openUpdateInsurance()}, cancelFunction: () => {continueAsCash(docObject, appointmentNo, false)}); dialog.showAlertDialog(context); } } }).catchError((err) { GifLoaderDialogUtils.hideDialog(context); // AppToast.showErrorToast(message: err); projectViewModel.selectedBodyPartList.clear(); projectViewModel.laserSelectionDuration = 0; navigateToHome(context); print(err); }); } getLiveCareAppointmentPatientShare(context, String appointmentNo, int clinicID, int projectID, DoctorList docObject) { String errorMsg = ""; widget.service.getLiveCareAppointmentPatientShare(appointmentNo, clinicID, projectID, projectViewModel.isArabic ? 1 : 2, context).then((res) { widget.patientShareResponse = new PatientShareResponse.fromJson(res); GifLoaderDialogUtils.hideDialog(context); isInsured = res["IsInsured"]; isEligible = res["IsEligible"]; isCash = res["IsCash"]; if (isCash) { navigateToBookSuccess(context, docObject, widget.patientShareResponse, isCash); } else { if (isInsured && isEligible) { navigateToBookSuccess(context, docObject, widget.patientShareResponse, isCash); } else { if (isInsured && !isEligible) { errorMsg = TranslationBase.of(context).invalidEligibility; } else { errorMsg = TranslationBase.of(context).invalidInsurance; } ConfirmDialog dialog = new ConfirmDialog( isDissmissable: false, context: context, confirmMessage: errorMsg, okText: TranslationBase.of(context).updateInsuranceText, cancelText: TranslationBase.of(context).continueCash, okFunction: () => {openUpdateInsurance()}, cancelFunction: () => {continueAsCash(docObject, appointmentNo, true)}); dialog.showAlertDialog(context); } } // navigateToBookSuccess(context, docObject, widget.patientShareResponse, false); }).catchError((err) { GifLoaderDialogUtils.hideDialog(context); AppToast.showErrorToast(message: err); navigateToHome(context); print(err); }); } String getTime(DateTime dateTime) { final DateFormat formatter = DateFormat('HH:mm'); setState(() { widget.appoTimeFormatted = formatter.format(dateTime); print(widget.appoTimeFormatted); }); return widget.appoTimeFormatted; } String getDate() { var dateObj = new DateTime(int.parse(widget.selectedDate.split("-")[0]), int.parse(widget.selectedDate.split("-")[1]), int.parse(widget.selectedDate.split("-")[2]), 0, 0, 0, 0); setState(() { widget.appoDateFormatted = DateUtil.getWeekDay(dateObj.weekday) + ", " + dateObj.day.toString() + " " + DateUtil.getMonth(dateObj.month) + " " + dateObj.year.toString(); }); return DateUtil.getDayMonthYearDateFormatted(dateObj); } DateTime getDateTime() { var parts = widget.selectedTime.split(':'); try { var dateObj = new DateTime(int.parse(widget.selectedDate.split("-")[0]), int.parse(widget.selectedDate.split("-")[1]), int.parse(widget.selectedDate.split("-")[2]), int.parse(parts[0].trim()), int.parse(parts[1].trim()), 0, 0); return dateObj; } catch (e) { var dateObj = new DateTime(int.parse(widget.selectedDate.split("-")[0]), int.parse(widget.selectedDate.split("-")[1]), int.parse(widget.selectedDate.split("-")[2]), 0, 0, 0, 0); return dateObj; } } String getDoctorSpeciality(List docSpecial) { String docSpeciality = ""; docSpecial.forEach((v) { docSpeciality = docSpeciality + v + "\n"; }); return docSpeciality; } // getPatientData() async { // AppSharedPreferences sharedPref = AppSharedPreferences(); // if (await sharedPref.getObject(USER_PROFILE) != null) { // var data = AuthenticatedUser.fromJson(await sharedPref.getObject(USER_PROFILE)); // setState(() { // print(data); // widget.authUser = data; // }); // } // } Future navigateToHome(context) async { Navigator.of(context).popAndPushNamed(HOME); } Future navigateToBookSuccess(context, DoctorList docObject, PatientShareResponse patientShareResponse, bool isCash) async { GifLoaderDialogUtils.hideDialog(context); this.sharedPref.remove(IS_LIVECARE_APPOINTMENT); Navigator.push( context, FadePage( page: BookReminderPage( docObject: docObject, patientShareResponse: patientShareResponse, appoDateFormatted: widget.appoDateFormatted, appoTimeFormatted: widget.selectedTime, dateTime: getDateTime(), isCash: isCash, ), ), ); } Future _showMyDialog(String message, BuildContext context) async { return showDialog( context: context, barrierDismissible: true, // user must tap button! builder: (BuildContext context) { return AlertDialog( title: const Text('Alert'), content: SingleChildScrollView( child: ListBody( children: [ Text(message), ], ), ), actions: [ TextButton( child: const Text('OK'), onPressed: () { Navigator.of(context).pop(); Navigator.pushAndRemoveUntil(context, MaterialPageRoute(builder: (context) => LandingPage()), (Route r) => false); }, ), ], ); }, ); } }