Compare commits

..

No commits in common. 'master' and 'etqan_ovr_integration' have entirely different histories.

File diff suppressed because one or more lines are too long

Before

Width:  |  Height:  |  Size: 31 KiB

File diff suppressed because one or more lines are too long

Before

Width:  |  Height:  |  Size: 31 KiB

File diff suppressed because one or more lines are too long

Before

Width:  |  Height:  |  Size: 730 KiB

@ -1,8 +0,0 @@
<svg xmlns="http://www.w3.org/2000/svg" width="19.5" height="19.5" viewBox="0 0 19.5 19.5">
<g id="graduation-cap" transform="translate(0)">
<path id="cap-top" d="M9.75,4.5L3.5,7.5L9.75,10.5L16,7.5L9.75,4.5Z" fill="#2e303a"/>
<path id="cap-body" d="M4.5,8.5V13.5C4.5,14.5,6.5,16.5,9.75,16.5C13,16.5,15,14.5,15,13.5V8.5L9.75,11.5L4.5,8.5Z" fill="#2e303a"/>
<path id="tassel" d="M16,8V12.5L16.5,13L17,12.5V8H16Z" fill="#2e303a"/>
</g>
</svg>

Before

Width:  |  Height:  |  Size: 457 B

File diff suppressed because one or more lines are too long

Before

Width:  |  Height:  |  Size: 1.2 MiB

File diff suppressed because one or more lines are too long

Before

Width:  |  Height:  |  Size: 1.2 MiB

@ -1,6 +0,0 @@
<svg xmlns="http://www.w3.org/2000/svg" width="32.774" height="32.788" viewBox="0 0 32.774 32.788">
<g id="park-tickets-couple" transform="translate(-0.205 0.001)">
<path id="Path_4724" data-name="Path 4724" d="M68.36,485.746a1.657,1.657,0,0,1-1.581,1.3.539.539,0,0,0-.206,1.025,1.656,1.656,0,0,1,.955,1.814l-.14.7a1.744,1.744,0,0,1-2.093,1.278c-.25-.06-.506-.106-.759-.156-.373-.073-.745-.15-1.118-.223-.493-.1-.985-.2-1.477-.3l-1.76-.353c-.655-.133-1.311-.263-1.967-.4-.7-.14-1.4-.279-2.1-.423-.719-.143-1.438-.289-2.153-.433l-2.133-.429-2.036-.409c-.622-.123-1.241-.25-1.863-.373-.539-.107-1.078-.216-1.614-.323l-1.291-.26-.888-.18c-.136-.027-.273-.057-.409-.083-.007,0-.013,0-.02,0a1.686,1.686,0,0,1-.12,1.062,1.705,1.705,0,0,1-1.87.958.5.5,0,0,0-.562.246l-.3.649a.5.5,0,0,0,.176.589c.033.027,24.018,11.084,24.058,11.094a.5.5,0,0,0,.562-.246l.3-.649a.5.5,0,0,0-.176-.589,1.7,1.7,0,0,1,1.388-3,.5.5,0,0,0,.562-.246l.3-.649a.5.5,0,0,0-.176-.589,1.7,1.7,0,0,1,1.388-3,.5.5,0,0,0,.562-.246l.3-.649a.5.5,0,0,0-.176-.589,1.7,1.7,0,0,1,1.388-3,.5.5,0,0,0,.562-.246l.329-.719a.41.41,0,0,0-.2-.546L68.416,485.5Z" transform="translate(-39.26 -469.349)" fill="#2bb8a6"/>
<path id="Path_4725" data-name="Path 4725" d="M.519,16.168c.04.02,25.932,5.214,25.975,5.214a.5.5,0,0,0,.489-.369l.14-.7a.5.5,0,0,0-.309-.532,1.7,1.7,0,0,1,.652-3.244.5.5,0,0,0,.489-.369l.1-.512.037-.19a.5.5,0,0,0-.309-.532,1.7,1.7,0,0,1,.652-3.244.5.5,0,0,0,.489-.369l.14-.7a.5.5,0,0,0-.309-.532,1.7,1.7,0,0,1,.652-3.244.5.5,0,0,0,.489-.369l.156-.775a.41.41,0,0,0-.323-.482S3.714,0,3.687,0a.412.412,0,0,0-.4.329L3.128,1.1a.5.5,0,0,0,.309.532A1.7,1.7,0,0,1,2.786,4.88.5.5,0,0,0,2.3,5.25l-.14.7a.5.5,0,0,0,.309.532,1.7,1.7,0,0,1-.652,3.244.5.5,0,0,0-.489.369l-.14.7a.5.5,0,0,0,.309.532A1.7,1.7,0,0,1,.842,14.57a.5.5,0,0,0-.489.369l-.14.7A.494.494,0,0,0,.519,16.168ZM22.7,7.639a.831.831,0,1,1,1.631.326l-1.1,5.464L22.555,16.8a.832.832,0,0,1-.815.669.9.9,0,0,1-.163-.017.833.833,0,0,1-.652-.978l.755-3.757ZM7.7,4.628a.831.831,0,0,1,1.631.326L8.948,6.84,8.519,8.98,8.173,10.7l-.616,3.081a.832.832,0,0,1-.815.669.9.9,0,0,1-.163-.017.4.4,0,0,1-.067-.017.829.829,0,0,1-.582-.962l.123-.622.323-1.611Z" fill="#125765"/>
</g>
</svg>

Before

Width:  |  Height:  |  Size: 2.1 KiB

@ -1,16 +0,0 @@
<svg xmlns="http://www.w3.org/2000/svg" width="23.959" height="37.006" viewBox="0 0 23.959 37.006">
<g id="Layer_x0020_1" transform="translate(-300.998)">
<g id="_411123120" transform="translate(301)">
<g id="Group_8657" data-name="Group 8657" transform="translate(3.252)">
<path id="Path_13674" data-name="Path 13674" d="M612.691,6.612H619.8V1.691h-7.111ZM620.669,8.3h-8.823A.833.833,0,0,1,611,7.458V.845A.847.847,0,0,1,611.846,0h8.823a.861.861,0,0,1,.845.845V7.458A.847.847,0,0,1,620.669,8.3Z" transform="translate(-607.531)" fill="#2bb8a6"/>
<path id="Path_13675" data-name="Path 13675" d="M466.845,305h15.089a.833.833,0,0,1,.845.845,5.44,5.44,0,0,1-5.42,5.441h-5.918A5.478,5.478,0,0,1,466,305.845.847.847,0,0,1,466.845,305Z" transform="translate(-465.675 -298.388)" fill="#2bb8a6"/>
<path id="Path_13676" data-name="Path 13676" d="M527.845,0A.861.861,0,0,0,527,.845a.847.847,0,0,0,.846.845h12.444a.851.851,0,0,0,.867-.845A.865.865,0,0,0,540.289,0Z" transform="translate(-525.352)" fill="#2bb8a6"/>
<g id="Group_8656" data-name="Group 8656" transform="translate(0 33.863)">
<path id="Path_13677" data-name="Path 13677" d="M455.553,1562v.867a2.276,2.276,0,1,1-4.553,0V1562h4.553Z" transform="translate(-451 -1562)" fill="#2bb8a6"/>
<path id="Path_13678" data-name="Path 13678" d="M1050.553,1562v.867a2.276,2.276,0,0,1-4.553,0V1562h4.553Z" transform="translate(-1033.101 -1562)" fill="#2bb8a6"/>
</g>
</g>
<path id="Subtraction_59" data-name="Subtraction 59" d="M20570.063,22681.4h-16.975a.817.817,0,0,1-.238-.023,3.388,3.388,0,0,1-2.236-1.018,3.476,3.476,0,0,1-1.02-2.471v-19.4a3.557,3.557,0,0,1,1.02-2.475,3.457,3.457,0,0,1,1.906-.975,1.745,1.745,0,0,0-.193.8,6.288,6.288,0,0,0,6.289,6.285h5.92a6.288,6.288,0,0,0,6.285-6.285,1.692,1.692,0,0,0-.217-.8,3.472,3.472,0,0,1,2.949,3.449v19.4a3.476,3.476,0,0,1-1.02,2.471,3.383,3.383,0,0,1-2.236,1.018A.879.879,0,0,1,20570.063,22681.4Zm-10.756-7.187a2.114,2.114,0,1,0,1.494.619A2.1,2.1,0,0,0,20559.307,22674.211Zm4.027.732-.613.621.961.939-.961.943.613.621.963-.949v0l.973.949.609-.621-.961-.943.961-.939-.609-.621-.973.951Zm-4.025-6.031a2.112,2.112,0,0,0-.807,4.063,2.071,2.071,0,0,0,.809.164,2.113,2.113,0,0,0,0-4.227Zm3.543,1.406-.645.584,1.531,1.7,2.637-2.6-.609-.619-1.992,1.963Zm-3.539-6.709a2.158,2.158,0,0,0-.486.059,2.111,2.111,0,1,0,.969,4.109,2.123,2.123,0,0,0,1.57-2.545A2.1,2.1,0,0,0,20559.313,22663.609Zm3.539,1.266-.645.58,1.531,1.7,2.637-2.6-.609-.619-1.992,1.963Z" transform="translate(-20549.596 -22648.381)" fill="#125765"/>
</g>
</g>
</svg>

Before

Width:  |  Height:  |  Size: 2.5 KiB

@ -1 +0,0 @@
<?xml version="1.0" ?><svg id="Outline" viewBox="0 0 512 512" xmlns="http://www.w3.org/2000/svg"><defs><style>.cls-1{fill:#ffffff;}</style></defs><path style="fill: #FFF" class="cls-1" d="M376,170a11.34,11.34,0,0,0-16,.15L215.28,317.64l-64-65.22a11.34,11.34,0,0,0-16.18,15.88l72.16,73.58a11.35,11.35,0,0,0,16,.15,12,12,0,0,0,1.43-1.7l.4-.37,151-154A11.33,11.33,0,0,0,376,170Z"/><path style="fill: #FFF" class="cls-1" d="M256,58.65c-108.38,0-196.56,88.18-196.56,196.56S147.62,451.77,256,451.77,452.56,363.6,452.56,255.21,364.38,58.65,256,58.65Zm0,370.45c-95.88,0-173.88-78-173.88-173.89S160.12,81.33,256,81.33s173.88,78,173.88,173.88S351.88,429.1,256,429.1Z"/></svg>

Before

Width:  |  Height:  |  Size: 665 B

@ -1 +0,0 @@
<?xml version="1.0" ?><svg data-name="Livello 1" id="Livello_1" viewBox="0 0 128 128" xmlns="http://www.w3.org/2000/svg"><title/><path style="fill: #fff;" d="M64,0a64,64,0,1,0,64,64A64.07,64.07,0,0,0,64,0Zm0,122a58,58,0,1,1,58-58A58.07,58.07,0,0,1,64,122Z"/><path style="fill: #fff;" d="M92.12,35.79a3,3,0,0,0-4.24,0L64,59.75l-23.87-24A3,3,0,0,0,35.88,40L59.76,64,35.88,88a3,3,0,0,0,4.25,4.24L64,68.25l23.88,24A3,3,0,0,0,92.13,88L68.24,64,92.13,40A3,3,0,0,0,92.12,35.79Z"/></svg>

Before

Width:  |  Height:  |  Size: 479 B

@ -533,7 +533,7 @@
"noWinner": "حزين! لم يفز أحد اليوم.",
"myTeam": "فريقي",
"youCanPlayDemo": "لكن يمكنك لعب العرض",
"group": "مجموعة",
"group" : "مجموعة",
"searchGroup": "مجموعة البحث",
"connectHmgWifi": "قم بتوصيل HMG WIFI",
"connectedHmgWifi": "اتصال HMG WIFI",
@ -577,20 +577,20 @@
"versionStatus": "حالة الإصدار",
"supplierNo": "رقم المورد",
"general": "عام",
"requesterOperatingUnit": "وحدة تشغيل مقدم الطلب",
"prepareEmpNum": "إعداد رقم الموظف",
"supplierInfo": "معلومات المورد",
"requesterOperatingUnit":"وحدة تشغيل مقدم الطلب",
"prepareEmpNum":"إعداد رقم الموظف",
"supplierInfo" : "معلومات المورد",
"supplierAcNo": "رقم حساب المورد",
"supplierAcName": "اسم حساب المورد",
"supplierIBAN": "رقم IBAN للمورد",
"supplierCRNo": "رقم السجل التجاري",
"suppliedAcNo": "رقم الحساب المقدم",
"patientRefundInvoice": "فاتورة استرداد الأموال للمريض",
"patientNumber": "رقم المريض",
"patientName": "اسم المريض",
"invoiceDate": "تاريخ الفاتورة",
"refundInvoice": "فاتورة الاسترجاع",
"hospitalClinic": "عيادة المستشفى",
"supplierIBAN" : "رقم IBAN للمورد",
"supplierCRNo" :"رقم السجل التجاري",
"suppliedAcNo" : "رقم الحساب المقدم",
"patientRefundInvoice" : "فاتورة استرداد الأموال للمريض",
"patientNumber" : "رقم المريض",
"patientName" : "اسم المريض",
"invoiceDate" : "تاريخ الفاتورة",
"refundInvoice" :"فاتورة الاسترجاع",
"hospitalClinic" : "عيادة المستشفى",
"graphicalAnalysis": "التحليل الرسومي",
"itemHistoryAnalysis": "تحليل تاريخ العنصر",
"pOno": "امر شراء #",
@ -616,23 +616,23 @@
"members": "الأعضاء",
"searchByUserName": "البحث بواسطة اسم المستخدم",
"shareScreen": "مشاركة الشاشة",
"start": "يبدأ",
"about": "عن",
"start":"يبدأ",
"about":"عن",
"explore": "يستكشف",
"mazaya": "مازيا",
"benefits": "فوائد",
"mazayaDesc": "اكتشف الخصومات والعروض الخاصة المتاحة للموظفين",
"viewallofferMazaya": "أعرض كل المزايا",
"viewallofferMazaya" : "أعرض كل المزايا",
"buyerName": "اسم المشتري",
"buyerNumber": "رقم المشتري",
"highestBidder": "أعلى مزايد",
"remarks": "ملاحظات",
"faHeader": "تفاصيل رأس الصفحة FA",
"bookTypeCode": "رمز نوع الكتاب",
"bookTypeCode": "رمز نوع الكتاب",
"categoryCode": "رمز الفئة",
"categoryGroup": "مجموعة الفئات",
"faLINES": "تفاصيل الأصول",
"assetNumber": "رقم الأصول",
"faLINES": "تفاصيل الأصول",
"assetNumber": "رقم الأصول",
"assetDescription": "وصف الأصول",
"barCodeNumber": "رقم الباركود",
"datePlaceInService": "تاريخ وضعه في الخدمة",
@ -640,22 +640,10 @@
"disposedDate": "تاريخ التخلص",
"netBookValue": "القيمة الدفترية الصافية",
"purchasedPrice": "سعر الشراء",
"usefulLife": "العمر الإنتاجي",
"usefulLife": "العمر الإنتاجي",
"yearsUsed": "سنوات الاستخدام",
"faRequest": "طلب التخلص من FA",
"showMore": "عرض المزيد",
"ticketDetails": "تفاصيل التذكرة",
"currentTicketBalance": "رصيد التذكرة الحالي",
"ticketHistory": "تاريخ التذكرة",
"proceedBooking": "المتابعة للحجز",
"courses": "الدورات التدريبية",
"course": "دورة",
"status": "الحالة",
"deadline": "الموعد النهائي",
"overdue": "متأخر",
"noCoursesAvailable": "لا توجد دورات متاحة",
"pullToRefresh": "اسحب للتحديث",
"courseUrlNotAvailable": "رابط الدورة غير متوفر",
"buyerDetails": "تفاصيل المشتري",
"etqanOVR": "الإبلاغ عن حادثة",
"etqanRequest": "طلبات الحوادث",
@ -669,7 +657,5 @@
"ticketId": "معرف التذكرة",
"pleaseSelectProject": "الرجاء اختيار مشروع",
"viewAttachment" : "عرض المرفق",
"parkingQr": "وقوف السيارات QR",
"startNow": "ابدأ الآن"
}
"parkingQr": "وقوف السيارات QR"
}

@ -567,7 +567,7 @@
"addAtLeastOneAttachment": "Please add at least one attachment.",
"pleaseClickButtonToJoinMarathon": "Press the button below to join the Marathon.",
"youCannotJoinTheMarathon": "You cannot join the Marathon because you have exceeded the time limit.",
"requesterOperatingUnit": "Requester Operating Unit",
"requesterOperatingUnit":"Requester Operating Unit",
"generate": "Generate",
"paymentRequest": "Pay Request",
"paymentDetails": "Payment Details",
@ -593,19 +593,19 @@
"versionStatus": "Version Status",
"supplierNo": "Supplier No",
"general": "General",
"prepareEmpNum": "Prepare Employee Num",
"supplierInfo": "Supplier Information",
"prepareEmpNum":"Prepare Employee Num",
"supplierInfo" : "Supplier Information",
"supplierAcNo": "Supplier Account No",
"supplierAcName": "Supplier Account Name",
"supplierIBAN": "Supplier IBAN",
"supplierCRNo": "CR Number",
"suppliedAcNo": "Supplied Account No.",
"patientRefundInvoice": "Patient Refund Invoice",
"patientNumber": "Patient Number",
"patientName": "Patient Name",
"invoiceDate": "Invoice Date",
"refundInvoice": "Refund Invoice",
"hospitalClinic": "Hospital Clinic",
"supplierAcName":"Supplier Account Name",
"supplierIBAN" : "Supplier IBAN",
"supplierCRNo" : "CR Number",
"suppliedAcNo" : "Supplied Account No.",
"patientRefundInvoice" : "Patient Refund Invoice",
"patientNumber" : "Patient Number",
"patientName" : "Patient Name",
"invoiceDate" : "Invoice Date",
"refundInvoice" :"Refund Invoice",
"hospitalClinic" : "Hospital Clinic",
"graphicalAnalysis": "Graphical Analysis",
"itemHistoryAnalysis": "Item History Analysis",
"pOno": "P.O #",
@ -614,23 +614,23 @@
"qtyReceived": "Qty. Received",
"bonusQty": "Bonus Qty.",
"balQty": "Bal. Qty.",
"start": "Start",
"about": "About",
"start":"Start",
"about":"About",
"explore": "Explore",
"mazaya": "MAZAYA",
"benefits": "Benefits",
"mazayaDesc": "Discover special Discounts and offers available to Employees",
"viewallofferMazaya": "View All Offers",
"viewallofferMazaya" : "View All Offers",
"buyerName": "Buyer Name",
"buyerNumber": "Buyer Number",
"highestBidder": "Highest Bidder",
"remarks": "Remarks",
"faHeader": "FA Header Details",
"bookTypeCode": "Book Type Code",
"bookTypeCode": "Book Type Code",
"categoryCode": "Category Code",
"categoryGroup": "Category Group",
"faLINES": "Asset Details",
"assetNumber": "Asset Number",
"faLINES": "Asset Details",
"assetNumber": "Asset Number",
"assetDescription": "Asset Description",
"barCodeNumber": "BarCode Number",
"datePlaceInService": "Date place In Service",
@ -638,22 +638,10 @@
"disposedDate": "Disposed Date",
"netBookValue": "Net Book Value",
"purchasedPrice": "Purchased Price",
"usefulLife": "Useful Life",
"usefulLife": "Useful Life",
"yearsUsed": "Years Used",
"faRequest": "FA Disposal Request",
"faRequest":"FA Disposal Request",
"showMore": "Show More",
"ticketDetails": "Ticket Details",
"currentTicketBalance": "Current Ticket Balance",
"ticketHistory": "Ticket History",
"proceedBooking": "Proceed For Booking",
"courses": "Courses",
"course": "Course",
"status": "Status",
"deadline": "Deadline",
"overdue": "Overdue",
"noCoursesAvailable": "No Courses Available",
"pullToRefresh": "Pull to refresh",
"courseUrlNotAvailable": "Course URL not available",
"buyerDetails": "Buyer Details",
"etqanOVR": "Report An Incident",
"etqanRequest": "Incident Requests",
@ -667,6 +655,5 @@
"ticketId": "Ticket ID",
"pleaseSelectProject": "Please select a project",
"viewAttachment" : "View Attachment",
"parkingQr": "Parking QR",
"startNow": "Start Now"
"parkingQr": "Parking QR"
}

@ -2,7 +2,6 @@ import 'dart:async';
import 'dart:convert';
import 'dart:io';
import 'package:flutter/cupertino.dart';
import 'package:flutter/foundation.dart';
import 'package:http/http.dart';
import 'package:http/io_client.dart';
@ -19,11 +18,15 @@ class APIError {
dynamic errorCode;
int? errorType;
String? errorMessage;
int? errorStatusCode;
int? errorStatusCode;
APIError(this.errorCode, this.errorMessage, this.errorType, this.errorStatusCode);
Map<String, dynamic> toJson() => {'errorCode': errorCode, 'errorMessage': errorMessage, 'errorType': errorType, 'ErrorStatusCode': errorStatusCode};
Map<String, dynamic> toJson() => {
'errorCode': errorCode,
'errorMessage': errorMessage,
'errorType': errorType,
'ErrorStatusCode': errorStatusCode
};
@override
String toString() {
@ -45,22 +48,22 @@ APIException _throwAPIException(Response response) {
APIError? apiError;
if (response.body != null && response.body.isNotEmpty) {
var jsonError = jsonDecode(response.body);
apiError = APIError(jsonError['ErrorCode'], jsonError['ErrorMessage'], jsonError['ErrorType'], jsonError['ErrorStatusCode']);
apiError = APIError(jsonError['ErrorCode'], jsonError['ErrorMessage'], jsonError['ErrorType'],jsonError['ErrorStatusCode']);
}
return APIException(APIException.BAD_REQUEST, error: apiError);
case 401:
return const APIException(APIException.UNAUTHORIZED);
return APIException(APIException.UNAUTHORIZED);
case 403:
return const APIException(APIException.FORBIDDEN);
return APIException(APIException.FORBIDDEN);
case 404:
return const APIException(APIException.NOT_FOUND);
return APIException(APIException.NOT_FOUND);
case 500:
return const APIException(APIException.INTERNAL_SERVER_ERROR);
return APIException(APIException.INTERNAL_SERVER_ERROR);
case 444:
var downloadUrl = response.headers["location"];
return APIException(APIException.UPGRADE_REQUIRED, arguments: downloadUrl);
default:
return const APIException(APIException.OTHER);
return APIException(APIException.OTHER);
}
}
@ -71,16 +74,8 @@ class ApiClient {
factory ApiClient() => _instance;
Future<U> postJsonForObject<T, U>(
FactoryConstructor<U> factoryConstructor,
String url,
T jsonObject, {
String? token,
Map<String, dynamic>? queryParameters,
Map<String, String>? headers,
int retryTimes = 0,
bool isFormData = false,
}) async {
Future<U> postJsonForObject<T, U>(FactoryConstructor<U> factoryConstructor, String url, T jsonObject,
{String? token, Map<String, dynamic>? queryParameters, Map<String, String>? headers, int retryTimes = 0, bool isFormData = false}) async {
var _headers = {'Accept': 'application/json'};
if (headers != null && headers.isNotEmpty) {
_headers.addAll(headers);
@ -126,15 +121,8 @@ class ApiClient {
}
}
Future<Response> postJsonForResponse<T>(
String url,
T jsonObject, {
String? token,
Map<String, dynamic>? queryParameters,
Map<String, String>? headers,
int retryTimes = 0,
bool isFormData = false,
}) async {
Future<Response> postJsonForResponse<T>(String url, T jsonObject,
{String? token, Map<String, dynamic>? queryParameters, Map<String, String>? headers, int retryTimes = 0, bool isFormData = false}) async {
String? requestBody;
late Map<String, String> stringObj;
if (jsonObject != null) {
@ -169,9 +157,9 @@ class ApiClient {
var queryString = new Uri(queryParameters: queryParameters).query;
url = url + '?' + queryString;
}
var response = await _post(Uri.parse(url), body: requestBody, headers: _headers).timeout(const Duration(seconds: 120));
var response = await _post(Uri.parse(url), body: requestBody, headers: _headers).timeout(Duration(seconds: 120));
if (response.statusCode >= 200 && response.statusCode < 300) {
if (response. statusCode >= 200 && response.statusCode < 300) {
return response;
} else {
throw _throwAPIException(response);
@ -179,7 +167,7 @@ class ApiClient {
} on SocketException catch (e) {
if (retryTimes > 0) {
print('will retry after 3 seconds...');
await Future.delayed(const Duration(seconds: 3));
await Future.delayed(Duration(seconds: 3));
return await _postForResponse(url, requestBody, token: token, queryParameters: queryParameters, headers: headers, retryTimes: retryTimes - 1);
} else {
throw APIException(APIException.OTHER, arguments: e);
@ -187,7 +175,7 @@ class ApiClient {
} on HttpException catch (e) {
if (retryTimes > 0) {
print('will retry after 3 seconds...');
await Future.delayed(const Duration(seconds: 3));
await Future.delayed(Duration(seconds: 3));
return await _postForResponse(url, requestBody, token: token, queryParameters: queryParameters, headers: headers, retryTimes: retryTimes - 1);
} else {
throw APIException(APIException.OTHER, arguments: e);
@ -197,7 +185,7 @@ class ApiClient {
} on ClientException catch (e) {
if (retryTimes > 0) {
print('will retry after 3 seconds...');
await Future.delayed(const Duration(seconds: 3));
await Future.delayed(Duration(seconds: 3));
return await _postForResponse(url, requestBody, token: token, queryParameters: queryParameters, headers: headers, retryTimes: retryTimes - 1);
} else {
throw APIException(APIException.OTHER, arguments: e);
@ -236,7 +224,7 @@ class ApiClient {
var queryString = new Uri(queryParameters: queryParameters).query;
url = url + '?' + queryString;
}
var response = await _get(Uri.parse(url), headers: _headers).timeout(const Duration(seconds: 60));
var response = await _get(Uri.parse(url), headers: _headers).timeout(Duration(seconds: 60));
if (response.statusCode >= 200 && response.statusCode < 300) {
return response;
@ -246,7 +234,7 @@ class ApiClient {
} on SocketException catch (e) {
if (retryTimes > 0) {
print('will retry after 3 seconds...');
await Future.delayed(const Duration(seconds: 3));
await Future.delayed(Duration(seconds: 3));
return await _getForResponse(url, token: token, queryParameters: queryParameters, headers: headers, retryTimes: retryTimes - 1);
} else {
throw APIException(APIException.OTHER, arguments: e);
@ -254,7 +242,7 @@ class ApiClient {
} on HttpException catch (e) {
if (retryTimes > 0) {
print('will retry after 3 seconds...');
await Future.delayed(const Duration(seconds: 3));
await Future.delayed(Duration(seconds: 3));
return await _getForResponse(url, token: token, queryParameters: queryParameters, headers: headers, retryTimes: retryTimes - 1);
} else {
throw APIException(APIException.OTHER, arguments: e);
@ -264,7 +252,7 @@ class ApiClient {
} on ClientException catch (e) {
if (retryTimes > 0) {
print('will retry after 3 seconds...');
await Future.delayed(const Duration(seconds: 3));
await Future.delayed(Duration(seconds: 3));
return await _getForResponse(url, token: token, queryParameters: queryParameters, headers: headers, retryTimes: retryTimes - 1);
} else {
throw APIException(APIException.OTHER, arguments: e);

@ -15,15 +15,11 @@ import 'package:mohem_flutter_app/models/dashboard/get_accural_ticket_balance_mo
import 'package:mohem_flutter_app/models/dashboard/get_attendance_tracking_list_model.dart';
import 'package:mohem_flutter_app/models/dashboard/itg_forms_model.dart';
import 'package:mohem_flutter_app/models/dashboard/list_menu.dart';
import 'package:mohem_flutter_app/models/eit_attachment_ticket_model.dart';
import 'package:mohem_flutter_app/models/dashboard/courses_response_model.dart';
import 'package:mohem_flutter_app/models/generic_response_model.dart';
import 'package:mohem_flutter_app/models/get_employee_parking_details_model.dart';
import 'package:mohem_flutter_app/models/greetings/greeting_card_model.dart';
import 'package:mohem_flutter_app/models/itg/itg_main_response.dart';
import 'package:mohem_flutter_app/models/itg/itg_response_model.dart';
import 'package:mohem_flutter_app/models/sso_auth_model.dart';
// import 'package:platform_device_id/platform_device_id.dart';
import 'package:uuid/uuid.dart';
@ -36,7 +32,7 @@ class DashboardApiClient {
Future<GetAttendanceTracking?> getAttendanceTracking() async {
String url = "${ApiConsts.erpRest}GET_Attendance_Tracking";
Map<String, dynamic> postParams = <String, dynamic>{};
Map<String, dynamic> postParams = {};
postParams.addAll(AppState().postParamsJson);
return await ApiClient().postJsonForObject(
(json) {
@ -50,7 +46,7 @@ class DashboardApiClient {
Future<GenericResponseModel?> getOpenNotifications() async {
String url = "${ApiConsts.erpRest}GET_OPEN_NOTIFICATIONS";
Map<String, dynamic> postParams = <String, dynamic>{};
Map<String, dynamic> postParams = {};
postParams.addAll(AppState().postParamsJson);
return await ApiClient().postJsonForObject(
(json) {
@ -64,7 +60,7 @@ class DashboardApiClient {
Future<GenericResponseModel?> getCOCNotifications() async {
String url = "${ApiConsts.cocRest}Mohemm_ITG_ReviewerAdmin_Pending_Tasks";
Map<String, dynamic> postParams = <String, dynamic>{"Date": DateUtil.getISODateFormat(DateTime.now()), "EmployeeNumber": AppState().memberInformationList?.eMPLOYEENUMBER};
Map<String, dynamic> postParams = {"Date": DateUtil.getISODateFormat(DateTime.now()), "EmployeeNumber": AppState().memberInformationList?.eMPLOYEENUMBER};
postParams.addAll(AppState().postParamsJson);
return await ApiClient().postJsonForObject(
(json) {
@ -78,7 +74,7 @@ class DashboardApiClient {
Future<ItgFormsModel?> getItgFormsPendingTask() async {
String url = "${ApiConsts.cocRest}ITGFormsPendingTasks";
Map<String, dynamic> postParams = <String, dynamic>{};
Map<String, dynamic> postParams = {};
postParams.addAll(AppState().postParamsJson);
return await ApiClient().postJsonForObject(
(json) {
@ -92,13 +88,13 @@ class DashboardApiClient {
Future<List<GetAccrualBalancesList>> getAccrualBalances(String effectiveDate, {String? empID}) async {
String url = "${ApiConsts.erpRest}GET_ACCRUAL_BALANCES";
Map<String, dynamic> postParams = <String, dynamic>{"P_EFFECTIVE_DATE": effectiveDate};
Map<String, dynamic> postParams = {"P_EFFECTIVE_DATE": effectiveDate};
postParams.addAll(AppState().postParamsJson);
if (empID != null) postParams["P_SELECTED_EMPLOYEE_NUMBER"] = empID;
return await ApiClient().postJsonForObject(
(json) {
GenericResponseModel responseData = GenericResponseModel.fromJson(json);
return responseData.getAccrualBalancesList ?? <GetAccrualBalancesList>[];
return responseData.getAccrualBalancesList ?? [];
},
url,
postParams,
@ -107,13 +103,13 @@ class DashboardApiClient {
Future<List<GetTicketAccuralBalanceModel>> getTicketAccuralBalance(String effectiveDate, {String? empID}) async {
String url = "${ApiConsts.erpRest}GET_TICKET_ACCRUAL_BALANCES";
Map<String, dynamic> postParams = <String, dynamic>{"P_EFFECTIVE_DATE": effectiveDate};
Map<String, dynamic> postParams = {"P_EFFECTIVE_DATE": effectiveDate};
postParams.addAll(AppState().postParamsJson);
if (empID != null) postParams["P_SELECTED_EMPLOYEE_NUMBER"] = empID;
return await ApiClient().postJsonForObject(
(json) {
GenericResponseModel responseData = GenericResponseModel.fromJson(json);
return responseData.getAccrualBalancesTicketList ?? <GetTicketAccuralBalanceModel>[];
return responseData.getAccrualBalancesTicketList ?? [];
},
url,
postParams,
@ -122,7 +118,7 @@ class DashboardApiClient {
Future<GenericResponseModel?> getOpenMissingSwipes() async {
String url = "${ApiConsts.erpRest}GET_OPEN_MISSING_SWIPES";
Map<String, dynamic> postParams = <String, dynamic>{};
Map<String, dynamic> postParams = {};
postParams.addAll(AppState().postParamsJson);
return await ApiClient().postJsonForObject(
(json) {
@ -137,12 +133,12 @@ class DashboardApiClient {
//Menus List
Future<List<ListMenu>> getListMenu() async {
String url = "${ApiConsts.erpRest}GET_MENU";
Map<String, dynamic> postParams = <String, dynamic>{};
Map<String, dynamic> postParams = {};
postParams.addAll(AppState().postParamsJson);
return await ApiClient().postJsonForObject(
(json) {
GenericResponseModel responseData = GenericResponseModel.fromJson(json);
return responseData.listMenu ?? <ListMenu>[];
return responseData.listMenu ?? [];
},
url,
postParams,
@ -152,7 +148,7 @@ class DashboardApiClient {
//GET_MENU_ENTRIES
Future<GenericResponseModel?> getGetMenuEntries() async {
String url = "${ApiConsts.erpRest}GET_MENU_ENTRIES";
Map<String, dynamic> postParams = <String, dynamic>{"P_SELECTED_RESP_ID": -999, "P_MENU_TYPE": "E"};
Map<String, dynamic> postParams = {"P_SELECTED_RESP_ID": -999, "P_MENU_TYPE": "E"};
postParams.addAll(AppState().postParamsJson);
return await ApiClient().postJsonForObject(
(json) {
@ -166,7 +162,7 @@ class DashboardApiClient {
Future<GenericResponseModel?> getEventActivity() async {
String url = "${ApiConsts.erpRest}Get_EventActivity";
Map<String, dynamic> postParams = <String, dynamic>{"P_SELECTED_RESP_ID": -999, "P_MENU_TYPE": "E"};
Map<String, dynamic> postParams = {"P_SELECTED_RESP_ID": -999, "P_MENU_TYPE": "E"};
postParams.addAll(AppState().postParamsJson);
return await ApiClient().postJsonForObject(
(json) {
@ -180,7 +176,7 @@ class DashboardApiClient {
Future<GenericResponseModel?> getTicketBookingRedirection() async {
String url = "${ApiConsts.erpRest}GET_PORTAL_REDIRECTION";
Map<String, dynamic> postParams = <String, dynamic>{"P_USER_NAME": AppState().memberInformationList?.eMPLOYEENUMBER};
Map<String, dynamic> postParams = {"P_USER_NAME": AppState().memberInformationList?.eMPLOYEENUMBER};
postParams.addAll(AppState().postParamsJson);
return await ApiClient().postJsonForObject(
(json) {
@ -194,7 +190,7 @@ class DashboardApiClient {
Future<GenericResponseModel?> getTicketBalance() async {
String url = "${ApiConsts.erpRest}GET_TICKET_BALANCE";
Map<String, dynamic> postParams = <String, dynamic>{"P_USER_NAME": AppState().memberInformationList?.eMPLOYEENUMBER};
Map<String, dynamic> postParams = {"P_USER_NAME": AppState().memberInformationList?.eMPLOYEENUMBER};
postParams.addAll(AppState().postParamsJson);
return await ApiClient().postJsonForObject(
@ -211,7 +207,7 @@ class DashboardApiClient {
String url = "${ApiConsts.ssoAuthRedirection}?grantType=mohemm";
//https://sso-uat.hmg.com/api/auth/connect?grantType=mohemm'
// Map<String, dynamic> postParams = {"P_USER_NAME": AppState().memberInformationList?.eMPLOYEENUMBER};
Map<String, dynamic> postParams = <String, dynamic>{
Map<String, dynamic> postParams = {
"ClientId": clientID,
// "ClientId": "a9f4d1a0596d4aea8f830992ec4bdac1",
"PersonId": AppState().memberInformationList?.eMPLOYEENUMBER,
@ -230,35 +226,20 @@ class DashboardApiClient {
);
}
Future<GetEitAttachmentTicket?> getTicketEitPDFDownload({required String peiExtraInfoId}) async {
String url = "${ApiConsts.erpRest}GET_EIT_ATTACHMENTS";
Map<String, dynamic> postParams = <String, dynamic>{
"P_PERSON_EXTRA_INFO_ID": peiExtraInfoId,
"PersonId": AppState().memberInformationList?.eMPLOYEENUMBER,
"Username": AppState().memberInformationList?.eMPLOYEENUMBER,
"Language": "US",
"SessionId": AppState().postParamsObject?.pSessionId,
};
postParams.addAll(AppState().postParamsJson);
return await ApiClient().postJsonForObject(
(json) {
GetEitAttachmentTicket responseData = GetEitAttachmentTicket.fromJson(json);
return responseData;
},
url,
postParams,
);
}
Future<dynamic> getBookingSSOFinalRedirection({required String token}) async {
// token =
// "eyJhbGciOiJSUzI1NiIsImtpZCI6IjhjZTE2OWM0YjIwYjQ2ZWM5YTQyOTU3Y2ZhODUzNzQ1IiwidHlwIjoiSldUIn0.eyJ0ZW5hbnRfaWQiOiJhOWY0ZDFhMDU5NmQ0YWVhOGY4MzA5OTJlYzRiZGFjMSIsImVpZCI6IjExNzkzMCIsImh0dHA6Ly9zY2hlbWFzLnhtbHNvYXAub3JnL3dzLzIwMDUvMDUvaWRlbnRpdHkvY2xhaW1zL3NpZCI6Ijk2MDI0OGM1NzA3YzQ3MmFhYTEzM2I1N2ZhODE1ZmVhIiwibGFuZ3VhZ2UiOiJVUyIsImh0dHA6Ly9zY2hlbWFzLnhtbHNvYXAub3JnL3dzLzIwMDUvMDUvaWRlbnRpdHkvY2xhaW1zL2VtYWlsYWRkcmVzcyI6IjExNzkzMEBobWcuY29tIiwiZXhwIjoxNzgyNDc1NzY5LCJpc3MiOiJodHRwczovL3Nzby11YXQuaG1nLmNvbSIsImF1ZCI6ImE5ZjRkMWEwNTk2ZDRhZWE4ZjgzMDk5MmVjNGJkYWMxIn0.rJcLVsG8D0XECyLERCTD2uqGeWyvp-OBVGE9uL2qKrX4etFUHgdFt_5kYF6edFTtGy-0PIZadHDmv7e-IOhVWHm5HVMClaukiXoRXR8cDN8XA1wfme3Kd-U5PXN-IRh49AyRTzLO0rYNPvH81ScosWGlsFSkOvA-0hJNa2adHdtvgNvB8wJshSU5p7sAmF8mjdDY6aInG19etu2iEuUDwHHA4ZY_ts4hboHo8fE392hFaYGonExoD7bpW5RMx5xKWeRCmWpG_PK8Aw_z1jGzdB9PANus4pteRGuln1J-kmo2lQC9pVrSyZATAKp1HfgfyZ_vUhaHEfM69cMWaCslJQ";
http.MultipartRequest request = http.MultipartRequest('POST', Uri.parse('https://www.paxes.com/sso/hmg'));
// http.MultipartRequest request = http.MultipartRequest('POST', Uri.parse('https://ek.techmaster.in/SSO/HMG'));
request.fields.addAll(<String, String>{'JWTToken': token});
// // var request = http.MultipartRequest('POST', Uri.parse('https://ek.techmaster.in/SSO/HMG'));
var request = http.MultipartRequest('POST', Uri.parse('https://Paxes-release.techmaster.in/SSO/HMG')); // UAT
// var request = http.MultipartRequest('POST', Uri.parse('https://paxes.com/sso/hmg')); // Prod
request.fields.addAll({'JWTToken': token});
// request.headers.addAll(headers);
http.StreamedResponse response = await request.send();
if (response.statusCode == 302) {
String res = await response.stream.bytesToString();
print("================== post ==========");
var res = await response.stream.bytesToString();
return response.headers["location"];
} else {
print(response.reasonPhrase);
@ -278,7 +259,7 @@ class DashboardApiClient {
var _mobileDeviceIdentifierPlugin = MobileDeviceIdentifier();
Codec<String, String> stringToBase64 = utf8.fuse(base64);
String url = "${ApiConsts.swpRest}AuthenticateAndSwipeUserSupportNFC";
Uuid uuid = Uuid();
var uuid = Uuid();
String? deviceId = "";
// Generate a v4 (random) id
if (Platform.isAndroid) {
@ -290,7 +271,7 @@ class DashboardApiClient {
IosDeviceInfo iosInfo = await DeviceInfoPlugin().iosInfo;
deviceId = iosInfo.identifierForVendor;
}
Map<String, dynamic> postParams = <String, dynamic>{
Map<String, dynamic> postParams = {
"UID": deviceId, //uuid.v4(), //Mobile Id
// "UID": uuid.v4(), //Mobile Id
"Latitude": lat,
@ -316,10 +297,10 @@ class DashboardApiClient {
//Mark Fake Location
Future<GenericResponseModel?> markFakeLocation({String lat = "0", String? long = "0", required String sourceName}) async {
String url = "${ApiConsts.swpRest}CreateIssueInfo";
Uuid uuid = Uuid();
var uuid = Uuid();
// Generate a v4 (random) id
Map<String, dynamic> postParams = <String, dynamic>{
Map<String, dynamic> postParams = {
"UID": uuid.v4(), //Mobile Id
"Latitude": lat,
"Longitude": long,
@ -343,7 +324,7 @@ class DashboardApiClient {
Future<MohemmItgResponseItem?> getITGPageNotification() async {
String url = "${ApiConsts.cocRest}Mohemm_ITG_GetPageNotification";
Map<String, dynamic> postParams = <String, dynamic>{
Map<String, dynamic> postParams = {
"EmployeeNumber": AppState().getUserName,
"ItgEnableAt": "After Service Submission", //Mobile Id
"ItgServiceName": "Login",
@ -365,7 +346,7 @@ class DashboardApiClient {
Future<ItgMainRes?> submitItgForm({required String comment, required String masterId, required List<Map<String, dynamic>> itgList, required int serviceId}) async {
String url = "${ApiConsts.cocRest}Mohemm_ITG_Survey_Response";
Map<String, dynamic> postParams = <String, dynamic>{
Map<String, dynamic> postParams = {
"EmployeeNumber": AppState().getUserName,
"ItgComments": comment,
"ItgNotificationMasterId": masterId,
@ -386,7 +367,7 @@ class DashboardApiClient {
Future<ItgMainRes?> getAdvertisementDetail(String masterID) async {
String url = "${ApiConsts.cocRest}Mohemm_ITG_GetPageNotificationDetails";
Map<String, dynamic> postParams = <String, dynamic>{
Map<String, dynamic> postParams = {
"EmployeeNumber": AppState().getUserName,
"ItgNotificationMasterId": masterID, //Mobile Id
};
@ -404,7 +385,7 @@ class DashboardApiClient {
Future setAdvertisementViewed(String masterID, int advertisementId, String? ackValue) async {
String url = "${ApiConsts.cocRest}Mohemm_ITG_UpdateAdvertisementAsViewed";
Map<String, dynamic> postParams = <String, dynamic>{
Map<String, dynamic> postParams = {
"ItgNotificationMasterId": masterID,
"EmployeeNumber": AppState().memberInformationList!.eMPLOYEENUMBER.toString(),
"ItgAdvertisementId": advertisementId,
@ -449,43 +430,4 @@ class DashboardApiClient {
postParams,
);
}
//Fetch All Courses Status
Future<CoursesResponseModel?> fetchAllCoursesStatus() async {
String url = ApiConsts.eLearningBaseUrl +"Fetch_All_Courses_Status.php";
Map<String, String> headers = {
'x-api-key': 'bLi@mbXJeXTHd/)h&LFh%25+%25(Nbnaq6hBg%7d%5dyQbthY%7bv6ew6-5UT\$NASwucn%7d,_PSJpuwNCCen2%7djj%7b00HR2T-%5b,k7W%7d-0yepK?%258',
'Content-Type': 'application/x-www-form-urlencoded',
};
Map<String, dynamic> postParams = {
"username": AppState().memberInformationList?.eMPLOYEENUMBER ?? "",
};
return await ApiClient().postJsonForObject(
(json) {
CoursesResponseModel responseData = CoursesResponseModel.fromJson(json);
return responseData;
},
url,
postParams,
headers: headers,
isFormData: false,
);
}
Future<GetGreetingCardsModelResponse?> getGreetingCards() async {
String url = "${ApiConsts.erpRest}Get_GreetingCards";
Map<String, dynamic> postParams = {};
postParams.addAll(AppState().postParamsJson);
return await ApiClient().postJsonForObject(
(json) {
GetGreetingCardsModelResponse responseData = GetGreetingCardsModelResponse.fromJson(json);
return responseData;
},
url,
postParams,
);
}
}

@ -25,23 +25,16 @@ class EITApiClient {
postParams.addAll(AppState().postParamsJson);
return await ApiClient().postJsonForObject(
(json) {
// Check if GetEITTransactionList exists and is not empty
if (json['GetEITTransactionList'] == null || (json['GetEITTransactionList'] is List && json['GetEITTransactionList'].isEmpty)) {
return isCompleteList ? <List<CollectionTransaction>>[] : <CollectionTransaction>[];
}
if (isCompleteList) {
List<List<CollectionTransaction>> responseData = [];
json['GetEITTransactionList'].forEach((element) {
var transactionList = GetEitTransactionsModel.fromJson(element).collectionTransaction;
if (transactionList != null && transactionList.isNotEmpty) {
responseData.add(transactionList);
}
if (transactionList != null) responseData.add(transactionList);
});
return responseData;
} else {
List<CollectionTransaction>? responseData = GetEitTransactionsModel.fromJson(json['GetEITTransactionList'][0]).collectionTransaction;
return responseData ?? <CollectionTransaction>[];
return responseData;
}
},
url,

@ -90,7 +90,7 @@ class AppState {
String get getHuaweiPushToken => _huaweiPushToken;
final PostParamsModel _postParamsInitConfig = PostParamsModel(channel: 31, versionID: 9.9, mobileType: Platform.isAndroid ? "android" : "ios");
final PostParamsModel _postParamsInitConfig = PostParamsModel(channel: 31, versionID: 9.5, mobileType: Platform.isAndroid ? "android" : "ios");
void setPostParamsInitConfig() {
isAuthenticated = false;

@ -4,19 +4,13 @@ class ApiConsts {
// static String baseUrl = "http://10.200.204.11"; // Local server
// static String baseUrl = "https://erptstapp.srca.org.sa"; // SRCA server
// static String baseUrl = "https://uat.hmgwebservices.com"; // UAT ser343622ver
// static String baseUrl = "http://10.201.204.101:2024";
static String baseUrl = "https://uat.hmgwebservices.com"; // UAT ser343622ver
// static String baseUrl = "http://10.201.204.101:2024";
// static String baseUrl = "https://webservices.hmg.com"; // PreProd
// static String baseUrl = "https://hmgwebservices.com"; // Live server
static String baseUrl = "https://mohemm.hmg.com"; // New Live server
static String ssoBaseUrl = "https://sso.hmg.com"; // New Live server
//
// static String baseUrl = "https://uat.hmgwebservices.com"; // UAT ser343622ver
// static String baseUrl = "http://10.20.200.111:1010/";
// static String baseUrl = "https://mohemm.hmg.com"; // New Live server
//static String eLearningBaseUrl = "https://elearning.hmg.com/moodle_dev/api/"; // Elearning server UAT
static String eLearningBaseUrl = "https://elearning.hmg.com/moodle/api/"; // Elearning server live
//
// static String baseUrl = "http://10.20.200.111:1010/";
@ -33,8 +27,8 @@ class ApiConsts {
static String user = baseUrlServices + "api/User/";
static String cocRest = baseUrlServices + "COCWS.svc/REST/";
static String ssoAuthRedirection = ssoBaseUrl + "/api/auth/connect";
static String ssoAuthRedirection = "https://sso-uat.hmg.com/api/auth/connect"; // UAT
// static String ssoAuthRedirection = "https://sso.hmg.com/api/auth/connect"; // Prod
//Chat
static String chatServerBaseUrl = "https://apiderichat.hmg.com/";
@ -62,7 +56,6 @@ class ApiConsts {
static String marathonBaseUrlUAT = "https://marathoon.com/uatservice/api/";
static String marathonBaseUrl = marathonBaseUrlLive;
// static String marathonBaseUrl = marathonBaseUrlUAT;
static String marathonBaseUrlServices = "https://marathoon.com/service/";
static String marathonParticipantLoginUrl = marathonBaseUrl + "auth/participantlogin";
@ -94,3 +87,5 @@ class SharedPrefsConsts {
static String mohemmWifiPassword = "mohemmWifiPassword";
static String editItemForSale = "editItemForSale";
}

@ -58,7 +58,6 @@ import 'package:mohem_flutter_app/ui/profile/profile_screen.dart';
import 'package:mohem_flutter_app/ui/screens/announcements/announcement_details.dart';
import 'package:mohem_flutter_app/ui/screens/announcements/announcements.dart';
import 'package:mohem_flutter_app/ui/screens/child_education/child_education_assistance.dart';
import 'package:mohem_flutter_app/ui/screens/courses/courses_screen.dart';
// import 'package:mohem_flutter_app/ui/my_attendance/work_from_home_screen.dart';
import 'package:mohem_flutter_app/ui/screens/eit/add_eit.dart';
import 'package:mohem_flutter_app/ui/screens/event_activity/event_activity.dart';
@ -171,9 +170,6 @@ class AppRoutes {
static const String offersAndDiscounts = "/offersAndDiscounts";
static const String offersAndDiscountsDetails = "/offersAndDiscountsDetails";
// Courses
static const String courses = "/courses";
//Pay slip
static const String monthlyPaySlip = "/monthlyPaySlip";
@ -306,9 +302,6 @@ class AppRoutes {
offersAndDiscounts: (BuildContext context) => OffersAndDiscountsHome(),
offersAndDiscountsDetails: (BuildContext context) => OffersAndDiscountsDetails(),
// Courses
courses: (BuildContext context) => const CoursesScreen(),
//pay slip
monthlyPaySlip: (BuildContext context) => MonthlyPaySlipScreen(),
performanceEvaluation: (BuildContext context) => PerformanceAppraisal(),

@ -657,18 +657,6 @@ class CodegenLoader extends AssetLoader{
"yearsUsed": "سنوات الاستخدام",
"faRequest": "طلب التخلص من FA",
"showMore": "عرض المزيد",
"ticketDetails": "تفاصيل التذكرة",
"currentTicketBalance": "رصيد التذكرة الحالي",
"ticketHistory": "تاريخ التذكرة",
"proceedBooking": "المتابعة للحجز",
"courses": "الدورات التدريبية",
"course": "دورة",
"status": "الحالة",
"deadline": "الموعد النهائي",
"overdue": "متأخر",
"noCoursesAvailable": "لا توجد دورات متاحة",
"pullToRefresh": "اسحب للتحديث",
"courseUrlNotAvailable": "رابط الدورة غير متوفر",
"buyerDetails": "تفاصيل المشتري",
"etqanOVR": "الإبلاغ عن حادثة",
"etqanRequest": "طلبات الحوادث",
@ -682,8 +670,7 @@ class CodegenLoader extends AssetLoader{
"ticketId": "معرف التذكرة",
"pleaseSelectProject": "الرجاء اختيار مشروع",
"viewAttachment": "عرض المرفق",
"parkingQr": "وقوف السيارات QR",
"startNow": "ابدأ الآن"
"parkingQr": "وقوف السيارات QR"
};
static const Map<String,dynamic> _en_US = {
"mohemm": "Mohemm",
@ -1328,18 +1315,6 @@ static const Map<String,dynamic> _en_US = {
"yearsUsed": "Years Used",
"faRequest": "FA Disposal Request",
"showMore": "Show More",
"ticketDetails": "Ticket Details",
"currentTicketBalance": "Current Ticket Balance",
"ticketHistory": "Ticket History",
"proceedBooking": "Proceed For Booking",
"courses": "Courses",
"course": "Course",
"status": "Status",
"deadline": "Deadline",
"overdue": "Overdue",
"noCoursesAvailable": "No Courses Available",
"pullToRefresh": "Pull to refresh",
"courseUrlNotAvailable": "Course URL not available",
"buyerDetails": "Buyer Details",
"etqanOVR": "Report An Incident",
"etqanRequest": "Incident Requests",
@ -1353,8 +1328,7 @@ static const Map<String,dynamic> _en_US = {
"ticketId": "Ticket ID",
"pleaseSelectProject": "Please select a project",
"viewAttachment": "View Attachment",
"parkingQr": "Parking QR",
"startNow": "Start Now"
"parkingQr": "Parking QR"
};
static const Map<String, Map<String,dynamic>> mapLocales = {"ar_SA": _ar_SA, "en_US": _en_US};
}

@ -629,18 +629,6 @@ abstract class LocaleKeys {
static const yearsUsed = 'yearsUsed';
static const faRequest = 'faRequest';
static const showMore = 'showMore';
static const ticketDetails = 'ticketDetails';
static const currentTicketBalance = 'currentTicketBalance';
static const ticketHistory = 'ticketHistory';
static const proceedBooking = 'proceedBooking';
static const courses = 'courses';
static const course = 'course';
static const status = 'status';
static const deadline = 'deadline';
static const overdue = 'overdue';
static const noCoursesAvailable = 'noCoursesAvailable';
static const pullToRefresh = 'pullToRefresh';
static const courseUrlNotAvailable = 'courseUrlNotAvailable';
static const buyerDetails = 'buyerDetails';
static const etqanOVR = 'etqanOVR';
static const etqanRequest = 'etqanRequest';
@ -655,6 +643,5 @@ abstract class LocaleKeys {
static const pleaseSelectProject = 'pleaseSelectProject';
static const viewAttachment = 'viewAttachment';
static const parkingQr = 'parkingQr';
static const startNow = 'startNow';
}

@ -1,94 +0,0 @@
class CoursesResponseModel {
bool? success;
int? status;
String? username;
List<CourseStatus>? coursesStatus;
int? totalCourses;
CoursesResponseModel({
this.success,
this.status,
this.username,
this.coursesStatus,
this.totalCourses,
});
CoursesResponseModel.fromJson(Map<String, dynamic> json) {
success = json['success'];
status = json['status'];
username = json['username'];
if (json['courses_status'] != null) {
coursesStatus = <CourseStatus>[];
json['courses_status'].forEach((v) {
coursesStatus!.add(CourseStatus.fromJson(v));
});
}
totalCourses = json['total_courses'];
}
Map<String, dynamic> toJson() {
Map<String, dynamic> data = <String, dynamic>{};
data['success'] = success;
data['status'] = status;
data['username'] = username;
if (coursesStatus != null) {
data['courses_status'] = coursesStatus!.map((v) => v.toJson()).toList();
}
data['total_courses'] = totalCourses;
return data;
}
}
class CourseStatus {
String? cId;
String? cFullname;
String? cNameAr;
String? cShortname;
String? cStatus;
String? cIsMohemmAffective;
String? cStartdate;
String? cEnddate;
String? cUrl;
String? token;
CourseStatus({
this.cId,
this.cFullname,
this.cNameAr,
this.cShortname,
this.cStatus,
this.cIsMohemmAffective,
this.cStartdate,
this.cEnddate,
this.cUrl,
this.token
});
CourseStatus.fromJson(Map<String, dynamic> json) {
cId = json['c_id'];
cFullname = json['c_fullname'];
cNameAr = json['c_name_ar'];
cShortname = json['c_shortname'];
cStatus = json['c_status'];
cIsMohemmAffective = json['c_is_mohemm_affective'];
cStartdate = json['c_startdate'];
cEnddate = json['c_enddate'];
cUrl = json['c_url'];
token =json['c_token'];
}
Map<String, dynamic> toJson() {
Map<String, dynamic> data = <String, dynamic>{};
data['c_id'] = cId;
data['c_fullname'] = cFullname;
data['c_name_ar'] = cNameAr;
data['c_shortname'] = cShortname;
data['c_status'] = cStatus;
data['c_is_mohemm_affective'] = cIsMohemmAffective;
data['c_startdate'] = cStartdate;
data['c_enddate'] = cEnddate;
data['c_url'] = cUrl;
data['c_token'] = token;
return data;
}
}

@ -30,7 +30,7 @@ class CollectionTransaction {
String? dISPLAYFLAG;
int? fROMROWNUM;
int? nOOFROWS;
dynamic nUMBERVALUE;
dynamic? nUMBERVALUE;
int? rOWNUM;
String? sEGMENTNAME;
String? sEGMENTPROMPT;
@ -80,7 +80,7 @@ class CollectionTransaction {
}
Map<String, dynamic> toJson() {
Map<String, dynamic> data = Map<String, dynamic>();
Map<String, dynamic> data = new Map<String, dynamic>();
data['APPLICATION_COLUMN_NAME'] = this.aPPLICATIONCOLUMNNAME;
data['DATATYPE'] = this.dATATYPE;
data['DATE_VALUE'] = this.dATEVALUE;

@ -1,97 +0,0 @@
import 'dart:convert';
class GetEitAttachmentTicket {
List<GetEitAttachmentList>? getEitAttachmentList;
GetEitAttachmentTicket({
this.getEitAttachmentList,
});
factory GetEitAttachmentTicket.fromRawJson(String str) => GetEitAttachmentTicket.fromJson(json.decode(str));
String toRawJson() => json.encode(toJson());
factory GetEitAttachmentTicket.fromJson(Map<String, dynamic> json) => GetEitAttachmentTicket(
getEitAttachmentList: json["GetEITAttachmentList"] == null ? [] : List<GetEitAttachmentList>.from(json["GetEITAttachmentList"]!.map((x) => GetEitAttachmentList.fromJson(x))),
);
Map<String, dynamic> toJson() => {
"GetEITAttachmentList": getEitAttachmentList == null ? [] : List<dynamic>.from(getEitAttachmentList!.map((x) => x.toJson())),
};
}
class GetEitAttachmentList {
int? attachedDocumentId;
int? categoryId;
int? datatypeId;
int? documentId;
String? entityName;
String? fileContentType;
String? fileData;
int? fileId;
String? fileName;
String? pk1Value;
String? pk2Value;
String? pk3Value;
String? pk4Value;
String? pk5Value;
int? seqNum;
GetEitAttachmentList({
this.attachedDocumentId,
this.categoryId,
this.datatypeId,
this.documentId,
this.entityName,
this.fileContentType,
this.fileData,
this.fileId,
this.fileName,
this.pk1Value,
this.pk2Value,
this.pk3Value,
this.pk4Value,
this.pk5Value,
this.seqNum,
});
factory GetEitAttachmentList.fromRawJson(String str) => GetEitAttachmentList.fromJson(json.decode(str));
String toRawJson() => json.encode(toJson());
factory GetEitAttachmentList.fromJson(Map<String, dynamic> json) => GetEitAttachmentList(
attachedDocumentId: json["ATTACHED_DOCUMENT_ID"],
categoryId: json["CATEGORY_ID"],
datatypeId: json["DATATYPE_ID"],
documentId: json["DOCUMENT_ID"],
entityName: json["ENTITY_NAME"],
fileContentType: json["FILE_CONTENT_TYPE"],
fileData: json["FILE_DATA"],
fileId: json["FILE_ID"],
fileName: json["FILE_NAME"],
pk1Value: json["PK1_VALUE"],
pk2Value: json["PK2_VALUE"],
pk3Value: json["PK3_VALUE"],
pk4Value: json["PK4_VALUE"],
pk5Value: json["PK5_VALUE"],
seqNum: json["SEQ_NUM"],
);
Map<String, dynamic> toJson() => {
"ATTACHED_DOCUMENT_ID": attachedDocumentId,
"CATEGORY_ID": categoryId,
"DATATYPE_ID": datatypeId,
"DOCUMENT_ID": documentId,
"ENTITY_NAME": entityName,
"FILE_CONTENT_TYPE": fileContentType,
"FILE_DATA": fileData,
"FILE_ID": fileId,
"FILE_NAME": fileName,
"PK1_VALUE": pk1Value,
"PK2_VALUE": pk2Value,
"PK3_VALUE": pk3Value,
"PK4_VALUE": pk4Value,
"PK5_VALUE": pk5Value,
"SEQ_NUM": seqNum,
};
}

@ -22,8 +22,6 @@ class GetDayHoursTypeDetailsList {
dynamic? fROMROWNUM;
String? lATEINFLAG;
String? lATEINHRS;
String? lEAVEDESCRIPTION;
String? lEAVETYPECODE;
String? mISSINGSWIPEFLAG;
String? nONSCHEDULEDFLAG;
dynamic? nOOFROWS;
@ -68,8 +66,6 @@ class GetDayHoursTypeDetailsList {
this.fROMROWNUM,
this.lATEINFLAG,
this.lATEINHRS,
this.lEAVEDESCRIPTION,
this.lEAVETYPECODE,
this.mISSINGSWIPEFLAG,
this.nONSCHEDULEDFLAG,
this.nOOFROWS,
@ -114,8 +110,6 @@ class GetDayHoursTypeDetailsList {
fROMROWNUM = json['FROM_ROW_NUM'];
lATEINFLAG = json['LATE_IN_FLAG'];
lATEINHRS = json['LATE_IN_HRS'];
lEAVEDESCRIPTION = json['LEAVE_DESCRIPTION'];
lEAVETYPECODE = json['LEAVE_TYPE_CODE'];
mISSINGSWIPEFLAG = json['MISSING_SWIPE_FLAG'];
nONSCHEDULEDFLAG = json['NON_SCHEDULED_FLAG'];
nOOFROWS = json['NO_OF_ROWS'];
@ -162,8 +156,6 @@ class GetDayHoursTypeDetailsList {
data['FROM_ROW_NUM'] = this.fROMROWNUM;
data['LATE_IN_FLAG'] = this.lATEINFLAG;
data['LATE_IN_HRS'] = this.lATEINHRS;
data['LEAVE_DESCRIPTION'] = this.lEAVEDESCRIPTION;
data['LEAVE_TYPE_CODE'] = this.lEAVETYPECODE;
data['MISSING_SWIPE_FLAG'] = this.mISSINGSWIPEFLAG;
data['NON_SCHEDULED_FLAG'] = this.nONSCHEDULEDFLAG;
data['NO_OF_ROWS'] = this.nOOFROWS;

@ -1,142 +0,0 @@
import 'dart:convert';
class GetGreetingCardsModelResponse {
List<GetGreetingCardsModelResponseElement>? getGreetingCardsModelResponse;
GetGreetingCardsModelResponse({
this.getGreetingCardsModelResponse,
});
factory GetGreetingCardsModelResponse.fromRawJson(String str) => GetGreetingCardsModelResponse.fromJson(json.decode(str));
String toRawJson() => json.encode(toJson());
factory GetGreetingCardsModelResponse.fromJson(Map<String, dynamic> json) => GetGreetingCardsModelResponse(
getGreetingCardsModelResponse: json["Get_GreetingCardsModel_Response"] == null ? [] : List<GetGreetingCardsModelResponseElement>.from(json["Get_GreetingCardsModel_Response"]!.map((x) => GetGreetingCardsModelResponseElement.fromJson(x))),
);
Map<String, dynamic> toJson() => {
"Get_GreetingCardsModel_Response": getGreetingCardsModelResponse == null ? [] : List<dynamic>.from(getGreetingCardsModelResponse!.map((x) => x.toJson())),
};
}
class GetGreetingCardsModelResponseElement {
String? backgroundImageUrlAr;
String? backgroundImageUrlEn;
String? buttonBgColor;
String? buttonText;
String? buttonTextN;
int? cardType;
int? categoryId;
String? categoryNameAr;
String? categoryNameEn;
int? channel;
String? createdOn;
String? descriptionAr;
String? descriptionEn;
String? endDate;
bool? hasButton;
int? id;
bool? isActive;
int? moduleId;
String? moduleName;
String? moduleNameN;
String? startDate;
String? textColor;
String? titleAr;
String? titleEn;
String? urlAr;
String? urlEn;
GetGreetingCardsModelResponseElement({
this.backgroundImageUrlAr,
this.backgroundImageUrlEn,
this.buttonBgColor,
this.buttonText,
this.buttonTextN,
this.cardType,
this.categoryId,
this.categoryNameAr,
this.categoryNameEn,
this.channel,
this.createdOn,
this.descriptionAr,
this.descriptionEn,
this.endDate,
this.hasButton,
this.id,
this.isActive,
this.moduleId,
this.moduleName,
this.moduleNameN,
this.startDate,
this.textColor,
this.titleAr,
this.titleEn,
this.urlAr,
this.urlEn,
});
factory GetGreetingCardsModelResponseElement.fromRawJson(String str) => GetGreetingCardsModelResponseElement.fromJson(json.decode(str));
String toRawJson() => json.encode(toJson());
factory GetGreetingCardsModelResponseElement.fromJson(Map<String, dynamic> json) => GetGreetingCardsModelResponseElement(
backgroundImageUrlAr: json["BackgroundImageUrlAr"],
backgroundImageUrlEn: json["BackgroundImageUrlEn"],
buttonBgColor: json["ButtonBgColor"],
buttonText: json["ButtonText"],
buttonTextN: json["ButtonTextN"],
cardType: json["CardType"],
categoryId: json["CategoryID"],
categoryNameAr: json["CategoryNameAr"],
categoryNameEn: json["CategoryNameEn"],
channel: json["Channel"],
createdOn: json["CreatedOn"],
descriptionAr: json["DescriptionAr"],
descriptionEn: json["DescriptionEn"],
endDate: json["EndDate"],
hasButton: json["HasButton"],
id: json["ID"],
isActive: json["IsActive"],
moduleId: json["ModuleID"],
moduleName: json["ModuleName"],
moduleNameN: json["ModuleNameN"],
startDate: json["StartDate"],
textColor: json["TextColor"],
titleAr: json["TitleAr"],
titleEn: json["TitleEn"],
urlAr: json["UrlAr"],
urlEn: json["UrlEn"],
);
Map<String, dynamic> toJson() => {
"BackgroundImageUrlAr": backgroundImageUrlAr,
"BackgroundImageUrlEn": backgroundImageUrlEn,
"ButtonBgColor": buttonBgColor,
"ButtonText": buttonText,
"ButtonTextN": buttonTextN,
"CardType": cardType,
"CategoryID": categoryId,
"CategoryNameAr": categoryNameAr,
"CategoryNameEn": categoryNameEn,
"Channel": channel,
"CreatedOn": createdOn,
"DescriptionAr": descriptionAr,
"DescriptionEn": descriptionEn,
"EndDate": endDate,
"HasButton": hasButton,
"ID": id,
"IsActive": isActive,
"ModuleID": moduleId,
"ModuleName": moduleName,
"ModuleNameN": moduleNameN,
"StartDate": startDate,
"TextColor": textColor,
"TitleAr": titleAr,
"TitleEn": titleEn,
"UrlAr": urlAr,
"UrlEn": urlEn,
};
}

@ -136,21 +136,10 @@ class ActionButtonsColl {
late String btnTextEn;
late String btnTextAr;
late String actionValue;
dynamic iconOrImage;
String? actionType;
late dynamic iconOrImage;
late int orderNo;
String? url;
ActionButtonsColl({
required this.actionButtonId,
required this.btnTextEn,
required this.btnTextAr,
required this.actionValue,
this.iconOrImage,
this.actionType,
required this.orderNo,
this.url,
});
ActionButtonsColl({required this.actionButtonId, required this.btnTextEn, required this.btnTextAr, required this.actionValue, required this.iconOrImage, required this.orderNo});
ActionButtonsColl.fromJson(Map<String, dynamic> json) {
actionButtonId = json['actionButtonId'];
@ -158,9 +147,7 @@ class ActionButtonsColl {
btnTextAr = json['btnTextAr'];
actionValue = json['actionValue'];
iconOrImage = json['iconOrImage'];
actionType = json['actionType'];
orderNo = json['orderNo'];
url = json['url'];
}
Map<String, dynamic> toJson() {
@ -170,9 +157,7 @@ class ActionButtonsColl {
data['btnTextAr'] = this.btnTextAr;
data['actionValue'] = this.actionValue;
data['iconOrImage'] = this.iconOrImage;
data['actionType'] = this.actionType;
data['orderNo'] = this.orderNo;
data['url'] = this.url;
return data;
}
}

@ -19,11 +19,8 @@ import 'package:mohem_flutter_app/models/dashboard/list_menu.dart';
import 'package:mohem_flutter_app/models/dashboard/menu_entries.dart';
import 'package:mohem_flutter_app/models/dashboard/menus.dart';
import 'package:mohem_flutter_app/models/dashboard/mohemm_itg_pending_task_responseitem.dart';
import 'package:mohem_flutter_app/models/dashboard/courses_response_model.dart';
import 'package:mohem_flutter_app/models/eit/get_eit_transaction_model.dart';
import 'package:mohem_flutter_app/models/eit_attachment_ticket_model.dart';
import 'package:mohem_flutter_app/models/generic_response_model.dart';
import 'package:mohem_flutter_app/models/greetings/greeting_card_model.dart';
import 'package:mohem_flutter_app/models/itg/itg_response_model.dart';
import 'package:mohem_flutter_app/models/offers_and_discounts/get_offers_list.dart';
import 'package:mohem_flutter_app/models/sso_auth_model.dart';
@ -70,15 +67,6 @@ class DashboardProviderModel with ChangeNotifier, DiagnosticableTreeMixin {
bool isOffersLoading = true;
List<OffersListModel> getOffersList = [];
//Courses
bool isCoursesLoading = true;
CoursesResponseModel? coursesResponse;
List<CourseStatus> coursesList = [];
bool isGreetingCardsLoading = true;
bool isDisplayEidGreetings = false;
List<GetGreetingCardsModelResponseElement>? greetingCardsList;
//Attendance Tracking API's & Methods
Future<bool> fetchAttendanceTracking(context) async {
try {
@ -127,8 +115,6 @@ class DashboardProviderModel with ChangeNotifier, DiagnosticableTreeMixin {
getMenuEntriesList = null;
isOffersLoading = true;
getOffersList = [];
isGreetingCardsLoading = true;
isDisplayEidGreetings = false;
drawerMenuItemList = [
DrawerMenuItem("assets/images/drawer/my_profile.svg", LocaleKeys.myProfile.tr(), AppRoutes.profile),
@ -138,7 +124,6 @@ class DashboardProviderModel with ChangeNotifier, DiagnosticableTreeMixin {
DrawerMenuItem("assets/images/drawer/mowadhafi.svg", LocaleKeys.keen.tr(), AppRoutes.etqanOvr),
// DrawerMenuItem("assets/images/drawer/car_parking_icon.svg", LocaleKeys.parkingQr.tr(), AppRoutes.parkingQr),
DrawerMenuItem("assets/images/drawer/pending_trasactions.svg", LocaleKeys.pendingTransactions.tr(), AppRoutes.pendingTransactions),
// DrawerMenuItem("assets/images/drawer/courses.svg", "courses".tr(), AppRoutes.courses),
// DrawerMenuItem("assets/images/drawer/drawer_marathon.svg", LocaleKeys.brainMarathon.tr(), AppRoutes.marathonIntroScreen),
DrawerMenuItem("assets/images/drawer/change_password.svg", LocaleKeys.changePassword.tr(), AppRoutes.changePassword),
];
@ -324,33 +309,10 @@ class DashboardProviderModel with ChangeNotifier, DiagnosticableTreeMixin {
}
}
void fetchGreetingCards() async {
isGreetingCardsLoading = true;
notifyListeners();
try {
GetGreetingCardsModelResponse? response = await DashboardApiClient().getGreetingCards();
greetingCardsList = response?.getGreetingCardsModelResponse ?? [];
if (greetingCardsList != null && greetingCardsList!.isNotEmpty) {
isDisplayEidGreetings = greetingCardsList!.any((card) => card.isActive == true);
} else {
isDisplayEidGreetings = false;
}
isGreetingCardsLoading = false;
notifyListeners();
} catch (ex) {
logger.wtf(ex);
isDisplayEidGreetings = false;
greetingCardsList = [];
isGreetingCardsLoading = false;
notifyListeners();
}
}
Future<void> fetchTicketBooking() async {
try {
GenericResponseModel? genericResponseModel = await DashboardApiClient().getTicketBookingRedirection();
if (genericResponseModel?.portalDirectionData?.pRedirection!.toLowerCase() == "alma") {
// ticketBookingResponse = TicketBookingResult(true, "a9f4d1a0596d4aea8f830992ec4bdac1");
ticketBookingResponse = TicketBookingResult(true, genericResponseModel?.portalDirectionData?.clientID);
return;
}
@ -360,7 +322,7 @@ class DashboardProviderModel with ChangeNotifier, DiagnosticableTreeMixin {
isEventLoadingLoading = false;
notifyListeners();
Utils.handleException(ex, null, null);
ticketBookingResponse = TicketBookingResult(false, null);
ticketBookingResponse = TicketBookingResult(false, null); // Ensure a return value in case of an exception
}
}
@ -408,23 +370,6 @@ class DashboardProviderModel with ChangeNotifier, DiagnosticableTreeMixin {
}
}
Future<GetEitAttachmentTicket?> getTicketEitPDFDownload({String? peiExtraInfoId}) async {
try {
GetEitAttachmentTicket? res = await DashboardApiClient().getTicketEitPDFDownload(peiExtraInfoId: peiExtraInfoId!);
if (res?.getEitAttachmentList != null && res?.getEitAttachmentList!.length! != 0 && res!.getEitAttachmentList!.first.fileData != null) {
return res;
} else {
return null;
}
} catch (ex) {
logger.wtf(ex);
isEventLoadingLoading = false;
notifyListeners();
Utils.handleException(ex, null, null);
return null; // Ensure a return value in case of an exception
}
}
List<Menus> parseMenus(List<GetMenuEntriesList> getMenuEntriesList) {
List<Menus> menus = [];
for (int i = 0; i < getMenuEntriesList.length; i++) {
@ -458,30 +403,6 @@ class DashboardProviderModel with ChangeNotifier, DiagnosticableTreeMixin {
return res;
}
//Courses API's & Methods
Future<void> fetchCourses(BuildContext context) async {
try {
isCoursesLoading = true;
notifyListeners();
coursesResponse = await DashboardApiClient().fetchAllCoursesStatus();
if (coursesResponse != null && coursesResponse!.success == true) {
coursesList = coursesResponse!.coursesStatus ?? [];
} else {
coursesList = [];
}
isCoursesLoading = false;
notifyListeners();
} catch (ex) {
isCoursesLoading = false;
coursesList = [];
notifyListeners();
Utils.handleException(ex, context, null);
}
}
void notify() {
notifyListeners();
}

@ -315,26 +315,6 @@ class _MonthlyAttendanceScreenState extends State<MonthlyAttendanceScreen> {
bool isDayIsPresent = getDayHoursTypeDetailsList[index].aTTENDEDFLAG == 'Y';
bool isDayIsAbsent = getDayHoursTypeDetailsList[index].aTTENDEDFLAG == 'N' && getDayHoursTypeDetailsList[index].aBSENTFLAG == 'Y';
// Get leave type code and corresponding color
String? leaveTypeCode = getDayHoursTypeDetailsList[index].lEAVETYPECODE;
Color? leaveTypeColor;
bool useGradient = false;
// Determine color based on leave type code
if (leaveTypeCode != null && leaveTypeCode.isNotEmpty) {
leaveTypeColor = leaveTypeColors[leaveTypeCode];
}
// If no leave type color found, use default colors based on attendance status
if (leaveTypeColor == null) {
if (isDayIsPresent) {
leaveTypeColor = leaveTypeColors['Present'];
useGradient = true; // Use gradient for present days without leave type
} else if (isDayIsAbsent) {
leaveTypeColor = leaveTypeColors['Absent'];
}
}
if (isDayIsOff) {
return Container(
margin: const EdgeInsets.all(4),
@ -351,13 +331,12 @@ class _MonthlyAttendanceScreenState extends State<MonthlyAttendanceScreen> {
return Container(
margin: const EdgeInsets.all(4),
decoration: BoxDecoration(
gradient: useGradient && leaveTypeColor != null ? LinearGradient(
gradient: const LinearGradient(
transform: GradientRotation(.46),
begin: Alignment.topRight,
end: Alignment.bottomLeft,
colors: [MyColors.gradiantEndColor, MyColors.gradiantStartColor],
) : null,
color: !useGradient && leaveTypeColor != null ? leaveTypeColor : null,
),
shape: BoxShape.circle,
boxShadow: [
BoxShadow(
@ -379,7 +358,7 @@ class _MonthlyAttendanceScreenState extends State<MonthlyAttendanceScreen> {
return Container(
margin: const EdgeInsets.all(4),
decoration: BoxDecoration(
color: leaveTypeColor ?? MyColors.backgroundBlackColor,
color: MyColors.backgroundBlackColor,
shape: BoxShape.circle,
boxShadow: [
BoxShadow(
@ -772,24 +751,3 @@ class Meeting {
Color background;
bool isAllDay;
}
const Map<String, Color> leaveTypeColors = {
'Present': Color(0xFF00ad62),
'Absent': Color(0xFFcb3232),
'HOLIDAY': Color(0xFFF26B0F),
'BUS_TRIP': Color(0xFF001A6E),
'WFH': Color(0xFF5DB996),
'ANNUAL': Color(0xFFf39c12),
'EMERGENCY': Color(0xFFFF2929),
'EXAM': Color(0xFFCB6040),
'HAJJ': Color(0xFF798645),
'HALF': Color(0xFFE8B86D),
'LWOP': Color(0xFFCD5C08),
'LWOP_MATUNPAID': Color(0xFFE73879),
'LWOP_UNAUUNPAID': Color(0xFFA02334),
'MATPAID': Color(0xFFE73879),
'MRGE': Color(0xFF0D7C66),
'PAT': Color(0xFFC96868),
'PROF': Color(0xFF6256CA),
'SICK': Color(0xFFA5B68D),
};

@ -110,20 +110,15 @@ class _EtqanOvrCreateRequestState extends State<EtqanOvrCreateRequest> {
if (ticketInfo != null) {
String ticketNumber = ticketInfo['ticketNumber'] ?? '';
String ticketId = ticketInfo['id'] ?? '';
// String successMessage = '${LocaleKeys.requestCreatedSuccessfully.tr()}\n\n${LocaleKeys.ticketNumber.tr()}: $ticketNumber\n${LocaleKeys.ticketId.tr()}: $ticketId';
String successMessage = '${LocaleKeys.requestCreatedSuccessfully.tr()}\n\n${LocaleKeys.ticketNumber.tr()}: $ticketNumber';
String successMessage = '${LocaleKeys.requestCreatedSuccessfully.tr()}\n\n${LocaleKeys.ticketNumber.tr()}: $ticketNumber\n${LocaleKeys.ticketId.tr()}: $ticketId';
Utils.showErrorDialog(
context: context,
message: successMessage,
onOkTapped: () {
Navigator.pop(context);
Navigator.pop(context);
// Navigator.popAndPushNamed(context, AppRoutes.etqanOvr);
Navigator.popAndPushNamed(context, AppRoutes.etqanOvr);
},
onCloseTap: () {
Navigator.pop(context);
Navigator.pop(context);
// Navigator.popAndPushNamed(context, AppRoutes.etqanOvr);
Navigator.popAndPushNamed(context, AppRoutes.etqanOvr);
},
);
}

@ -1,6 +1,7 @@
import 'dart:async';
import 'dart:io';
import 'dart:ui' as ui;
import 'package:easy_localization/easy_localization.dart';
import 'package:flutter/material.dart';
import 'package:flutter_countdown_timer/flutter_countdown_timer.dart';
@ -33,7 +34,6 @@ import 'package:mohem_flutter_app/widgets/shimmer/offers_shimmer_widget.dart';
import 'package:provider/provider.dart';
import 'package:pull_to_refresh/pull_to_refresh.dart';
import 'package:signalr_netcore/signalr_client.dart';
import 'package:url_launcher/url_launcher.dart';
late HubConnection chatHubConnection;
@ -156,7 +156,6 @@ class _DashboardScreenState extends State<DashboardScreen> with WidgetsBindingOb
data.fetchMenuEntries();
data.fetchEventActivity();
data.getCategoryOffersListAPI(context);
data.fetchGreetingCards();
marathonProvider.getMarathonDetailsFromApi();
marathonProvider.getMarathonTutorial();
if (isFromInit) {
@ -165,7 +164,7 @@ class _DashboardScreenState extends State<DashboardScreen> with WidgetsBindingOb
if (!cProvider.disbaleChatForThisUser && !isFromInit) checkHubCon();
_refreshController.refreshCompleted();
await data.fetchTicketBooking();
// await data.fetchTicketBooking();
// if (data.ticketBookingResponse != null && !data.ticketBookingResponse!.success) {
// data.fetchTicketBalance();
@ -317,103 +316,103 @@ class _DashboardScreenState extends State<DashboardScreen> with WidgetsBindingOb
child: Consumer<DashboardProviderModel>(
builder: (BuildContext context, DashboardProviderModel model, Widget? child) {
return (model.isAttendanceTrackingLoading
? GetAttendanceTrackingShimmer()
: Container(
decoration: BoxDecoration(
borderRadius: BorderRadius.circular(15),
gradient: const LinearGradient(
transform: GradientRotation(.46),
begin: Alignment.topRight,
end: Alignment.bottomLeft,
colors: [MyColors.gradiantEndColor, MyColors.gradiantStartColor],
),
),
child: Stack(
alignment: Alignment.center,
children: [
if (model.isTimeRemainingInSeconds == 0) SvgPicture.asset("assets/images/thumb.svg"),
Column(
crossAxisAlignment: CrossAxisAlignment.start,
children: [
Expanded(
child: Column(
mainAxisSize: MainAxisSize.min,
crossAxisAlignment: CrossAxisAlignment.start,
children: [
LocaleKeys.markAttendance.tr().toText14(color: Colors.white, isBold: true),
if (model.isTimeRemainingInSeconds == 0) DateTime.now().toString().split(" ")[0].toText12(color: Colors.white),
if (model.isTimeRemainingInSeconds != 0)
Column(
mainAxisSize: MainAxisSize.min,
crossAxisAlignment: CrossAxisAlignment.start,
children: [
9.height,
Directionality(
textDirection: ui.TextDirection.ltr,
child: CountdownTimer(
endTime: model.endTime,
onEnd: null,
endWidget: "00:00:00".toText14(color: Colors.white, isBold: true),
textStyle: const TextStyle(color: Colors.white, fontSize: 14, letterSpacing: -0.48, fontWeight: FontWeight.bold),
),
),
LocaleKeys.timeLeftToday.tr().toText12(color: Colors.white),
9.height,
ClipRRect(
borderRadius: const BorderRadius.all(Radius.circular(20)),
child: LinearProgressIndicator(
value: model.progress,
minHeight: 8,
valueColor: const AlwaysStoppedAnimation<Color>(Colors.white),
backgroundColor: const Color(0xff196D73),
),
),
],
),
],
).paddingOnly(top: 12, right: 15, left: 12),
),
Row(
? GetAttendanceTrackingShimmer()
: Container(
decoration: BoxDecoration(
borderRadius: BorderRadius.circular(15),
gradient: const LinearGradient(
transform: GradientRotation(.46),
begin: Alignment.topRight,
end: Alignment.bottomLeft,
colors: [MyColors.gradiantEndColor, MyColors.gradiantStartColor],
),
),
child: Stack(
alignment: Alignment.center,
children: [
if (model.isTimeRemainingInSeconds == 0) SvgPicture.asset("assets/images/thumb.svg"),
Column(
crossAxisAlignment: CrossAxisAlignment.start,
children: [
Expanded(
child: Column(
mainAxisSize: MainAxisSize.min,
crossAxisAlignment: CrossAxisAlignment.start,
children: [
LocaleKeys.markAttendance.tr().toText14(color: Colors.white, isBold: true),
if (model.isTimeRemainingInSeconds == 0) DateTime.now().toString().split(" ")[0].toText12(color: Colors.white),
if (model.isTimeRemainingInSeconds != 0)
Column(
mainAxisSize: MainAxisSize.min,
crossAxisAlignment: CrossAxisAlignment.start,
children: [
Expanded(
child: Column(
mainAxisSize: MainAxisSize.min,
crossAxisAlignment: CrossAxisAlignment.start,
children: [
LocaleKeys.checkIn.tr().toText12(color: Colors.white),
(model.attendanceTracking!.pSwipeIn == null ? "--:--" : model.attendanceTracking!.pSwipeIn).toString().toText14(
color: Colors.white,
isBold: true,
),
4.height,
],
).paddingOnly(left: 12, right: 12),
9.height,
Directionality(
textDirection: ui.TextDirection.ltr,
child: CountdownTimer(
endTime: model.endTime,
onEnd: null,
endWidget: "00:00:00".toText14(color: Colors.white, isBold: true),
textStyle: const TextStyle(color: Colors.white, fontSize: 14, letterSpacing: -0.48, fontWeight: FontWeight.bold),
),
),
Container(
margin: EdgeInsets.only(top: AppState().isArabic(context) ? 6 : 0),
width: 45,
height: 45,
padding: const EdgeInsets.only(left: 10, right: 10),
decoration: BoxDecoration(
color: const Color(0xff259EA4),
borderRadius: BorderRadius.only(
bottomRight: AppState().isArabic(context) ? const Radius.circular(0) : const Radius.circular(15),
bottomLeft: AppState().isArabic(context) ? const Radius.circular(15) : const Radius.circular(0),
),
LocaleKeys.timeLeftToday.tr().toText12(color: Colors.white),
9.height,
ClipRRect(
borderRadius: const BorderRadius.all(Radius.circular(20)),
child: LinearProgressIndicator(
value: model.progress,
minHeight: 8,
valueColor: const AlwaysStoppedAnimation<Color>(Colors.white),
backgroundColor: const Color(0xff196D73),
),
child: SvgPicture.asset(model.isTimeRemainingInSeconds == 0 ? "assets/images/biometrics.svg" : "assets/images/biometrics.svg"),
).onPress(() {
showMyBottomSheet(context, callBackFunc: () {}, child: MarkAttendanceWidget(model, isFromDashboard: true));
}),
),
],
),
],
],
).paddingOnly(top: 12, right: 15, left: 12),
),
Row(
children: [
Expanded(
child: Column(
mainAxisSize: MainAxisSize.min,
crossAxisAlignment: CrossAxisAlignment.start,
children: [
LocaleKeys.checkIn.tr().toText12(color: Colors.white),
(model.attendanceTracking!.pSwipeIn == null ? "--:--" : model.attendanceTracking!.pSwipeIn).toString().toText14(
color: Colors.white,
isBold: true,
),
4.height,
],
).paddingOnly(left: 12, right: 12),
),
Container(
margin: EdgeInsets.only(top: AppState().isArabic(context) ? 6 : 0),
width: 45,
height: 45,
padding: const EdgeInsets.only(left: 10, right: 10),
decoration: BoxDecoration(
color: const Color(0xff259EA4),
borderRadius: BorderRadius.only(
bottomRight: AppState().isArabic(context) ? const Radius.circular(0) : const Radius.circular(15),
bottomLeft: AppState().isArabic(context) ? const Radius.circular(15) : const Radius.circular(0),
),
),
child: SvgPicture.asset(model.isTimeRemainingInSeconds == 0 ? "assets/images/biometrics.svg" : "assets/images/biometrics.svg"),
).onPress(() {
showMyBottomSheet(context, callBackFunc: () {}, child: MarkAttendanceWidget(model, isFromDashboard: true));
}),
],
),
).onPress(() {
Navigator.pushNamed(context, AppRoutes.todayAttendance);
}))
],
),
],
),
).onPress(() {
Navigator.pushNamed(context, AppRoutes.todayAttendance);
}))
.animatedSwither();
},
),
@ -425,29 +424,8 @@ class _DashboardScreenState extends State<DashboardScreen> with WidgetsBindingOb
),
],
).paddingOnly(left: 21, right: 21, top: 7, bottom: 21),
Consumer<DashboardProviderModel>(
builder: (BuildContext context, DashboardProviderModel model, Widget? child) {
if (model.isGreetingCardsLoading) {
return const GreetingCardShimmer();
} else if (model.isDisplayEidGreetings && model.greetingCardsList != null && model.greetingCardsList!.isNotEmpty) {
return SizedBox(
width: double.infinity,
child: SvgPicture.network(
AppState().isArabic(context)
? (model.greetingCardsList!.first.backgroundImageUrlAr ?? "https://www.hmg.com/Lists/CS_Greeting_Cards/Attachments/5/CS_Ramadan_26.jpg")
: (model.greetingCardsList!.first.backgroundImageUrlEn ?? "https://www.hmg.com/Lists/CS_Greeting_Cards/Attachments/5/CS_Ramadan_26.jpg"),
fit: BoxFit.cover,
placeholderBuilder: (context) => ClipRRect(borderRadius: BorderRadius.circular(18), child: Container(height: 80, color: Colors.white).toShimmer()),
).onPress(() {
launchUrl(Uri.parse(AppState().isArabic(context) ? model.greetingCardsList!.first.urlAr! : model.greetingCardsList!.first.urlEn!));
}),
);
} else {
return const SizedBox();
}
},
).paddingOnly(bottom: 24, left: 24, right: 24),
// eventActivityWidget(context),
eventActivityWidget(context),
if (isDisplayMazaya) ...[
Column(
mainAxisSize: MainAxisSize.min,
@ -483,70 +461,70 @@ class _DashboardScreenState extends State<DashboardScreen> with WidgetsBindingOb
flex: 2,
child: RichText(
text:
AppState().isArabic(context)
? TextSpan(
children: [
TextSpan(
text: 'اطلع على مميزات',
style: TextStyle(
fontSize: 16,
letterSpacing: -0.2,
fontFamily: AppState().isArabic(context) ? 'Cairo' : 'Poppins',
fontWeight: FontWeight.w700,
height: 24 / 16,
color: const Color(0xFF5D5E5E),
),
),
TextSpan(
text: ' مزايا',
style: TextStyle(
fontSize: 16,
fontFamily: AppState().isArabic(context) ? 'Cairo' : 'Poppins',
fontWeight: FontWeight.w700,
letterSpacing: -0.2,
height: 24 / 16,
color: MyColors.mazayaRedColor, // Use your MAZAYA red color here if defined, e.g. MyColors.mazayaRed
),
),
],
)
: TextSpan(
children: [
TextSpan(
text: LocaleKeys.explore.tr() + ' ',
style: const TextStyle(
fontSize: 16,
letterSpacing: -0.2,
fontFamily: 'Poppins',
fontWeight: FontWeight.w700,
height: 24 / 16,
color: Color(0xFF5D5E5E),
),
),
TextSpan(
text: LocaleKeys.mazaya.tr(),
style: const TextStyle(
fontSize: 16,
fontWeight: FontWeight.w700,
fontFamily: 'Poppins',
letterSpacing: -0.2,
height: 24 / 16,
color: MyColors.mazayaRedColor, // Use your MAZAYA red color here if defined, e.g. MyColors.mazayaRed
),
),
TextSpan(
text: ' ' + LocaleKeys.benefits.tr(),
style: const TextStyle(
fontSize: 16,
letterSpacing: -0.2,
fontFamily: 'Poppins',
fontWeight: FontWeight.w700,
height: 24 / 16,
color: Color(0xFF5D5E5E),
),
),
],
),
AppState().isArabic(context)
? TextSpan(
children: [
TextSpan(
text: 'اطلع على مميزات',
style: TextStyle(
fontSize: 16,
letterSpacing: -0.2,
fontFamily: AppState().isArabic(context) ? 'Cairo' : 'Poppins',
fontWeight: FontWeight.w700,
height: 24 / 16,
color: Color(0xFF5D5E5E),
),
),
TextSpan(
text: ' مزايا',
style: TextStyle(
fontSize: 16,
fontFamily: AppState().isArabic(context) ? 'Cairo' : 'Poppins',
fontWeight: FontWeight.w700,
letterSpacing: -0.2,
height: 24 / 16,
color: MyColors.mazayaRedColor, // Use your MAZAYA red color here if defined, e.g. MyColors.mazayaRed
),
),
],
)
: TextSpan(
children: [
TextSpan(
text: LocaleKeys.explore.tr() + ' ',
style: const TextStyle(
fontSize: 16,
letterSpacing: -0.2,
fontFamily: 'Poppins',
fontWeight: FontWeight.w700,
height: 24 / 16,
color: Color(0xFF5D5E5E),
),
),
TextSpan(
text: LocaleKeys.mazaya.tr(),
style: const TextStyle(
fontSize: 16,
fontWeight: FontWeight.w700,
fontFamily: 'Poppins',
letterSpacing: -0.2,
height: 24 / 16,
color: MyColors.mazayaRedColor, // Use your MAZAYA red color here if defined, e.g. MyColors.mazayaRed
),
),
TextSpan(
text: ' ' + LocaleKeys.benefits.tr(),
style: const TextStyle(
fontSize: 16,
letterSpacing: -0.2,
fontFamily: 'Poppins',
fontWeight: FontWeight.w700,
height: 24 / 16,
color: Color(0xFF5D5E5E),
),
),
],
),
),
),
const Expanded(flex: 1, child: SizedBox()),
@ -599,10 +577,12 @@ class _DashboardScreenState extends State<DashboardScreen> with WidgetsBindingOb
LocaleKeys.discounts.tr().toText24(isBold: true),
6.width,
Container(
padding: const EdgeInsets.only(left: 8, right: 8),
decoration: BoxDecoration(color: MyColors.yellowColor, borderRadius: BorderRadius.circular(10)),
child: LocaleKeys.newString.tr().toText10(isBold: true),
),
padding: const EdgeInsets.only(left: 8, right: 8),
decoration: BoxDecoration(
color: MyColors.yellowColor,
borderRadius: BorderRadius.circular(10),
),
child: LocaleKeys.newString.tr().toText10(isBold: true)),
],
),
],
@ -610,7 +590,7 @@ class _DashboardScreenState extends State<DashboardScreen> with WidgetsBindingOb
),
LocaleKeys.viewAllOffers.tr().toText12(isUnderLine: true).onPress(() {
Navigator.pushNamed(context, AppRoutes.offersAndDiscounts);
}),
})
],
).paddingOnly(left: 21, right: 21),
Consumer<DashboardProviderModel>(
@ -618,54 +598,59 @@ class _DashboardScreenState extends State<DashboardScreen> with WidgetsBindingOb
return SizedBox(
height: 103 + 33,
child: ListView.separated(
shrinkWrap: true,
physics: const BouncingScrollPhysics(),
padding: const EdgeInsets.only(left: 21, right: 21, top: 13),
scrollDirection: Axis.horizontal,
itemBuilder: (BuildContext cxt, int index) {
return model.isOffersLoading
? const OffersShimmerWidget()
: InkWell(
onTap: () {
navigateToDetails(data.getOffersList[index]);
},
child: SizedBox(
width: 73,
child: Column(
crossAxisAlignment: CrossAxisAlignment.center,
children: [
Container(
width: 73,
height: 73,
decoration: BoxDecoration(
color: Colors.white,
borderRadius: const BorderRadius.all(Radius.circular(100)),
border: Border.all(color: MyColors.lightGreyE3Color, width: 1),
shrinkWrap: true,
physics: const BouncingScrollPhysics(),
padding: const EdgeInsets.only(left: 21, right: 21, top: 13),
scrollDirection: Axis.horizontal,
itemBuilder: (BuildContext cxt, int index) {
return model.isOffersLoading
? const OffersShimmerWidget()
: InkWell(
onTap: () {
navigateToDetails(data.getOffersList[index]);
},
child: SizedBox(
width: 73,
child: Column(
crossAxisAlignment: CrossAxisAlignment.center,
children: [
Container(
width: 73,
height: 73,
decoration: BoxDecoration(
color: Colors.white,
borderRadius: const BorderRadius.all(
Radius.circular(100),
),
child: ClipRRect(
borderRadius: const BorderRadius.all(Radius.circular(50)),
child: Hero(
tag: "ItemImage" + data.getOffersList[index].offersDiscountId.toString()!,
transitionOnUserGestures: true,
child: Image.network(data.getOffersList[index].logo ?? "", fit: BoxFit.contain),
border: Border.all(color: MyColors.lightGreyE3Color, width: 1),
),
child: ClipRRect(
borderRadius: const BorderRadius.all(
Radius.circular(50),
),
child: Hero(
tag: "ItemImage" + data.getOffersList[index].offersDiscountId.toString()!,
transitionOnUserGestures: true,
child: Image.network(
data.getOffersList[index].logo ?? "",
fit: BoxFit.contain,
),
),
),
4.height,
Expanded(
child:
AppState().isArabic(context)
? data.getOffersList[index].titleAr!.toText12(isCenter: true, maxLine: 1)
: data.getOffersList[index].titleEn!.toText12(isCenter: true, maxLine: 1),
),
],
),
),
4.height,
Expanded(
child: AppState().isArabic(context)
? data.getOffersList[index].titleAr!.toText12(isCenter: true, maxLine: 1)
: data.getOffersList[index].titleEn!.toText12(isCenter: true, maxLine: 1),
),
],
),
);
},
separatorBuilder: (BuildContext cxt, int index) => 8.width,
itemCount: 9,
),
),
);
},
separatorBuilder: (BuildContext cxt, int index) => 8.width,
itemCount: 9),
);
},
),
@ -788,28 +773,28 @@ class _DashboardScreenState extends State<DashboardScreen> with WidgetsBindingOb
SvgPicture.asset(
"assets/icons/chat/chat.svg",
color:
!checkIfPrivilegedForChat()
? MyColors.lightGreyE3Color
: currentIndex == 4
? MyColors.grey3AColor
: cProvider.disbaleChatForThisUser
? MyColors.lightGreyE3Color
: MyColors.grey98Color,
!checkIfPrivilegedForChat()
? MyColors.lightGreyE3Color
: currentIndex == 4
? MyColors.grey3AColor
: cProvider.disbaleChatForThisUser
? MyColors.lightGreyE3Color
: MyColors.grey98Color,
).paddingAll(4),
Consumer<ChatProviderModel>(
builder: (BuildContext cxt, ChatProviderModel data, Widget? child) {
return !checkIfPrivilegedForChat()
? const SizedBox()
: Positioned(
right: 0,
top: 0,
child: Container(
padding: const EdgeInsets.only(left: 4, right: 4),
alignment: Alignment.center,
decoration: BoxDecoration(color: cProvider.disbaleChatForThisUser ? MyColors.pinkDarkColor : MyColors.redColor, borderRadius: BorderRadius.circular(17)),
child: data.chatUConvCounter.toString().toText10(color: Colors.white),
),
);
right: 0,
top: 0,
child: Container(
padding: const EdgeInsets.only(left: 4, right: 4),
alignment: Alignment.center,
decoration: BoxDecoration(color: cProvider.disbaleChatForThisUser ? MyColors.pinkDarkColor : MyColors.redColor, borderRadius: BorderRadius.circular(17)),
child: data.chatUConvCounter.toString().toText10(color: Colors.white),
),
);
},
),
],
@ -880,4 +865,4 @@ class _DashboardScreenState extends State<DashboardScreen> with WidgetsBindingOb
}
return false;
}
}
}

@ -6,19 +6,14 @@ import 'package:mohem_flutter_app/app_state/app_state.dart';
import 'package:mohem_flutter_app/classes/colors.dart';
import 'package:mohem_flutter_app/classes/lottie_consts.dart';
import 'package:mohem_flutter_app/classes/utils.dart';
import 'package:mohem_flutter_app/config/routes.dart';
import 'package:mohem_flutter_app/extensions/int_extensions.dart';
import 'package:mohem_flutter_app/extensions/string_extensions.dart';
import 'package:mohem_flutter_app/extensions/widget_extensions.dart';
import 'package:mohem_flutter_app/main.dart';
import 'package:mohem_flutter_app/models/dashboard/menu_entries.dart';
import 'package:mohem_flutter_app/models/itg/advertisement.dart' as ads;
import 'package:mohem_flutter_app/provider/dashboard_provider_model.dart';
import 'package:mohem_flutter_app/ui/my_attendance/services_menu_list_screen.dart';
import 'package:mohem_flutter_app/widgets/app_bar_widget.dart';
import 'package:mohem_flutter_app/widgets/button/default_button.dart';
import 'package:mohem_flutter_app/widgets/my_video_progress_indicator.dart';
import 'package:provider/provider.dart';
import 'package:url_launcher/url_launcher.dart';
import 'package:video_player/video_player.dart';
@ -31,7 +26,7 @@ class ITGAdsScreen extends StatefulWidget {
class _ITGAdsScreenState extends State<ITGAdsScreen> {
late Future<VideoPlayerController> _futureController;
VideoPlayerController? _controller;
late VideoPlayerController _controller;
bool skip = false;
bool isVideo = false;
bool isImage = false;
@ -130,7 +125,7 @@ class _ITGAdsScreenState extends State<ITGAdsScreen> {
@override
void dispose() {
_controller?.dispose();
if (_controller != null) _controller.dispose();
super.dispose();
}
@ -171,11 +166,11 @@ class _ITGAdsScreenState extends State<ITGAdsScreen> {
child: isAudio
? Lottie.asset(MyLottieConsts.audioPlaybackLottie)
: AspectRatio(
aspectRatio: _controller!.value.aspectRatio,
aspectRatio: _controller.value.aspectRatio,
child: Stack(
alignment: Alignment.bottomCenter,
children: [
VideoPlayer(_controller!),
VideoPlayer(_controller),
if (advertisementData?.isOptional ?? false)
Positioned(
top: 4,
@ -235,7 +230,7 @@ class _ITGAdsScreenState extends State<ITGAdsScreen> {
alignment: Alignment.center,
children: [
MyVideoProgressIndicator(
_controller!,
_controller,
allowScrubbing: false,
//padding: EdgeInsets.only(left: 60, right: 60),
),
@ -391,39 +386,16 @@ class _ITGAdsScreenState extends State<ITGAdsScreen> {
if (advertisementData!.actionButtonsColl![index].actionValue.toLowerCase() == "skip") {
Navigator.pop(context);
} else {
if (advertisementData!.actionButtonsColl![index].actionType!.toLowerCase() == 'redirect' && advertisementData!.actionButtonsColl![index].actionValue!.toLowerCase() ==
'external') {
Uri uri = Uri.parse(advertisementData!.actionButtonsColl![index].url!);
await launchUrl(uri, mode: LaunchMode.externalApplication).catchError((err) {
// print(err);
Utils.showToast('Could not launch');
});
Navigator.pop(context);
} else if (advertisementData!.actionButtonsColl![index].actionType!.toLowerCase() == 'redirect' && advertisementData!.actionButtonsColl![index].actionValue!.toLowerCase() ==
'internal') {
await Navigator.pushNamed(context, advertisementData!.actionButtonsColl![index].url!);
} else if(advertisementData!.actionButtonsColl![index].actionType!.toLowerCase() == 'eit' && advertisementData!.actionButtonsColl![index].actionValue!.toLowerCase() ==
'internal'){
var pro = Provider.of<DashboardProviderModel>(context, listen: false);
List<GetMenuEntriesList> _menuList =
pro.getMenuEntriesList?.where((element) => element.parentMenuName == advertisementData!.actionButtonsColl![index].url && (element.menuEntryType == "FUNCTION" || element.menuEntryType == "MENU")).toList() ?? [];
Navigator.pushNamed(context, AppRoutes.servicesMenuListScreen, arguments: ServicesMenuListScreenParams(advertisementData!.advertisementTitle!, _menuList));
}
else{
Uri uri = Uri.parse(advertisementData!.actionButtonsColl![index].iconOrImage);
// if (await canLaunchUrl(uri)) {
await launchUrl(uri, mode: LaunchMode.externalApplication).catchError((err) {
// print(err);
Utils.showToast('Could not launch');
});
Navigator.pop(context);
// } else {
// Utils.showToast('Could not launch');
// }
}
Uri uri = Uri.parse(advertisementData!.actionButtonsColl![index].iconOrImage);
// if (await canLaunchUrl(uri)) {
await launchUrl(uri, mode: LaunchMode.externalApplication).catchError((err) {
// print(err);
Utils.showToast('Could not launch');
});
Navigator.pop(context);
// } else {
// Utils.showToast('Could not launch');
// }
}
},
),

@ -49,18 +49,32 @@ class _AppDrawerState extends State<AppDrawer> {
children: <Widget>[
Row(
mainAxisAlignment: MainAxisAlignment.spaceBetween,
children: [Image.asset("assets/images/logos/main_mohemm_logo.png", width: 134, height: 24), const Icon(Icons.clear).onPress(() => Navigator.pop(context))],
children: [
Image.asset("assets/images/logos/main_mohemm_logo.png", width: 134, height: 24),
const Icon(Icons.clear).onPress(() => Navigator.pop(context)),
],
).paddingOnly(left: 4, right: 14),
Row(
children: [
AppState().memberInformationList!.eMPLOYEEIMAGE == null
? SvgPicture.asset("assets/images/user.svg", height: 52, width: 52)
: CircleAvatar(radius: 52 / 2, backgroundImage: MemoryImage(Utils.dataFromBase64String(AppState().memberInformationList!.eMPLOYEEIMAGE!)), backgroundColor: Colors.black),
? SvgPicture.asset(
"assets/images/user.svg",
height: 52,
width: 52,
)
: CircleAvatar(
radius: 52 / 2,
backgroundImage: MemoryImage(Utils.dataFromBase64String(AppState().memberInformationList!.eMPLOYEEIMAGE!)),
backgroundColor: Colors.black,
),
12.width,
Column(
crossAxisAlignment: CrossAxisAlignment.start,
children: [AppState().memberInformationList!.eMPLOYEENAME!.toText18(isBold: true), AppState().memberInformationList!.getPositionName().toText14(weight: FontWeight.w500)],
).expanded,
children: [
AppState().memberInformationList!.eMPLOYEENAME!.toText18(isBold: true),
AppState().memberInformationList!.getPositionName().toText14(weight: FontWeight.w500),
],
).expanded
],
).paddingOnly(left: 14, right: 14, top: 21, bottom: 21),
// Row(
@ -85,77 +99,67 @@ class _AppDrawerState extends State<AppDrawer> {
// ),
// ],
// ).paddingOnly(left: 14, right: 14, bottom: 14),
const Divider(height: 1, thickness: 1, color: MyColors.lightGreyEFColor),
const Divider(
height: 1,
thickness: 1,
color: MyColors.lightGreyEFColor,
),
ListView(
padding: const EdgeInsets.only(top: 21, bottom: 21),
children: [
ListView.builder(
padding: EdgeInsets.zero,
shrinkWrap: true,
physics: const NeverScrollableScrollPhysics(),
itemCount: drawerMenuItemList.length,
itemBuilder: (cxt, index) {
return menuItem(
drawerMenuItemList[index].icon,
drawerMenuItemList[index].title,
drawerMenuItemList[index].routeName,
onPress: () {
padding: EdgeInsets.zero,
shrinkWrap: true,
physics: const NeverScrollableScrollPhysics(),
itemCount: drawerMenuItemList.length,
itemBuilder: (cxt, index) {
return menuItem(drawerMenuItemList[index].icon, drawerMenuItemList[index].title, drawerMenuItemList[index].routeName, onPress: () {
Navigator.pushNamed(context, drawerMenuItemList[index].routeName);
},
);
},
),
});
}),
menuItem("assets/images/drawer/employee_id.svg", LocaleKeys.employeeDigitalID.tr(), "", closeDrawer: false, onPress: () => showMDialog(context, child: EmployeeDigitialIdDialog())),
if (AppState().businessCardPrivilege)
menuItem(
"assets/images/drawer/view_business_card.svg",
LocaleKeys.viewBusinessCard.tr(),
"",
closeDrawer: false,
onPress: () => showMDialog(context, child: BusinessCardDialog(), isBusniessCard: true),
),
menuItem(
"assets/images/drawer/logout.svg",
LocaleKeys.logout.tr(),
"",
color: MyColors.redA3Color,
closeDrawer: false,
onPress: () async {
await Utils.performLogout(context, chatData);
},
),
menuItem("assets/images/drawer/view_business_card.svg", LocaleKeys.viewBusinessCard.tr(), "", closeDrawer: false, onPress: () => showMDialog(context, child: BusinessCardDialog(), isBusniessCard: true)),
menuItem("assets/images/drawer/logout.svg", LocaleKeys.logout.tr(), "", color: MyColors.redA3Color, closeDrawer: false, onPress: (){Utils.performLogout(context, chatData);}),
// menuItem("assets/images/drawer/logout.svg", LocaleKeys.logout.tr(), "", color: MyColors.redA3Color, closeDrawer: false, onPress: () {Navigator.pushNamed(context, AppRoutes.survey,);
],
).expanded,
const Divider(height: 1, thickness: 1, color: MyColors.lightGreyEFColor),
const Divider(
height: 1,
thickness: 1,
color: MyColors.lightGreyEFColor,
),
Row(
children: [
RichText(
text: TextSpan(
text: LocaleKeys.poweredBy.tr() + " ",
style: const TextStyle(color: MyColors.grey98Color, fontSize: 14, letterSpacing: -0.56, fontWeight: FontWeight.w600),
children: [TextSpan(text: LocaleKeys.cloudSolutions.tr(), style: const TextStyle(color: MyColors.grey3AColor, fontSize: 14, letterSpacing: -0.56, fontWeight: FontWeight.w600))],
),
text: TextSpan(text: LocaleKeys.poweredBy.tr() + " ", style: const TextStyle(color: MyColors.grey98Color, fontSize: 14, letterSpacing: -0.56, fontWeight: FontWeight.w600), children: [
TextSpan(
text: LocaleKeys.cloudSolutions.tr(),
style: const TextStyle(color: MyColors.grey3AColor, fontSize: 14, letterSpacing: -0.56, fontWeight: FontWeight.w600),
),
]),
).expanded,
Image.asset("assets/images/logos/bn_cloud_soloution.jpg", width: 40, height: 40),
Image.asset("assets/images/logos/bn_cloud_soloution.jpg", width: 40, height: 40)
],
).paddingOnly(left: 21, right: 21, top: 21),
).paddingOnly(left: 21, right: 21, top: 21)
],
).paddingOnly(top: 21, bottom: 21),
);
}
Widget menuItem(String icon, String title, String routeName, {Color? color, bool closeDrawer = true, VoidCallback? onPress}) {
return Row(children: [SvgPicture.asset(icon, height: 20, width: 20), 9.width, title.toText14(color: color, textAlign: AppState().isArabic(context) ? TextAlign.right : null).expanded])
.paddingOnly(left: 21, top: 10, bottom: 10, right: 21)
.onPress(
closeDrawer
? () async {
Navigator.pop(context);
Future.delayed(const Duration(microseconds: 200), onPress);
}
: onPress!,
);
return Row(
children: [
SvgPicture.asset(icon, height: 20, width: 20),
9.width,
title.toText14(color: color, textAlign: AppState().isArabic(context) ? TextAlign.right : null).expanded,
],
).paddingOnly(left: 21, top: 10, bottom: 10, right: 21).onPress(closeDrawer
? () async {
Navigator.pop(context);
Future.delayed(const Duration(microseconds: 200), onPress);
}
: onPress!);
}
void postLanguageChange(BuildContext context) {
@ -167,13 +171,13 @@ class _AppDrawerState extends State<AppDrawer> {
setState(() {});
}
void performLogout() async {
AppState().isAuthenticated = false;
AppState().isLogged = false;
AppState().setPostParamsInitConfig();
chatData.disposeData();
// SharedPreferences prefs = await SharedPreferences.getInstance();
// await prefs.clear();
Navigator.pushNamedAndRemoveUntil(context, AppRoutes.login, (Route<dynamic> route) => false, arguments: null);
}
// void performLogout() async {
// // AppState().isAuthenticated = false;
// // AppState().isLogged = false;
// // AppState().setPostParamsInitConfig();
// // chatData.disposeData();
// // // SharedPreferences prefs = await SharedPreferences.getInstance();
// // // await prefs.clear();
// // Navigator.pushNamedAndRemoveUntil(context, AppRoutes.login, (Route<dynamic> route) => false, arguments: null);
// }
}

@ -8,7 +8,6 @@ import 'package:mohem_flutter_app/config/routes.dart';
import 'package:mohem_flutter_app/extensions/string_extensions.dart';
import 'package:mohem_flutter_app/extensions/widget_extensions.dart';
import 'package:mohem_flutter_app/generated/locale_keys.g.dart';
import 'package:mohem_flutter_app/models/eit/get_eit_transaction_model.dart';
import 'package:mohem_flutter_app/models/sso_auth_model.dart';
import 'package:mohem_flutter_app/provider/dashboard_provider_model.dart';
import 'package:mohem_flutter_app/ui/my_attendance/dynamic_screens/dynamic_listview_screen.dart';
@ -123,28 +122,28 @@ class MenusWidget extends StatelessWidget {
],
).paddingOnly(left: 10, right: 10, bottom: 6, top: 6),
).onPress(() async {
// Navigator.pushNamed(context, AppRoutes.dynamicScreen, arguments: DynamicListViewParams(LocaleKeys.ticketBalance.tr(), "HMG_TKT_NEW_EIT_SS"));
Navigator.pushNamed(context, AppRoutes.dynamicScreen, arguments: DynamicListViewParams(LocaleKeys.ticketBalance.tr(), "HMG_TKT_NEW_EIT_SS"));
var pro = Provider.of<DashboardProviderModel>(context, listen: false);
// if (menuEntry.menuName == "HMG_TICKET_REQUESTS") {
Utils.showLoading(context);
//Ticket Work
if (pro.ticketBookingResponse != null && pro.ticketBookingResponse!.success) {
SSOAuthModel? ssoToken = await pro.fetchSSOAuthRedirection(clientID: pro.ticketBookingResponse!.clientId);
if (ssoToken != null) {
dynamic url = await pro.fetchURLRedirection(token: ssoToken.data!.accessToken!);
await pro.fetchTicketAccuralBalance(context, DateTime.now());
pro.ticketHistoryTransactionList = await EITApiClient().getEITTransactions("HMG_TICKET_ITENARY_HR_EIT_SS", isCompleteList: true);
Utils.hideLoading(context);
// Here Need Work
Navigator.push(context, MaterialPageRoute(builder: (BuildContext context) => TicketDetailedScreen(url: url, jwtToken: ssoToken.data!.accessToken)));
}
//}
} else {
Navigator.pushNamed(context, AppRoutes.dynamicScreen, arguments: DynamicListViewParams(LocaleKeys.ticketBalance.tr(), "HMG_TKT_NEW_EIT_SS"));
}
// var pro = Provider.of<DashboardProviderModel>(context, listen: false);
//
// // if (menuEntry.menuName == "HMG_TICKET_REQUESTS") {
// Utils.showLoading(context);
// //Ticket Work
// if (pro.ticketBookingResponse != null && pro.ticketBookingResponse!.success) {
// SSOAuthModel? ssoToken = await pro.fetchSSOAuthRedirection(clientID: pro.ticketBookingResponse!.clientId);
// if (ssoToken != null) {
// dynamic url = await pro.fetchURLRedirection(token: ssoToken.data!.accessToken!);
// await pro.fetchTicketAccuralBalance(context, DateTime.now());
// pro.ticketHistoryTransactionList = await EITApiClient().getEITTransactions("HMG_TICKET_ITENARY_HR_EIT_SS", isCompleteList: true);
//
// Utils.hideLoading(context);
// // Here Need Work
// Navigator.push(context, MaterialPageRoute(builder: (BuildContext context) => TicketDetailedScreen(url: url, jwtToken: ssoToken.data!.accessToken)));
// }
// //}
// } else {
// Navigator.pushNamed(context, AppRoutes.dynamicScreen, arguments: DynamicListViewParams(LocaleKeys.ticketBalance.tr(), "HMG_TKT_NEW_EIT_SS"));
// }
}),
],
);

@ -92,7 +92,7 @@ class ServicesWidget extends StatelessWidget {
aspectRatio: 105 / 105,
child:
data.isServicesMenusLoading
? const ServicesMenuShimmer()
? ServicesMenuShimmer()
: Container(
decoration: BoxDecoration(
color: Colors.white,
@ -266,6 +266,7 @@ class ServicesWidget extends StatelessWidget {
await pro.fetchTicketAccuralBalance(context, DateTime.now());
pro.ticketHistoryTransactionList = await EITApiClient().getEITTransactions("HMG_TICKET_ITENARY_HR_EIT_SS", isCompleteList: true);
Utils.hideLoading(context);
// Here Need Work
Navigator.push(context, MaterialPageRoute(builder: (BuildContext context) => TicketDetailedScreen(url: url, jwtToken: ssoToken.data!.accessToken)));
@ -310,7 +311,7 @@ class ServicesWidget extends StatelessWidget {
padding: const EdgeInsets.only(left: 21, right: 21, top: 13, bottom: 13),
scrollDirection: Axis.horizontal,
itemBuilder: (cxt, index) {
return AspectRatio(aspectRatio: 105 / 105, child: const ServicesMenuShimmer());
return AspectRatio(aspectRatio: 105 / 105, child: ServicesMenuShimmer());
},
separatorBuilder: (cxt, index) => 9.width,
itemCount: 4,

@ -1,333 +0,0 @@
import 'package:easy_localization/easy_localization.dart';
import 'package:flutter/material.dart';
import 'package:flutter_inappwebview/flutter_inappwebview.dart';
import 'package:flutter_svg/flutter_svg.dart';
import 'package:mohem_flutter_app/app_state/app_state.dart';
import 'package:mohem_flutter_app/classes/colors.dart';
import 'package:mohem_flutter_app/classes/inAppWebView.dart';
import 'package:mohem_flutter_app/classes/utils.dart';
import 'package:mohem_flutter_app/extensions/int_extensions.dart';
import 'package:mohem_flutter_app/extensions/string_extensions.dart';
import 'package:mohem_flutter_app/extensions/widget_extensions.dart';
import 'package:mohem_flutter_app/generated/locale_keys.g.dart';
import 'package:mohem_flutter_app/models/dashboard/courses_response_model.dart';
import 'package:mohem_flutter_app/provider/dashboard_provider_model.dart';
import 'package:mohem_flutter_app/theme/colors.dart' as theme_colors;
import 'package:mohem_flutter_app/widgets/app_bar_widget.dart';
import 'package:mohem_flutter_app/widgets/sso_webview_widget.dart';
import 'package:provider/provider.dart';
import 'package:pull_to_refresh/pull_to_refresh.dart';
class CoursesScreen extends StatefulWidget {
const CoursesScreen({Key? key}) : super(key: key);
@override
_CoursesScreenState createState() => _CoursesScreenState();
}
class _CoursesScreenState extends State<CoursesScreen> {
late DashboardProviderModel data;
final RefreshController _refreshController = RefreshController(initialRefresh: false);
@override
void initState() {
super.initState();
WidgetsBinding.instance.addPostFrameCallback((_) {
data = Provider.of<DashboardProviderModel>(context, listen: false);
_onRefresh();
});
}
void _onRefresh() async {
await data.fetchCourses(context);
_refreshController.refreshCompleted();
}
@override
Widget build(BuildContext context) {
return Scaffold(
appBar: AppBarWidget(
context,
title: LocaleKeys.courses.tr(),
),
body: Consumer<DashboardProviderModel>(
builder: (context, provider, child) {
return SmartRefresher(
enablePullDown: true,
enablePullUp: false,
controller: _refreshController,
onRefresh: _onRefresh,
child: provider.isCoursesLoading
? _buildShimmerLoading()
: provider.coursesList.isEmpty
? _buildEmptyState()
: _buildCoursesList(provider.coursesList),
);
},
),
);
}
Widget _buildShimmerLoading() {
return ListView.builder(
padding: const EdgeInsets.all(21),
itemCount: 5,
itemBuilder: (context, index) {
return Container(
margin: const EdgeInsets.only(bottom: 12),
height: 150,
decoration: BoxDecoration(
color: Colors.white,
borderRadius: BorderRadius.circular(15),
boxShadow: [
BoxShadow(
color: const Color(0xff000000).withOpacity(.05),
blurRadius: 26,
offset: const Offset(0, -3),
),
],
),
child: Column(
crossAxisAlignment: CrossAxisAlignment.start,
children: [
Container(
height: 20,
width: 200,
decoration: BoxDecoration(
color: Colors.grey[300],
borderRadius: BorderRadius.circular(4),
),
).toShimmer(),
12.height,
Container(
height: 14,
width: 100,
decoration: BoxDecoration(
color: Colors.grey[300],
borderRadius: BorderRadius.circular(4),
),
).toShimmer(),
const Spacer(),
Container(
height: 40,
decoration: BoxDecoration(
color: Colors.grey[300],
borderRadius: BorderRadius.circular(6),
),
).toShimmer(),
],
).paddingAll(14),
);
},
);
}
Widget _buildEmptyState() {
return Utils.getNoDataWidget(context);
}
Widget _buildCoursesList(List<CourseStatus> courses) {
return ListView.separated(
physics: const BouncingScrollPhysics(),
shrinkWrap: true,
padding: const EdgeInsets.all(21),
itemBuilder: (BuildContext context, int index) {
return _buildCourseCard(courses[index]);
},
separatorBuilder: (BuildContext context, int index) => 12.height,
itemCount: courses.length,
);
}
Widget _buildCourseCard(CourseStatus course) {
bool isArabic = AppState().isArabic(context);
String courseName = isArabic && course.cNameAr != null && course.cNameAr!.isNotEmpty
? course.cNameAr!
: course.cFullname ?? '';
String status = course.cStatus ?? 'Unknown';
Color statusColor = _getStatusColor(status);
return InkWell(
onTap: () => _openCourse(course.cUrl, course.token),
child: Column(
crossAxisAlignment: CrossAxisAlignment.start,
children: [
// Course Title
Row(
children: [
Container(
padding: const EdgeInsets.all(8),
decoration: BoxDecoration(
color: MyColors.lightGreyEFColor,
borderRadius: BorderRadius.circular(8),
),
child: const Icon(
Icons.school_rounded,
color: MyColors.gradiantStartColor,
size: 20,
),
),
12.width,
Expanded(
child: courseName.toText14(isBold: true, color: MyColors.darkTextColor),
),
],
),
12.height,
// Status Badge
Row(
children: [
Icon(
_getStatusIcon(status),
size: 16,
color: statusColor,
),
6.width,
LocaleKeys.status.tr().toText11(color: MyColors.grey98Color),
8.width,
Container(
padding: const EdgeInsets.symmetric(horizontal: 10, vertical: 4),
decoration: BoxDecoration(
color: statusColor.withOpacity(0.1),
borderRadius: BorderRadius.circular(12),
border: Border.all(
color: statusColor.withOpacity(0.3),
width: 1,
),
),
child: status.toText10(color: statusColor, isBold: true),
),
],
),
10.height,
// Start Date
if (course.cEnddate != null && course.cEnddate!.isNotEmpty)
Row(
children: [
const Icon(
Icons.calendar_month_rounded,
size: 16,
color: MyColors.darkIconColor,
),
6.width,
LocaleKeys.endDateT.tr().toText11(color: MyColors.grey98Color),
8.width,
Expanded(
child: _formatDate(course.cEnddate!).toText11(
color: MyColors.darkTextColor,
isBold: true,
),
),
],
),
if (course.cStartdate != null && course.cStartdate!.isNotEmpty) 14.height,
// Open Button
Row(
mainAxisAlignment: MainAxisAlignment.end,
children: [
LocaleKeys.open.tr().toText12(color: MyColors.gradiantStartColor, isUnderLine: true),
6.width,
RotatedBox(
quarterTurns: AppState().isArabic(context) ? 2 : 4,
child: SvgPicture.asset(
"assets/images/arrow_next.svg",
color: MyColors.gradiantStartColor,
width: 16,
height: 16,
),
),
],
),
],
).objectContainerView(),
);
}
IconData _getStatusIcon(String status) {
if (status.toLowerCase().contains('passed')) {
return Icons.check_circle_rounded;
} else if (status.toLowerCase().contains('not passed') || status.toLowerCase().contains('failed')) {
return Icons.cancel_rounded;
} else if (status.toLowerCase().contains('in progress')) {
return Icons.pending_rounded;
} else {
return Icons.info_rounded;
}
}
Color _getStatusColor(String status) {
if (status.toLowerCase().contains('passed') && !status.toLowerCase().contains('not passed')) {
return Colors.green;
} else if (status.toLowerCase().contains('not passed') || status.toLowerCase().contains('failed')) {
return Colors.red;
} else if (status.toLowerCase().contains('in progress')) {
return Colors.yellow[700]!;
} else {
return MyColors.grey98Color;
}
}
DateTime? _parseDate(String? date) {
if (date == null || date.isEmpty) return null;
try {
return DateTime.parse(date.replaceAll(' ', 'T'));
} catch (e) {
try {
DateFormat format = DateFormat('yyyy-MM-dd HH:mm:ss');
return format.parse(date);
} catch (e) {
return null;
}
}
}
String _formatDate(String date) {
DateTime? dateTime = _parseDate(date);
if (dateTime == null) return date;
bool isArabic = AppState().isArabic(context);
DateFormat format = DateFormat('dd MMM yyyy, hh:mm a', isArabic ? 'ar' : 'en');
return format.format(dateTime);
}
void _openCourse(String? url, String? jwtToken) {
Navigator.push(context, MaterialPageRoute(builder: (BuildContext context) => SsoLoginWebView(url: url, jwtToken: jwtToken)));
//Utils.showToast(LocaleKeys.courseUrlNotAvailable.tr());
// return;
// }
//
// MyInAppBrowser browser = MyInAppBrowser(
// onExitCallback: () {},
// onLoadStartCallback: (String url) {},
// );
//
// var settings = InAppBrowserClassSettings(
// webViewSettings: InAppWebViewSettings(
// useShouldOverrideUrlLoading: false,
// transparentBackground: false,
// ),
// browserSettings: InAppBrowserSettings(
// hideUrlBar: true,
// hideTitleBar: false,
// toolbarTopBackgroundColor: theme_colors.primaryColor,
// ),
// );
//
// browser.openUrlRequest(
// urlRequest: URLRequest(url: WebUri(url)),
// settings: settings,
// );
}
@override
void dispose() {
_refreshController.dispose();
super.dispose();
}
}

@ -192,78 +192,10 @@ class _MowadhafhiHRRequestState extends State<MowadhafhiHRRequest> {
title.toText16().expanded,
6.width,
SimpleButton(LocaleKeys.add.tr(), () async {
FilePickerResult? result = await FilePicker.platform.pickFiles(
allowMultiple: true,
);
FilePickerResult? result = await FilePicker.platform.pickFiles(allowMultiple: true);
if (result != null) {
// Maximum file size: 2 MB (in bytes)
const int maxFileSizeInBytes = 2 * 1024 * 1024; // 2 MB = 2097152 bytes
List<File> newFiles = [];
List<String> oversizedFiles = [];
for (PlatformFile platformFile in result.files) {
if (platformFile.path != null) {
File file = File(platformFile.path!);
// Get file size - check multiple sources for iOS compatibility
int fileSize = 0;
// Method 1: Check platformFile.size first
if (platformFile.size > 0) {
fileSize = platformFile.size;
debugPrint('Using platformFile.size: $fileSize bytes');
}
// Method 2: Always verify with file.length() as well
try {
int fileLengthSize = await file.length();
debugPrint('Using file.length(): $fileLengthSize bytes');
// Use the maximum of both to ensure we catch the real size
if (fileLengthSize > fileSize) {
fileSize = fileLengthSize;
debugPrint('Using larger value from file.length()');
}
} catch (e) {
debugPrint('Error getting file.length(): $e');
// If file.length() fails, rely on platformFile.size
if (fileSize == 0) {
debugPrint('Cannot determine file size, rejecting file: ${platformFile.name}');
oversizedFiles.add('${platformFile.name} (unknown size)');
continue;
}
}
double fileSizeMB = fileSize / (1024 * 1024);
debugPrint('Final file size - ${platformFile.name}: $fileSize bytes (${fileSizeMB.toStringAsFixed(2)} MB)');
// STRICT validation: Only accept files that are 2 MB or less
if (fileSize > 0 && fileSize <= maxFileSizeInBytes) {
debugPrint('✓ File accepted: ${platformFile.name}');
newFiles.add(file);
} else if (fileSize > maxFileSizeInBytes) {
debugPrint('✗ File REJECTED (too large): ${platformFile.name} - ${fileSizeMB.toStringAsFixed(2)} MB');
oversizedFiles.add('${platformFile.name} (${fileSizeMB.toStringAsFixed(2)} MB)');
} else {
debugPrint('✗ File REJECTED (invalid size): ${platformFile.name}');
oversizedFiles.add('${platformFile.name} (invalid)');
}
}
}
// Only add valid files
if (newFiles.isNotEmpty) {
attachmentFiles = attachmentFiles + newFiles;
attachmentFiles = attachmentFiles.toSet().toList();
debugPrint('Total files attached: ${attachmentFiles.length}');
}
// Show error message for rejected files
if (oversizedFiles.isNotEmpty) {
String fileList = oversizedFiles.join('\n');
Utils.showToast('Max 2MB File allowed.');
debugPrint('Total rejected files: ${oversizedFiles.length}');
}
attachmentFiles = attachmentFiles + result.paths.map((path) => File(path!)).toList();
attachmentFiles = attachmentFiles.toSet().toList();
setState(() {});
}
}, fontSize: 14),

@ -5,17 +5,14 @@ import 'package:flutter/material.dart';
import 'package:mohem_flutter_app/app_state/app_state.dart';
import 'package:mohem_flutter_app/classes/colors.dart';
import 'package:mohem_flutter_app/classes/date_uitl.dart';
import 'package:mohem_flutter_app/classes/file_process.dart';
import 'package:mohem_flutter_app/classes/utils.dart';
import 'package:mohem_flutter_app/extensions/int_extensions.dart';
import 'package:mohem_flutter_app/extensions/string_extensions.dart';
import 'package:mohem_flutter_app/extensions/widget_extensions.dart';
import 'package:mohem_flutter_app/generated/locale_keys.g.dart';
import 'package:mohem_flutter_app/models/dashboard/get_accural_ticket_balance_model.dart';
import 'package:mohem_flutter_app/models/eit/get_eit_transaction_model.dart';
import 'package:mohem_flutter_app/models/eit_attachment_ticket_model.dart';
import 'package:mohem_flutter_app/provider/dashboard_provider_model.dart';
import 'package:mohem_flutter_app/widgets/app_bar_widget.dart';
import 'package:mohem_flutter_app/widgets/balances_dashboard_widget.dart';
import 'package:mohem_flutter_app/widgets/button/default_button.dart';
import 'package:mohem_flutter_app/widgets/item_detail_view_widget.dart';
import 'package:mohem_flutter_app/widgets/sso_webview_widget.dart';
@ -58,7 +55,7 @@ class _TicketDetailedScreenState extends State<TicketDetailedScreen> {
Widget build(BuildContext context) {
return Scaffold(
backgroundColor: Colors.white,
appBar: AppBarWidget(context, title:LocaleKeys.ticketDetails.tr()),
appBar: AppBarWidget(context, title: "Ticket Details"),
body: Column(
children: <Widget>[
ListView(
@ -77,7 +74,7 @@ class _TicketDetailedScreenState extends State<TicketDetailedScreen> {
children: <Widget>[
Row(
children: <Widget>[
LocaleKeys.currentTicketBalance.tr().toText20().expanded,
"Current Ticket Balance".toText20().expanded,
Row(
children: <Widget>[
const Icon(Icons.calendar_month_rounded, color: MyColors.darkIconColor, size: 16),
@ -115,20 +112,21 @@ class _TicketDetailedScreenState extends State<TicketDetailedScreen> {
),
),
const SizedBox(height: 21),
(dashboardProviderModel != null && dashboardProviderModel!.ticketHistoryTransactionList != null && dashboardProviderModel!.ticketHistoryTransactionList!.isNotEmpty)
? ListView(
dashboardProviderModel == null && dashboardProviderModel!.ticketHistoryTransactionList == null
? const SizedBox()
: ListView(
shrinkWrap: true,
physics: const NeverScrollableScrollPhysics(),
children: <Widget>[
LocaleKeys.ticketHistory.tr().toText20().expanded,
"Tickets History".toText20().expanded,
12.height,
ListView.separated(
physics: const NeverScrollableScrollPhysics(),
shrinkWrap: true,
padding: EdgeInsets.zero,
itemBuilder: (BuildContext cxt, int cardIndex) {
List<CollectionTransaction> transactionDetails = dashboardProviderModel!.ticketHistoryTransactionList![cardIndex];
const Set<String> allowedSegmentNames = <String>{
var transactionDetails = dashboardProviderModel!.ticketHistoryTransactionList![cardIndex];
const allowedSegmentNames = <String>{
"TICKETS_ROUTE",
"TRAVELER_NAME",
"TICKETS_EFFECTIVE_DATE",
@ -137,22 +135,11 @@ class _TicketDetailedScreenState extends State<TicketDetailedScreen> {
"TICKET_COMP_SHARE",
"TICKET_EMP_SHARE",
};
// Get items for display
List<CollectionTransaction> uniqueDetails =
var uniqueDetails =
transactionDetails
.where(
(CollectionTransaction item) =>
item.dISPLAYFLAG != 'N' && item.sEGMENTPROMPT != null && item.sEGMENTPROMPT!.isNotEmpty && allowedSegmentNames.contains(item.sEGMENTNAME),
)
.where((item) => item.dISPLAYFLAG != 'N' && item.sEGMENTPROMPT != null && item.sEGMENTPROMPT!.isNotEmpty && allowedSegmentNames.contains(item.sEGMENTNAME))
.toList();
// Get PEI_EXTRA_INFO_ID value for View PDF
CollectionTransaction? peiExtraInfoItem = transactionDetails.firstWhere(
(CollectionTransaction item) => item.aPPLICATIONCOLUMNNAME == "PEI_EXTRA_INFO_ID",
orElse: () => CollectionTransaction(),
);
num? peiExtraInfoId = peiExtraInfoItem.nUMBERVALUE;
return Column(
crossAxisAlignment: CrossAxisAlignment.start,
mainAxisSize: MainAxisSize.min,
@ -161,15 +148,15 @@ class _TicketDetailedScreenState extends State<TicketDetailedScreen> {
physics: const NeverScrollableScrollPhysics(),
shrinkWrap: true,
itemCount: (uniqueDetails.length / 2).ceil(),
itemBuilder: (BuildContext context, int rowIndex) {
itemBuilder: (context, rowIndex) {
int firstIndex = rowIndex * 2;
int? secondIndex = (firstIndex + 1 < uniqueDetails.length) ? firstIndex + 1 : null;
bool isLastRow = (rowIndex == (uniqueDetails.length / 2).ceil() - 1);
CollectionTransaction item1 = uniqueDetails[firstIndex];
ItemDetailViewCol child1 = ItemDetailViewCol(item1.sEGMENTPROMPT!, item1.vARCHAR2VALUE ?? item1.nUMBERVALUE?.toString() ?? "");
var item1 = uniqueDetails[firstIndex];
var child1 = ItemDetailViewCol(item1.sEGMENTPROMPT!, item1.vARCHAR2VALUE ?? item1.nUMBERVALUE?.toString() ?? "");
Widget child2;
if (secondIndex != null) {
CollectionTransaction item2 = uniqueDetails[secondIndex];
var item2 = uniqueDetails[secondIndex];
child2 = ItemDetailViewCol(item2.sEGMENTPROMPT!, item2.vARCHAR2VALUE ?? item2.nUMBERVALUE?.toString() ?? "");
} else {
child2 = const SizedBox(); // Empty widget if there is no second item
@ -177,40 +164,6 @@ class _TicketDetailedScreenState extends State<TicketDetailedScreen> {
return ItemDetailGrid(child1, child2, isItLast: isLastRow);
},
),
// View PDF link at the bottom
if (peiExtraInfoId != null) ...[
const SizedBox(height: 5),
Align(
alignment: Alignment.centerRight,
child: GestureDetector(
onTap: () async {
Utils.showLoading(context);
try {
GetEitAttachmentTicket? result = await dashboardProviderModel!.getTicketEitPDFDownload(peiExtraInfoId: peiExtraInfoId.toString());
if (result != null && result.getEitAttachmentList != null && result.getEitAttachmentList!.isNotEmpty) {
String? base64Data = result.getEitAttachmentList!.first.fileData;
if (base64Data != null && base64Data.isNotEmpty) {
String fileName = result.getEitAttachmentList!.first.fileName!;
await FileProcess.downloadFile(base64Data, fileName);
Utils.hideLoading(context);
FileProcess.openFile(fileName);
} else {
Utils.hideLoading(context);
Utils.showToast("PDF data not available");
}
} else {
Utils.hideLoading(context);
Utils.showToast("No attachment found");
}
} catch (e) {
Utils.hideLoading(context);
Utils.showToast("Something Went Wrong");
}
},
child: Padding(padding: const EdgeInsets.only(top: 8.0, left: 0.0, bottom: 8.0), child: "View PDF".toText14(isUnderLine: true, isBold: true)),
),
),
],
],
).objectContainerView();
},
@ -218,12 +171,11 @@ class _TicketDetailedScreenState extends State<TicketDetailedScreen> {
itemCount: dashboardProviderModel!.ticketHistoryTransactionList!.length,
),
],
)
: const SizedBox(),
),
],
],
).expanded,
DefaultButton(LocaleKeys.proceedBooking.tr(), () {
DefaultButton("Proceed For Booking", () {
if (widget.url != null && widget.jwtToken != null) {
Navigator.push(context, MaterialPageRoute(builder: (BuildContext context) => SsoLoginWebView(url: widget.url, jwtToken: widget.jwtToken)));
}

@ -8,8 +8,6 @@ import 'package:mohem_flutter_app/generated/locale_keys.g.dart';
import 'package:shimmer/shimmer.dart';
class GetAttendanceTrackingShimmer extends StatelessWidget {
const GetAttendanceTrackingShimmer({Key? key}) : super(key: key);
@override
Widget build(BuildContext context) {
return Container(
@ -19,7 +17,13 @@ class GetAttendanceTrackingShimmer extends StatelessWidget {
decoration: BoxDecoration(
color: Colors.white,
borderRadius: BorderRadius.circular(15),
boxShadow: [BoxShadow(color: const Color(0xff000000).withOpacity(.05), blurRadius: 26, offset: const Offset(0, -3))],
boxShadow: [
BoxShadow(
color: const Color(0xff000000).withOpacity(.05),
blurRadius: 26,
offset: const Offset(0, -3),
),
],
),
child: Stack(
alignment: Alignment.center,
@ -40,8 +44,15 @@ class GetAttendanceTrackingShimmer extends StatelessWidget {
LocaleKeys.timeLeftToday.tr().toText10(color: Colors.white).toShimmer(),
9.height,
const ClipRRect(
borderRadius: BorderRadius.all(Radius.circular(20)),
child: LinearProgressIndicator(value: 0.7, minHeight: 8, valueColor: const AlwaysStoppedAnimation<Color>(Colors.white), backgroundColor: const Color(0xff196D73)),
borderRadius: BorderRadius.all(
Radius.circular(20),
),
child: LinearProgressIndicator(
value: 0.7,
minHeight: 8,
valueColor: const AlwaysStoppedAnimation<Color>(Colors.white),
backgroundColor: const Color(0xff196D73),
),
).toShimmer(),
],
).paddingOnly(top: 12, right: 15, left: 12),
@ -52,7 +63,9 @@ class GetAttendanceTrackingShimmer extends StatelessWidget {
child: Column(
mainAxisSize: MainAxisSize.min,
crossAxisAlignment: CrossAxisAlignment.start,
children: [LocaleKeys.checkIn.tr().toText12(color: Colors.white).toShimmer()],
children: [
LocaleKeys.checkIn.tr().toText12(color: Colors.white).toShimmer(),
],
).paddingOnly(left: 12),
),
Container(
@ -72,8 +85,6 @@ class GetAttendanceTrackingShimmer extends StatelessWidget {
}
class MenuShimmer extends StatelessWidget {
const MenuShimmer({Key? key}) : super(key: key);
@override
Widget build(BuildContext context) {
return Container(
@ -81,7 +92,13 @@ class MenuShimmer extends StatelessWidget {
decoration: BoxDecoration(
color: Colors.white,
borderRadius: BorderRadius.circular(15),
boxShadow: [BoxShadow(color: const Color(0xff000000).withOpacity(.05), blurRadius: 26, offset: const Offset(0, -3))],
boxShadow: [
BoxShadow(
color: const Color(0xff000000).withOpacity(.05),
blurRadius: 26,
offset: const Offset(0, -3),
),
],
),
child: Column(
mainAxisAlignment: MainAxisAlignment.spaceBetween,
@ -90,11 +107,14 @@ class MenuShimmer extends StatelessWidget {
LocaleKeys.workList.tr().toText12(color: Colors.white).toShimmer(),
Row(
children: [
Expanded(flex: 3, child: 123.toString().toText10(color: Colors.white, isBold: true).toShimmer()),
Expanded(
flex: 3,
child: 123.toString().toText10(color: Colors.white, isBold: true).toShimmer(),
),
12.width,
SvgPicture.asset("assets/images/arrow_next.svg", color: Colors.white).toShimmer(),
SvgPicture.asset("assets/images/arrow_next.svg", color: Colors.white).toShimmer()
],
),
)
],
).paddingOnly(left: 10, right: 10, bottom: 6, top: 6),
);
@ -102,8 +122,6 @@ class MenuShimmer extends StatelessWidget {
}
class ServicesHeaderShimmer extends StatelessWidget {
const ServicesHeaderShimmer({Key? key}) : super(key: key);
@override
Widget build(BuildContext context) {
return Row(
@ -113,7 +131,11 @@ class ServicesHeaderShimmer extends StatelessWidget {
child: Column(
crossAxisAlignment: CrossAxisAlignment.start,
mainAxisSize: MainAxisSize.min,
children: [LocaleKeys.otherCharges.tr().toText10().toShimmer(), 6.height, LocaleKeys.services.tr().toText12(isBold: true).toShimmer()],
children: [
LocaleKeys.otherCharges.tr().toText10().toShimmer(),
6.height,
LocaleKeys.services.tr().toText12(isBold: true).toShimmer(),
],
),
),
LocaleKeys.viewAllServices.tr().toText12(isUnderLine: true).toShimmer(),
@ -123,15 +145,19 @@ class ServicesHeaderShimmer extends StatelessWidget {
}
class ServicesMenuShimmer extends StatelessWidget {
const ServicesMenuShimmer({Key? key}) : super(key: key);
@override
Widget build(BuildContext context) {
return Container(
decoration: BoxDecoration(
color: Colors.white,
borderRadius: BorderRadius.circular(15),
boxShadow: [BoxShadow(color: const Color(0xff000000).withOpacity(.05), blurRadius: 26, offset: const Offset(0, -3))],
boxShadow: [
BoxShadow(
color: const Color(0xff000000).withOpacity(.05),
blurRadius: 26,
offset: const Offset(0, -3),
),
],
),
child: Column(
mainAxisAlignment: MainAxisAlignment.spaceBetween,
@ -147,54 +173,21 @@ class ServicesMenuShimmer extends StatelessWidget {
Row(
crossAxisAlignment: CrossAxisAlignment.end,
children: [
Expanded(child: LocaleKeys.attendance.tr().toText11(isBold: false).toShimmer()),
Expanded(
child: LocaleKeys.attendance.tr().toText11(isBold: false).toShimmer(),
),
6.width,
SvgPicture.asset("assets/images/arrow_next.svg").paddingOnly(bottom: 4).toShimmer(),
SvgPicture.asset("assets/images/arrow_next.svg").paddingOnly(bottom: 4).toShimmer()
],
),
],
),
)
],
).paddingOnly(left: 10, right: 10, bottom: 10, top: 12),
);
}
}
class GreetingCardShimmer extends StatelessWidget {
const GreetingCardShimmer({Key? key}) : super(key: key);
@override
Widget build(BuildContext context) {
return Container(
height: 140,
decoration: BoxDecoration(color: const Color(0xFFFAF4E7), border: Border.all(width: 2, color: const Color(0xFFE7E7E7)), borderRadius: BorderRadius.circular(20)),
child: Row(
mainAxisAlignment: MainAxisAlignment.start,
crossAxisAlignment: CrossAxisAlignment.start,
children: [
const SizedBox(width: 10),
Container(width: 65, height: 100, decoration: BoxDecoration(color: Colors.grey[300], borderRadius: BorderRadius.circular(10))).toShimmer().paddingOnly(top: 10),
const SizedBox(width: 10),
Column(
crossAxisAlignment: CrossAxisAlignment.start,
mainAxisAlignment: MainAxisAlignment.center,
children: [
Container(width: 150, height: 16, decoration: BoxDecoration(color: Colors.white, borderRadius: BorderRadius.circular(4))).toShimmer(),
const SizedBox(height: 8),
Container(width: 120, height: 16, decoration: BoxDecoration(color: Colors.white, borderRadius: BorderRadius.circular(4))).toShimmer(),
],
).expanded,
Column(
crossAxisAlignment: CrossAxisAlignment.end,
mainAxisAlignment: MainAxisAlignment.end,
children: [Container(width: 60, height: 12, decoration: BoxDecoration(color: Colors.white, borderRadius: BorderRadius.circular(4))).toShimmer()],
),
],
).paddingOnly(left: 8, right: 8, top: 6, bottom: 12),
).paddingOnly(top: 14, bottom: 14);
}
}
class MarathonBannerShimmer extends StatelessWidget {
const MarathonBannerShimmer({Key? key}) : super(key: key);
@ -204,7 +197,13 @@ class MarathonBannerShimmer extends StatelessWidget {
decoration: BoxDecoration(
color: Colors.white,
borderRadius: BorderRadius.circular(15),
boxShadow: [BoxShadow(color: const Color(0xff000000).withOpacity(.05), blurRadius: 26, offset: const Offset(0, -3))],
boxShadow: [
BoxShadow(
color: const Color(0xff000000).withOpacity(.05),
blurRadius: 26,
offset: const Offset(0, -3),
),
],
),
child: Column(
mainAxisAlignment: MainAxisAlignment.spaceBetween,
@ -220,13 +219,15 @@ class MarathonBannerShimmer extends StatelessWidget {
Row(
crossAxisAlignment: CrossAxisAlignment.end,
children: [
Expanded(child: LocaleKeys.attendance.tr().toText11(isBold: false).toShimmer()),
Expanded(
child: LocaleKeys.attendance.tr().toText11(isBold: false).toShimmer(),
),
6.width,
SvgPicture.asset("assets/images/arrow_next.svg").paddingOnly(bottom: 4).toShimmer(),
SvgPicture.asset("assets/images/arrow_next.svg").paddingOnly(bottom: 4).toShimmer()
],
),
],
),
)
],
).paddingOnly(left: 10, right: 10, bottom: 10, top: 12),
);
@ -242,43 +243,65 @@ class ChatHomeShimmer extends StatelessWidget {
@override
Widget build(BuildContext context) {
return Container(
width: double.infinity,
padding: const EdgeInsets.symmetric(horizontal: 16.0, vertical: 16.0),
child: Column(
mainAxisSize: MainAxisSize.max,
children: <Widget>[
Expanded(
child: Shimmer.fromColors(
baseColor: Colors.white,
highlightColor: Colors.grey.shade100,
child: ListView.builder(
itemBuilder:
(_, __) => Padding(
padding: const EdgeInsets.only(bottom: 8.0),
child: Row(
crossAxisAlignment: CrossAxisAlignment.start,
children: <Widget>[
if (!isDetailedScreen) Container(width: 48.0, height: 48.0, decoration: const BoxDecoration(color: Colors.white, borderRadius: BorderRadius.all(Radius.circular(40)))),
if (!isDetailedScreen) const Padding(padding: EdgeInsets.symmetric(horizontal: 8.0)),
Column(
crossAxisAlignment: CrossAxisAlignment.start,
children: <Widget>[
Container(width: double.infinity, height: 20.0, color: Colors.white),
const Padding(padding: EdgeInsets.symmetric(vertical: 2.0)),
Container(width: double.infinity, height: 15.0, color: Colors.white),
const Padding(padding: EdgeInsets.symmetric(vertical: 2.0)),
Container(width: 40.0, height: 10.0, color: Colors.white),
],
).expanded,
],
),
width: double.infinity,
padding: const EdgeInsets.symmetric(horizontal: 16.0, vertical: 16.0),
child: Column(
mainAxisSize: MainAxisSize.max,
children: <Widget>[
Expanded(
child: Shimmer.fromColors(
baseColor: Colors.white,
highlightColor: Colors.grey.shade100,
child: ListView.builder(
itemBuilder: (_, __) => Padding(
padding: const EdgeInsets.only(bottom: 8.0),
child: Row(
crossAxisAlignment: CrossAxisAlignment.start,
children: <Widget>[
if (!isDetailedScreen)
Container(
width: 48.0,
height: 48.0,
decoration: const BoxDecoration(color: Colors.white, borderRadius: BorderRadius.all(Radius.circular(40))),
),
if (!isDetailedScreen)
const Padding(
padding: EdgeInsets.symmetric(horizontal: 8.0),
),
Column(
crossAxisAlignment: CrossAxisAlignment.start,
children: <Widget>[
Container(
width: double.infinity,
height: 20.0,
color: Colors.white,
),
const Padding(
padding: EdgeInsets.symmetric(vertical: 2.0),
),
Container(
width: double.infinity,
height: 15.0,
color: Colors.white,
),
const Padding(
padding: EdgeInsets.symmetric(vertical: 2.0),
),
Container(
width: 40.0,
height: 10.0,
color: Colors.white,
),
],
).expanded
],
),
itemCount: 6,
),
itemCount: 6,
),
),
),
),
],
),
);
],
));
}
}

@ -15,13 +15,10 @@ class SsoLoginWebView extends StatefulWidget {
class _SsoLoginWebViewState extends State<SsoLoginWebView> {
late final WebViewController _controller;
String? url;
@override
void initState() {
// TODO: implement initState
url = widget.url ?? "https://Paxes-release.techmaster.in/SSO/HMG";
super.initState();
_controller =
WebViewController()
@ -49,7 +46,7 @@ class _SsoLoginWebViewState extends State<SsoLoginWebView> {
<!DOCTYPE html>
<html>
<body onload="document.forms[0].submit()">
<form method="POST" action="https://www.paxes.com/sso/hmg">
<form method="POST" action="https://Paxes-release.techmaster.in/SSO/HMG">
<input type="hidden" name="JWTToken" value="${widget.jwtToken}" />
</form>
<h1>Redirecting...</h1>
@ -57,9 +54,8 @@ class _SsoLoginWebViewState extends State<SsoLoginWebView> {
</html>''');
}
//// <form method="POST" action="${widget.url}">
@override
Widget build(BuildContext context) {
return Scaffold(appBar: null, body:SafeArea(child: WebViewWidget(controller: _controller)));
return Scaffold(appBar: AppBar(title: Text('Logging in...')), body: WebViewWidget(controller: _controller));
}
}

@ -17,7 +17,7 @@ publish_to: 'none' # Remove this line if you wish to publish to pub.dev
# Read more about iOS versioning at
# https://developer.apple.com/library/archive/documentation/General/Reference/InfoPlistKeyReference/Articles/CoreFoundationKeys.html
version: 3.7.2+300082
version: 3.7.1+300081
#version: 3.9.3+1
environment:

Loading…
Cancel
Save