This commit is contained in:
Hamza-Ayed
2024-11-10 18:38:07 +02:00
parent c9ac8da2ec
commit e8c72d79a9
25 changed files with 1211 additions and 329 deletions

View File

@@ -54,8 +54,8 @@ android {
// For more information, see: https://docs.flutter.dev/deployment/android#reviewing-the-gradle-build-configuration. // For more information, see: https://docs.flutter.dev/deployment/android#reviewing-the-gradle-build-configuration.
minSdk = 23 minSdk = 23
targetSdk = flutter.targetSdkVersion targetSdk = flutter.targetSdkVersion
versionCode = 113 versionCode = 117
versionName = '1.5.13' versionName = '1.5.17'
multiDexEnabled =true multiDexEnabled =true
} }

View File

@@ -28,6 +28,8 @@
<uses-feature android:name="android.hardware.camera.autofocus" /> <uses-feature android:name="android.hardware.camera.autofocus" />
<uses-permission android:name="android.permission.RECEIVE_BOOT_COMPLETED" /> <uses-permission android:name="android.permission.RECEIVE_BOOT_COMPLETED" />
<uses-permission android:name="com.google.android.c2dm.permission.RECEIVE" /> <uses-permission android:name="com.google.android.c2dm.permission.RECEIVE" />
<uses-permission android:name="android.permission.QUICKBOOT_POWERON" />
<uses-permission android:name="com.htc.intent.action.QUICKBOOT_POWERON" />
<application <application
android:allowBackup="true" android:allowBackup="true"
@@ -125,11 +127,8 @@
</service> </service>
<!-- <receiver <!-- <receiver
android:name="com.dexterous.flutterlocalnotifications.ScheduledNotificationReceiver"
android:exported="false" />
<receiver
android:name="com.dexterous.flutterlocalnotifications.ScheduledNotificationBootReceiver" android:name="com.dexterous.flutterlocalnotifications.ScheduledNotificationBootReceiver"
android:exported="false"> android:exported="true">
<intent-filter> <intent-filter>
<action android:name="android.intent.action.BOOT_COMPLETED" /> <action android:name="android.intent.action.BOOT_COMPLETED" />
<action android:name="android.intent.action.MY_PACKAGE_REPLACED" /> <action android:name="android.intent.action.MY_PACKAGE_REPLACED" />
@@ -137,6 +136,18 @@
<action android:name="com.htc.intent.action.QUICKBOOT_POWERON" /> <action android:name="com.htc.intent.action.QUICKBOOT_POWERON" />
</intent-filter> </intent-filter>
</receiver> --> </receiver> -->
<receiver android:exported="false"
android:name="com.dexterous.flutterlocalnotifications.ScheduledNotificationReceiver" />
<receiver android:exported="false"
android:name="com.dexterous.flutterlocalnotifications.ScheduledNotificationBootReceiver">
<intent-filter>
<action android:name="android.intent.action.BOOT_COMPLETED" />
<action android:name="android.intent.action.MY_PACKAGE_REPLACED" />
<action android:name="android.intent.action.QUICKBOOT_POWERON" />
<action android:name="com.htc.intent.action.QUICKBOOT_POWERON" />
</intent-filter>
</receiver>
<receiver <receiver
android:name=".YourBroadcastReceiver" android:name=".YourBroadcastReceiver"
android:exported="false" /> android:exported="false" />

View File

@@ -35,7 +35,7 @@
<key>CFBundlePackageType</key> <key>CFBundlePackageType</key>
<string>APPL</string> <string>APPL</string>
<key>CFBundleShortVersionString</key> <key>CFBundleShortVersionString</key>
<string>72</string> <string>77</string>
<key>CFBundleSignature</key> <key>CFBundleSignature</key>
<string>????</string> <string>????</string>
<key>CFBundleURLTypes</key> <key>CFBundleURLTypes</key>
@@ -50,7 +50,7 @@
</dict> </dict>
</array> </array>
<key>CFBundleVersion</key> <key>CFBundleVersion</key>
<string>4.0.72</string> <string>4.0.77</string>
<key>FirebaseAppDelegateProxyEnabled</key> <key>FirebaseAppDelegateProxyEnabled</key>
<string>NO</string> <string>NO</string>
<key>GMSApiKey</key> <key>GMSApiKey</key>

View File

@@ -48,7 +48,8 @@ class AppLink {
static String getWalletByDriver = "$walletDriver/getWalletByDriver.php"; static String getWalletByDriver = "$walletDriver/getWalletByDriver.php";
static String driverStatistic = "$walletDriver/driverStatistic.php"; static String driverStatistic = "$walletDriver/driverStatistic.php";
static String getDriverDetails = "$walletDriver/getDriverDetails.php"; static String getDriverDetails =
"$seferCairoServer/ride/driverWallet/getDriverDetails.php";
static String getDriverWeekPaymentMove = static String getDriverWeekPaymentMove =
"$walletDriver/getDriverWeekPaymentMove.php"; "$walletDriver/getDriverWeekPaymentMove.php";
static String getDriversWallet = "$walletDriver/get.php"; static String getDriversWallet = "$walletDriver/get.php";
@@ -73,6 +74,7 @@ class AppLink {
//-----------------ridessss------------------ //-----------------ridessss------------------
static String addRides = "$ride/rides/add.php"; static String addRides = "$ride/rides/add.php";
static String getRides = "$ride/rides/get.php"; static String getRides = "$ride/rides/get.php";
static String getMishwari = "$ride/ride/mishwari/get.php";
static String getTripCountByCaptain = "$ride/rides/getTripCountByCaptain.php"; static String getTripCountByCaptain = "$ride/rides/getTripCountByCaptain.php";
static String getRideOrderID = "$ride/rides/getRideOrderID.php"; static String getRideOrderID = "$ride/rides/getRideOrderID.php";
static String getRideStatus = "$ride/rides/getRideStatus.php"; static String getRideStatus = "$ride/rides/getRideStatus.php";
@@ -235,6 +237,10 @@ class AppLink {
static String getTotalDriverDurationToday = static String getTotalDriverDurationToday =
"$location/getTotalDriverDurationToday.php"; "$location/getTotalDriverDurationToday.php";
//==================cars new drivers=============
static String addNewCarsDrivers = '$server/ride/carDrivers/add.php';
static String getNewCarsDrivers = '$server/ride/carDrivers/get.php';
//==================Blog============= //==================Blog=============
static String profile = '$server/ride/profile'; static String profile = '$server/ride/profile';
static String getprofile = "$profile/get.php"; static String getprofile = "$profile/get.php";

View File

@@ -0,0 +1,22 @@
List<String> driverMessages = [
"💸 فرص الربح: افتح تطبيق سفر الآن وزد دخلك اليوم! المزيد من الطلبات بانتظارك! 🚗",
"🚀 طلبات جديدة: لا تضيع الفرصة! المزيد من الركاب ينتظرونك الآن على تطبيق سفر. 🏃‍♂️",
"📈 زيادة الدخل: حقق أعلى أرباح اليوم مع سفر! افتح التطبيق وابدأ عملك الآن. 💵",
"🕒 أوقات الذروة: استعد لكسب المزيد خلال فترات الطلب المرتفعة. افتح التطبيق الآن! 📲",
"🚗 طلبات جديدة: كن مستعداً، افتح تطبيق سفر الآن واستقبل المزيد من الطلبات. 🔔",
"🎉 فرص النجاح: ابدأ رحلتك إلى النجاح! افتح تطبيق سفر لزيادة دخلك اليوم. 💼",
"🌍 طلبات مرتفعة: المزيد من الركاب بانتظارك، لا تفوّت الفرص، افتح التطبيق الآن! 🚖",
"💪 زيادة الدخل: انطلق نحو تحقيق أهدافك المالية، افتح تطبيق سفر واكسب المزيد. 🏆",
"💰 أرباح إضافية: افتح التطبيق واستعد لتحقيق أرباح إضافية مع سفر! المزيد من الطلبات في انتظارك. 🛣️",
"🔥 فرص جديدة: تطبيق سفر مزدحم الآن! افتح التطبيق وزد أرباحك بفرص جديدة. 🚗",
"🚨 طلبات متزايدة: افتح تطبيق سفر الآن! الطلب مرتفع وفرص الربح كبيرة! 💸",
"💼 زيادة الدخل: هل أنت جاهز لتحقيق المزيد من الدخل؟ افتح التطبيق وانطلق الآن! 🚖",
"🚗 أوقات الذروة: احجز مقعدك في فترات الطلب العالي، افتح تطبيق سفر الآن واكسب المزيد. 📈",
"📲 بدء اليوم: ابدأ يومك مع سفر، وافتح التطبيق الآن لتزيد من فرص الربح. 💵",
"💸 فرص مستمرة: لا تفوت فرص الربح، افتح تطبيق سفر الآن وكن على استعداد للمزيد! 🔔",
"📆 زيادة الطلب: انطلق اليوم واستفد من الطلبات المتزايدة على تطبيق سفر! افتح التطبيق الآن. 🚗",
"💥 دخل إضافي: افتح تطبيق سفر الآن واستقبل طلبات جديدة تحقق لك المزيد من الدخل. 💰",
"🏆 فرص مرتفعة: استفد من طلبات اليوم المرتفعة، افتح التطبيق الآن مع سفر. 📲",
"🚗 تفضيل العملاء: كن السائق الذي يختاره الجميع! افتح تطبيق سفر اليوم واربح المزيد. 🔥",
"💸 دخل إضافي: فرص الدخل الإضافي في انتظارك! افتح تطبيق سفر واستمتع بالطلبات المتزايدة. 💼",
];

View File

@@ -187,11 +187,11 @@ class LoginDriverController extends GetxController {
if (token != 'failure') { if (token != 'failure') {
if (jsonDecode(token)['data'][0]['token'] != if (jsonDecode(token)['data'][0]['token'] !=
box.read(BoxName.tokenDriver)) { box.read(BoxName.tokenDriver)) {
Get.put(FirebaseMessagesController()) Get.put(FirebaseMessagesController()).sendNotificationToDriverMAP(
.sendNotificationToAnyWithoutData(
'token change'.tr, 'token change'.tr,
'change device'.tr, 'change device'.tr,
jsonDecode(token)['data'][0]['token'].toString(), jsonDecode(token)['data'][0]['token'].toString(),
[],
'promo.wav'); 'promo.wav');
Get.defaultDialog( Get.defaultDialog(
title: 'you will use this device?'.tr, title: 'you will use this device?'.tr,
@@ -316,11 +316,11 @@ class LoginDriverController extends GetxController {
if (token != 'failure') { if (token != 'failure') {
if (jsonDecode(token)['data'][0]['token'] != if (jsonDecode(token)['data'][0]['token'] !=
box.read(BoxName.tokenDriver)) { box.read(BoxName.tokenDriver)) {
Get.put(FirebaseMessagesController()) Get.put(FirebaseMessagesController()).sendNotificationToDriverMAP(
.sendNotificationToAnyWithoutData(
'token change'.tr, 'token change'.tr,
'change device'.tr, 'change device'.tr,
jsonDecode(token)['data'][0]['token'].toString(), jsonDecode(token)['data'][0]['token'].toString(),
[],
'promo.wav'); 'promo.wav');
Get.defaultDialog( Get.defaultDialog(
title: 'you will use this device?'.tr, title: 'you will use this device?'.tr,

View File

@@ -90,15 +90,28 @@ class GoogleSignInHelper {
final GoogleSignInAccount? googleUser = await _googleSignIn.signIn(); final GoogleSignInAccount? googleUser = await _googleSignIn.signIn();
if (googleUser != null) { if (googleUser != null) {
// Handle sign-up and store user information
await _handleSignUp(googleUser); await _handleSignUp(googleUser);
// Add detailed debug print statements // Retrieve driverID and emailDriver with added validation
final driverID = box.read(BoxName.driverID)?.toString() ?? 'Unknown ID'; final driverID = box.read(BoxName.driverID)?.toString() ?? 'Unknown ID';
final emailDriver = final emailDriver =
box.read(BoxName.emailDriver)?.toString() ?? 'Unknown Email'; box.read(BoxName.emailDriver)?.toString() ?? 'Unknown Email';
// Debug print statements
print('Driver ID: $driverID');
print('Driver Email: $emailDriver');
// Check if driverID is a valid numeric string
// if (driverID != 'Unknown ID' && int.tryParse(driverID) != null) {
await Get.find<LoginDriverController>() await Get.find<LoginDriverController>()
.loginUsingCredentials(driverID, emailDriver); .loginUsingCredentials(driverID, emailDriver);
// }
// else {
// print('Invalid driverID format: $driverID');
// Get.snackbar('Login Error', 'Invalid driver ID format.',
// backgroundColor: AppColor.redColor);
// }
} }
return googleUser; return googleUser;
@@ -110,6 +123,13 @@ class GoogleSignInHelper {
} }
} }
static Future<void> _handleSignUp(GoogleSignInAccount user) async {
// Store driver information
box.write(BoxName.driverID,
user.id ?? 'Unknown ID'); // Ensure there's a fallback value
box.write(BoxName.emailDriver, user.email ?? 'Unknown Email');
}
// Method to handle Google Sign-Out // Method to handle Google Sign-Out
static Future<void> signOut() async { static Future<void> signOut() async {
try { try {
@@ -145,16 +165,4 @@ class GoogleSignInHelper {
static GoogleSignInAccount? getCurrentUser() { static GoogleSignInAccount? getCurrentUser() {
return _googleSignIn.currentUser; return _googleSignIn.currentUser;
} }
// Method to handle sign-up process
static Future<void> _handleSignUp(GoogleSignInAccount user) async {
// Store driver information
box.write(BoxName.driverID, user.id);
box.write(BoxName.emailDriver, user.email);
// box.write(BoxName.nameDriver, user.displayName);
// box.write(BoxName.driverPhotoUrl, user.photoUrl);
// Perform any additional sign-up tasks or API calls here
// For example, you can send the user data to your server for registration
}
} }

View File

@@ -33,7 +33,8 @@ class FirebaseMessagesController extends GetxController {
late String driverID; late String driverID;
late String driverToken; late String driverToken;
NotificationSettings? notificationSettings; NotificationSettings? notificationSettings;
NotificationController notificationController =
Get.put(NotificationController());
Future<void> getNotificationSettings() async { Future<void> getNotificationSettings() async {
// Get the current notification settings // Get the current notification settings
NotificationSettings? notificationSettings = NotificationSettings? notificationSettings =
@@ -78,34 +79,15 @@ class FirebaseMessagesController extends GetxController {
RemoteNotification? notification = message.notification; RemoteNotification? notification = message.notification;
AndroidNotification? android = notification?.android; AndroidNotification? android = notification?.android;
// if (notification != null && android != null) { // if (notification != null && android != null) {
if (message.data.isNotEmpty && message.notification != null) {
fireBaseTitles(message);
}
if (message.data.isNotEmpty && message.notification != null) { if (message.data.isNotEmpty && message.notification != null) {
fireBaseTitles(message); fireBaseTitles(message);
} }
}); });
FirebaseMessaging.onBackgroundMessage((RemoteMessage message) async { FirebaseMessaging.onBackgroundMessage((RemoteMessage message) async {});
// if (message.notification!.title! == 'Order'.tr) {
// if (Platform.isAndroid) {
// NotificationController1()
// .showNotification('Order'.tr, '', 'order', 'order_page_payload');
// }
// // await FirebaseMessagesController().showOverlayNotification(message);
// var myListString = message.data['DriverList'];
// // var points = message.data['PolylineJson'];
// var myList = jsonDecode(myListString) as List<dynamic>;
// // var myPoints = jsonDecode(points) as List<dynamic>;
// driverToken = myList[14].toString();
// // This is for location using and uploading status
// Get.put(HomeCaptainController()).changeRideId();
// update();
// Get.to(() => OrderRequestPage(), arguments: {
// 'myListString': myListString,
// 'DriverList': myList,
// // 'PolylineJson': myPoints,
// 'body': message.notification!.body
// });
// }
});
FirebaseMessaging.onMessageOpenedApp.listen((RemoteMessage message) { FirebaseMessaging.onMessageOpenedApp.listen((RemoteMessage message) {
if (message.data.isNotEmpty && message.notification != null) { if (message.data.isNotEmpty && message.notification != null) {
@@ -117,7 +99,7 @@ class FirebaseMessagesController extends GetxController {
Future<void> fireBaseTitles(RemoteMessage message) async { Future<void> fireBaseTitles(RemoteMessage message) async {
if (message.notification!.title! == 'OrderSpeed'.tr) { if (message.notification!.title! == 'OrderSpeed'.tr) {
if (Platform.isAndroid) { if (Platform.isAndroid) {
NotificationController().showNotification( notificationController.showNotification(
message.notification!.title.toString(), message.notification!.title.toString(),
message.notification!.body.toString(), message.notification!.body.toString(),
'order', 'order',
@@ -139,9 +121,25 @@ class FirebaseMessagesController extends GetxController {
// 'PolylineJson': myPoints, // 'PolylineJson': myPoints,
'body': message.notification!.body 'body': message.notification!.body
}); });
} else if (message.notification!.title == 'Cancel Trip') { } else if (message.notification!.title == 'OrderVIP') {
var myListString = message.data['DriverList'];
var myList = jsonDecode(myListString) as List<dynamic>;
// driverToken = myList[10].toString();
if (Platform.isAndroid) { if (Platform.isAndroid) {
NotificationController1().showNotification( notificationController.showNotification(
'OrderVIP'.tr, 'OrderVIP'.tr, 'order', '');
}
Get.to(VipOrderPage(), arguments: {
'myListString': myListString,
'DriverList': myList,
// 'PolylineJson': myPoints,
'body': message.notification!.body
});
} else if (message.notification!.title == 'Cancel Trip'.tr) {
if (Platform.isAndroid) {
notificationController.showNotification(
'Cancel Trip'.tr, 'Passenger Cancel Trip'.tr, 'cancel', ''); 'Cancel Trip'.tr, 'Passenger Cancel Trip'.tr, 'cancel', '');
} }
cancelTripDialog(); cancelTripDialog();
@@ -149,8 +147,8 @@ class FirebaseMessagesController extends GetxController {
var myListString = message.data['DriverList']; var myListString = message.data['DriverList'];
var driverList = jsonDecode(myListString) as List<dynamic>; var driverList = jsonDecode(myListString) as List<dynamic>;
if (Platform.isAndroid) { if (Platform.isAndroid) {
NotificationController1() notificationController.showNotification(
.showNotification('VIP Order'.tr, '', 'order', ''); 'VIP Order'.tr, '', 'order', '');
} }
MyDialog().getDialog('VIP Order'.tr, 'midTitle', () { MyDialog().getDialog('VIP Order'.tr, 'midTitle', () {
sendNotificationToPassengerToken( sendNotificationToPassengerToken(
@@ -162,26 +160,19 @@ class FirebaseMessagesController extends GetxController {
}); });
// Get.to(const VipOrderPage()); // Get.to(const VipOrderPage());
} else if (message.notification!.title! == 'message From passenger'.tr) { } else if (message.notification!.title == 'message From passenger') {
// passengerDialog(message.notification!.body!);
if (Platform.isAndroid) { if (Platform.isAndroid) {
NotificationController() notificationController.showNotification(
.showNotification('message From passenger'.tr, ''.tr, 'ding', ''); 'message From passenger'.tr, ''.tr, 'ding', '');
} }
MyDialog().getDialog( MyDialog().getDialog(
'message From passenger'.tr, message.notification!.body!, () { 'message From passenger'.tr, message.notification!.body!, () {
// FirebaseMessagesController().sendNotificationToPassengerToken(
// 'Hi ,I will go now'.tr,
// 'I will go now'.tr,
// Get.find<MapPassengerController>().driverToken, []);
// Get.find<MapPassengerController>()
// .startTimerDriverWaitPassenger5Minute();
Get.back(); Get.back();
}); });
} else if (message.notification!.title == 'Cancel') { } else if (message.notification!.title == 'Cancel') {
if (Platform.isAndroid) { if (Platform.isAndroid) {
NotificationController() notificationController.showNotification(
.showNotification('Cancel'.tr, ''.tr, 'cancel', ''); 'Cancel'.tr, ''.tr, 'cancel', '');
} }
MyDialog().getDialog( MyDialog().getDialog(
'Passenger Cancel Trip'.tr, 'Passenger Cancel Trip'.tr,
@@ -192,14 +183,14 @@ class FirebaseMessagesController extends GetxController {
}); });
// cancelTripDialog1(); // cancelTripDialog1();
} else if (message.notification!.title! == 'token change') { } else if (message.notification!.title! == 'token change') {
// NotificationController1() // notificationController
// .showNotification('token change'.tr, 'token change', 'cancel'); // .showNotification('token change'.tr, 'token change', 'cancel');
// GoogleSignInHelper.signOut(); // GoogleSignInHelper.signOut();
GoogleSignInHelper.signOut(); GoogleSignInHelper.signOut();
} else if (message.notification!.title! == 'face detect') { } else if (message.notification!.title! == 'face detect') {
if (Platform.isAndroid) { if (Platform.isAndroid) {
NotificationController() notificationController.showNotification(
.showNotification('face detect'.tr, ''.tr, 'tone2', ''); 'face detect'.tr, ''.tr, 'tone2', '');
} }
String result0 = await faceDetector(); String result0 = await faceDetector();
// Handle the result here, e.g., show a dialog or update the UI // Handle the result here, e.g., show a dialog or update the UI
@@ -220,7 +211,7 @@ class FirebaseMessagesController extends GetxController {
// Get.snackbar('Hi ,I will go now', '', // Get.snackbar('Hi ,I will go now', '',
// backgroundColor: AppColor.greenColor); // backgroundColor: AppColor.greenColor);
if (Platform.isAndroid) { if (Platform.isAndroid) {
NotificationController1().showNotification( notificationController.showNotification(
'Passenger come to you'.tr, 'Hi ,I will go now'.tr, 'tone2', ''); 'Passenger come to you'.tr, 'Hi ,I will go now'.tr, 'tone2', '');
} }
update(); update();
@@ -230,7 +221,7 @@ class FirebaseMessagesController extends GetxController {
var driverList = jsonDecode(myListString) as List<dynamic>; var driverList = jsonDecode(myListString) as List<dynamic>;
// if (Platform.isAndroid) { // if (Platform.isAndroid) {
if (Platform.isAndroid) { if (Platform.isAndroid) {
NotificationController1().showNotification('Call Income'.tr, notificationController.showNotification('Call Income'.tr,
message.notification!.body!, 'iphone_ringtone', ''); message.notification!.body!, 'iphone_ringtone', '');
} }
// } // }
@@ -248,7 +239,7 @@ class FirebaseMessagesController extends GetxController {
var driverList = jsonDecode(myListString) as List<dynamic>; var driverList = jsonDecode(myListString) as List<dynamic>;
// if (Platform.isAndroid) { // if (Platform.isAndroid) {
if (Platform.isAndroid) { if (Platform.isAndroid) {
NotificationController1().showNotification('Call Income'.tr, notificationController.showNotification('Call Income'.tr,
message.notification!.body!, 'iphone_ringtone', ''); message.notification!.body!, 'iphone_ringtone', '');
} }
// } // }
@@ -262,11 +253,8 @@ class FirebaseMessagesController extends GetxController {
} else if (message.notification!.title! == } else if (message.notification!.title! ==
"Criminal Document Required".tr) { "Criminal Document Required".tr) {
if (Platform.isAndroid) { if (Platform.isAndroid) {
NotificationController1().showNotification( notificationController.showNotification("Criminal Document Required".tr,
"Criminal Document Required".tr, message.notification!.body!, 'tone2', '');
message.notification!.body!,
'tone2',
'');
} }
MyDialog().getDialog( MyDialog().getDialog(
"Criminal Document Required".tr, 'You should have upload it .'.tr, "Criminal Document Required".tr, 'You should have upload it .'.tr,
@@ -279,7 +267,7 @@ class FirebaseMessagesController extends GetxController {
var myListString = message.data['passengerList']; var myListString = message.data['passengerList'];
var driverList = jsonDecode(myListString) as List<dynamic>; var driverList = jsonDecode(myListString) as List<dynamic>;
if (Platform.isAndroid) { if (Platform.isAndroid) {
NotificationController1().showNotification( notificationController.showNotification(
'Call End'.tr, message.notification!.body!, 'tone2', ''); 'Call End'.tr, message.notification!.body!, 'tone2', '');
} }
// Assuming GetMaterialApp is initialized and context is valid for navigation // Assuming GetMaterialApp is initialized and context is valid for navigation
@@ -296,7 +284,7 @@ class FirebaseMessagesController extends GetxController {
); );
} else if (message.notification!.title! == 'Order') { } else if (message.notification!.title! == 'Order') {
if (Platform.isAndroid) { if (Platform.isAndroid) {
NotificationController().showNotification( notificationController.showNotification(
message.notification!.title.toString(), message.notification!.title.toString(),
message.notification!.body.toString(), message.notification!.body.toString(),
'order', 'order',
@@ -318,7 +306,7 @@ class FirebaseMessagesController extends GetxController {
}); });
} else if (message.notification!.title! == 'Order Applied'.tr) { } else if (message.notification!.title! == 'Order Applied'.tr) {
if (Platform.isAndroid) { if (Platform.isAndroid) {
NotificationController1().showNotification( notificationController.showNotification(
'The order Accepted by another Driver'.tr, 'The order Accepted by another Driver'.tr,
'We regret to inform you that another driver has accepted this order.' 'We regret to inform you that another driver has accepted this order.'
.tr, .tr,
@@ -761,98 +749,6 @@ class FirebaseMessagesController extends GetxController {
} }
} }
void sendNotificationToAnyWithoutData(
String title, String body, String token, String tone,
{int retryCount = 2}) async {
try {
String serviceAccountKeyJson = '''{
"type": "service_account",
"project_id": "ride-b1bd8",
"private_key_id": "75e817c0b902db2ef35edf2c2bd159dec1f13249",
"private_key": "-----BEGIN PRIVATE KEY-----\\nMIIEvQIBADANBgkqhkiG9w0BAQEFAASCBKcwggSjAgEAAoIBAQD0zH9TQGDQHUv3\\na3/JAD1UKPwAp3wNKT0a6fxiIzjI3JxQWI30QvZCcfl6CdMhIcydX1ncSaYTcEeC\\n/AdPVCPkqyJx1YIGGg6P/mRzCWeaN8fsp6z250m5vcObDCZc3dbJEkepbep+6FPY\\n21m3KO+AHh1glgsTGZOTm5xiU8NGXpdk2QEh8wpiIIlR/HuKwVw9g8urNe3Sno+U\\nDm3z37iFqvZdmpqO8aWTJu6beb3hsREK9XK2I9JqC2JUwiGQRo3idOvPP6hkqrWx\\nKSX96vglQFYfakvJdDp2ZATOlpBYPMtS/IWhJ985u58TSS+Kl8qpnpaZBSxgJirf\\nhWzhnKLfAgMBAAECggEAJP785SePGhS7ZN6ltspm+l+hSjYFrPWFCxq+rlQ1YkHZ\\nC9l+RqKSFhOkiPmQI2s4wbXl3kFxLHHlFNoi/q2wKQBmGb8TQfnRJpjjNHGA61Ev\\n0Ue7/6qPvVb9B2MsLw/FxKiTFPuMG3bgKR9pbSFuJLYoaW7zqITOhVnYphGTqwAY\\nBVVcvISSLvELDmH9VZcv/9DVqVlqbbESHWh1Z4W6XGPoEqeDH/upNTyQQ/46Msgm\\nTGE6VqLHpWuSf6SqHp+r0Y0lI3vIPM1vz5FAJDJbOE/enHa0fSup0OHSMxl0HVMn\\nnO1yrGF3vsIPOej5HKr5d71bEIckzk73/yjNC1/mDQKBgQD7RtUvc9omsSsFMJ6e\\nBASAn6Dktx/QY/XNJjFzHQj69cywLDe5t5AL2gUi3phQ2oqB5XJdwnd5bTIEPEPZ\\nDOuOai2802p6FJk6kjmZAMVGx5JtXBH+vs6jrmQQSMiKbjwN1TT6xIWakvLOonUi\\nX6ZvjYYjU/E0YJU3jSiXWEr76wKBgQD5Zn4SouJ6BCDZMbausJVMBkk3qxsYooip\\np89WakC6e7AZinpkRcqjGGV9GOvc8crJs6fyXAA9ORepGP47Mc0ZrDssOkstznsM\\npr8R0S6MKwEZaT9ixOHdOcLZ47ps+JzA2Wr4KN2OvFHksUkB/46ATD1j9WZVgB8M\\namsYp/Y73QKBgHOo+PvsoZ9psVmkNX6abtAdqdtdB0HOoRea2uwXk0ig12TIFaZg\\nfedWpUKVnxqoXVTJHklV99RmlL0qWDiSH+LfsMnXro0e6iDxqZ1po2Se/CFmXcoa\\nXdctsFVmixhdATuExewfhTfPKABA+xWlXWC/jdy5CK+JPWXijaqMM4edAoGAE5Bj\\nsWiPpYyvWvpYX0nA3G7dzX0hqgQN/mkIjbnWDArp3IcNZNJIvBSM2Yxb7EAXbU0n\\njo6DAkp5Pa2VO+WDNlFZbvW/sf8xjeOCt44WPa6d7nVgIIpbQXRngZoopKW3/jTP\\n/FmQT8McFXmGxZ5belsAsdetSGW9icbLUerTGQ0CgYEAmf/G8Ag3XxmqTXvvHuv2\\n14OP7WnrVqkEMnydrftEwn4peXd/Lz+/GYX5Zc4ZoNgbN8IvZ5z0+OmRsallsbiW\\nBw0/tc68CjzxXOvReWxDluUopqWVGj5tlGqE5xUDku9SWJSxbkiQ3rqutzBdPXpr\\noqHwPyDrmK/Zgqn+uiIm4Ck=\\n-----END PRIVATE KEY-----\\n",
"client_email": "firebase-adminsdk-o2wqi@ride-b1bd8.iam.gserviceaccount.com",
"client_id": "111210077025005706623",
"auth_uri": "https://accounts.google.com/o/oauth2/auth",
"token_uri": "https://oauth2.googleapis.com/token",
"auth_provider_x509_cert_url": "https://www.googleapis.com/oauth2/v1/certs",
"client_x509_cert_url": "https://www.googleapis.com/robot/v1/metadata/x509/firebase-adminsdk-o2wqi%40ride-b1bd8.iam.gserviceaccount.com",
"universe_domain": "googleapis.com"
}
'''; // As defined above
// Initialize AccessTokenManager
final accessTokenManager = AccessTokenManager(serviceAccountKeyJson);
// Obtain an OAuth 2.0 access token
final accessToken = await accessTokenManager.getAccessToken();
// Send the notification
final response = await http.post(
Uri.parse(
'https://fcm.googleapis.com/v1/projects/ride-b1bd8/messages:send'),
headers: <String, String>{
'Content-Type': 'application/json',
'Authorization': 'Bearer $accessToken',
},
body: jsonEncode({
'message': {
'token': token,
'notification': {
'title': title,
'body': body,
},
// 'data': {
// 'DriverList': jsonEncode([]),
// },
'android': {
'priority': 'high', // Set priority to high
'notification': {
'sound': tone,
},
},
'apns': {
'headers': {
'apns-priority': '10', // Set APNs priority to 10
},
'payload': {
'aps': {
'sound': tone,
},
},
},
},
}),
);
if (response.statusCode == 200) {
print(
'Notification sent successfully. Status code: ${response.statusCode}');
print('Response body: ${response.body}');
} else {
print(
'Failed to send notification. Status code: ${response.statusCode}');
print('Response body: ${response.body}');
if (retryCount > 0) {
print('Retrying... Attempts remaining: $retryCount');
await Future.delayed(
const Duration(seconds: 2)); // Optional delay before retrying
return sendNotificationToAnyWithoutData(title, body, token, tone,
retryCount: retryCount - 1);
}
}
} catch (e) {
print('Error sending notification: $e');
if (retryCount > 0) {
print('Retrying... Attempts remaining: $retryCount');
await Future.delayed(
const Duration(seconds: 2)); // Optional delay before retrying
return sendNotificationToAnyWithoutData(title, body, token, tone,
retryCount: retryCount - 1);
}
}
}
void sendNotificationToDriverMAP( void sendNotificationToDriverMAP(
String title, String body, String token, List<String> data, String tone, String title, String body, String token, List<String> data, String tone,
{int retryCount = 2}) async { {int retryCount = 2}) async {
@@ -946,79 +842,6 @@ class FirebaseMessagesController extends GetxController {
} }
} }
} }
void sendNotificationToDriverMapPolyline(String title, String body,
String token, List<String> data, String polylineJson, String tone) async {
try {
String serviceAccountKeyJson = '''{
"type": "service_account",
"project_id": "ride-b1bd8",
"private_key_id": "75e817c0b902db2ef35edf2c2bd159dec1f13249",
"private_key": "-----BEGIN PRIVATE KEY-----\\nMIIEvQIBADANBgkqhkiG9w0BAQEFAASCBKcwggSjAgEAAoIBAQD0zH9TQGDQHUv3\\na3/JAD1UKPwAp3wNKT0a6fxiIzjI3JxQWI30QvZCcfl6CdMhIcydX1ncSaYTcEeC\\n/AdPVCPkqyJx1YIGGg6P/mRzCWeaN8fsp6z250m5vcObDCZc3dbJEkepbep+6FPY\\n21m3KO+AHh1glgsTGZOTm5xiU8NGXpdk2QEh8wpiIIlR/HuKwVw9g8urNe3Sno+U\\nDm3z37iFqvZdmpqO8aWTJu6beb3hsREK9XK2I9JqC2JUwiGQRo3idOvPP6hkqrWx\\nKSX96vglQFYfakvJdDp2ZATOlpBYPMtS/IWhJ985u58TSS+Kl8qpnpaZBSxgJirf\\nhWzhnKLfAgMBAAECggEAJP785SePGhS7ZN6ltspm+l+hSjYFrPWFCxq+rlQ1YkHZ\\nC9l+RqKSFhOkiPmQI2s4wbXl3kFxLHHlFNoi/q2wKQBmGb8TQfnRJpjjNHGA61Ev\\n0Ue7/6qPvVb9B2MsLw/FxKiTFPuMG3bgKR9pbSFuJLYoaW7zqITOhVnYphGTqwAY\\nBVVcvISSLvELDmH9VZcv/9DVqVlqbbESHWh1Z4W6XGPoEqeDH/upNTyQQ/46Msgm\\nTGE6VqLHpWuSf6SqHp+r0Y0lI3vIPM1vz5FAJDJbOE/enHa0fSup0OHSMxl0HVMn\\nnO1yrGF3vsIPOej5HKr5d71bEIckzk73/yjNC1/mDQKBgQD7RtUvc9omsSsFMJ6e\\nBASAn6Dktx/QY/XNJjFzHQj69cywLDe5t5AL2gUi3phQ2oqB5XJdwnd5bTIEPEPZ\\nDOuOai2802p6FJk6kjmZAMVGx5JtXBH+vs6jrmQQSMiKbjwN1TT6xIWakvLOonUi\\nX6ZvjYYjU/E0YJU3jSiXWEr76wKBgQD5Zn4SouJ6BCDZMbausJVMBkk3qxsYooip\\np89WakC6e7AZinpkRcqjGGV9GOvc8crJs6fyXAA9ORepGP47Mc0ZrDssOkstznsM\\npr8R0S6MKwEZaT9ixOHdOcLZ47ps+JzA2Wr4KN2OvFHksUkB/46ATD1j9WZVgB8M\\namsYp/Y73QKBgHOo+PvsoZ9psVmkNX6abtAdqdtdB0HOoRea2uwXk0ig12TIFaZg\\nfedWpUKVnxqoXVTJHklV99RmlL0qWDiSH+LfsMnXro0e6iDxqZ1po2Se/CFmXcoa\\nXdctsFVmixhdATuExewfhTfPKABA+xWlXWC/jdy5CK+JPWXijaqMM4edAoGAE5Bj\\nsWiPpYyvWvpYX0nA3G7dzX0hqgQN/mkIjbnWDArp3IcNZNJIvBSM2Yxb7EAXbU0n\\njo6DAkp5Pa2VO+WDNlFZbvW/sf8xjeOCt44WPa6d7nVgIIpbQXRngZoopKW3/jTP\\n/FmQT8McFXmGxZ5belsAsdetSGW9icbLUerTGQ0CgYEAmf/G8Ag3XxmqTXvvHuv2\\n14OP7WnrVqkEMnydrftEwn4peXd/Lz+/GYX5Zc4ZoNgbN8IvZ5z0+OmRsallsbiW\\nBw0/tc68CjzxXOvReWxDluUopqWVGj5tlGqE5xUDku9SWJSxbkiQ3rqutzBdPXpr\\noqHwPyDrmK/Zgqn+uiIm4Ck=\\n-----END PRIVATE KEY-----\\n",
"client_email": "firebase-adminsdk-o2wqi@ride-b1bd8.iam.gserviceaccount.com",
"client_id": "111210077025005706623",
"auth_uri": "https://accounts.google.com/o/oauth2/auth",
"token_uri": "https://oauth2.googleapis.com/token",
"auth_provider_x509_cert_url": "https://www.googleapis.com/oauth2/v1/certs",
"client_x509_cert_url": "https://www.googleapis.com/robot/v1/metadata/x509/firebase-adminsdk-o2wqi%40ride-b1bd8.iam.gserviceaccount.com",
"universe_domain": "googleapis.com"
}
'''; // As defined above
// Initialize AccessTokenManager
final accessTokenManager = AccessTokenManager(serviceAccountKeyJson);
// Obtain an OAuth 2.0 access token
final accessToken = await accessTokenManager.getAccessToken();
// Send the notification
final response = await http.post(
Uri.parse(
'https://fcm.googleapis.com/v1/projects/ride-b1bd8/messages:send'),
headers: <String, String>{
'Content-Type': 'application/json',
'Authorization': 'Bearer $accessToken',
},
body: jsonEncode({
'message': {
'token': token,
'notification': {
'title': title,
'body': body,
},
'data': {
'DriverList': jsonEncode(data),
},
'android': {
'priority': 'high', // Set priority to high
'notification': {
'sound': tone,
},
},
'apns': {
'headers': {
'apns-priority': '10', // Set APNs priority to 10
},
'payload': {
'aps': {
'sound': tone,
},
},
},
},
}),
);
if (response.statusCode == 200) {
// Notification sent successfully
} else {
// Handle error response
'Failed to send notification. Status code: ${response.statusCode}';
}
} catch (e) {
// Handle other exceptions
}
}
} }
class OverlayContent extends StatelessWidget { class OverlayContent extends StatelessWidget {

View File

@@ -1,4 +1,6 @@
import 'dart:async';
import 'dart:convert'; import 'dart:convert';
import 'dart:io';
import 'dart:typed_data'; import 'dart:typed_data';
import 'package:SEFER/constant/colors.dart'; import 'package:SEFER/constant/colors.dart';
@@ -6,7 +8,11 @@ import 'package:SEFER/views/home/Captin/orderCaptin/order_request_page.dart';
import 'package:SEFER/views/home/Captin/orderCaptin/order_speed_request.dart'; import 'package:SEFER/views/home/Captin/orderCaptin/order_speed_request.dart';
import 'package:flutter_local_notifications/flutter_local_notifications.dart'; import 'package:flutter_local_notifications/flutter_local_notifications.dart';
import 'package:get/get.dart'; import 'package:get/get.dart';
import 'package:permission_handler/permission_handler.dart';
import 'package:timezone/data/latest.dart' as tz;
import 'package:timezone/timezone.dart' as tz;
import '../../constant/box_name.dart';
import '../../main.dart'; import '../../main.dart';
import '../../print.dart'; import '../../print.dart';
import '../../views/notification/notification_captain.dart'; import '../../views/notification/notification_captain.dart';
@@ -19,10 +25,17 @@ class NotificationController extends GetxController {
Future<void> initNotifications() async { Future<void> initNotifications() async {
const AndroidInitializationSettings android = const AndroidInitializationSettings android =
AndroidInitializationSettings('@mipmap/launcher_icon'); AndroidInitializationSettings('@mipmap/launcher_icon');
DarwinInitializationSettings ios = DarwinInitializationSettings(
const InitializationSettings initializationSettings = requestAlertPermission: true,
InitializationSettings(android: android); requestBadgePermission: true,
requestSoundPermission: true,
onDidReceiveLocalNotification:
(int id, String? title, String? body, String? payload) async {},
);
InitializationSettings initializationSettings =
InitializationSettings(android: android, iOS: ios);
tz.initializeTimeZones();
print('Notifications initialized');
await _flutterLocalNotificationsPlugin.initialize( await _flutterLocalNotificationsPlugin.initialize(
initializationSettings, initializationSettings,
onDidReceiveNotificationResponse: onDidReceiveNotificationResponse, onDidReceiveNotificationResponse: onDidReceiveNotificationResponse,
@@ -85,13 +98,266 @@ class NotificationController extends GetxController {
], ],
category: AndroidNotificationCategory.progress, category: AndroidNotificationCategory.progress,
); );
DarwinNotificationDetails ios = const DarwinNotificationDetails(
NotificationDetails details = NotificationDetails(android: android); sound: 'default',
presentAlert: true,
presentBadge: true,
presentSound: true,
);
NotificationDetails details =
NotificationDetails(android: android, iOS: ios);
await _flutterLocalNotificationsPlugin.show(0, title, message, details, await _flutterLocalNotificationsPlugin.show(0, title, message, details,
payload: jsonEncode({'title': title, 'data': payLoad})); payload: jsonEncode({'title': title, 'data': payLoad}));
} }
void scheduleNotificationAtSpecificTime(
String title, String message, String tone, int hour, int minute) async {
// Initialize and set Cairo time zone
tz.initializeTimeZones();
var cairoLocation;
if (box.read(BoxName.countryCode).toString() == 'Egypt') {
cairoLocation = tz.getLocation('Africa/Cairo');
} else {} // todo get for location country
final AndroidNotificationDetails android = AndroidNotificationDetails(
'high_importance_channel',
'High Importance Notifications',
importance: Importance.max,
priority: Priority.high,
showWhen: false,
sound: RawResourceAndroidNotificationSound(tone),
);
const DarwinNotificationDetails ios = DarwinNotificationDetails(
sound: 'default',
presentAlert: true,
presentBadge: true,
presentSound: true,
);
final NotificationDetails details =
NotificationDetails(android: android, iOS: ios);
final now =
tz.TZDateTime.now(cairoLocation); // Use Cairo timezone for current time
tz.TZDateTime scheduledTime = tz.TZDateTime(
cairoLocation, now.year, now.month, now.day, hour, minute);
// If the scheduled time has already passed for today, schedule it for the next day
if (scheduledTime.isBefore(now)) {
scheduledTime = scheduledTime.add(const Duration(days: 1));
}
if (Platform.isAndroid) {
if (await Permission.scheduleExactAlarm.isDenied) {
if (await Permission.scheduleExactAlarm.request().isGranted) {
print('SCHEDULE_EXACT_ALARM permission granted');
} else {
print('SCHEDULE_EXACT_ALARM permission denied');
return;
}
}
}
print('Current time: $now');
print('Scheduling notification for: $scheduledTime');
await _flutterLocalNotificationsPlugin.zonedSchedule(
0,
title,
message,
scheduledTime,
details,
androidAllowWhileIdle: true,
uiLocalNotificationDateInterpretation:
UILocalNotificationDateInterpretation.absoluteTime,
matchDateTimeComponents:
DateTimeComponents.time, // Triggers daily at the same time
);
print('Notification scheduled successfully');
}
void scheduleNotificationAfter1Minute(
String title, String message, String tone) async {
final AndroidNotificationDetails android = AndroidNotificationDetails(
'high_importance_channel',
'High Importance Notifications',
importance: Importance.max,
priority: Priority.high,
showWhen: false,
sound: RawResourceAndroidNotificationSound(tone),
);
const DarwinNotificationDetails ios = DarwinNotificationDetails(
sound: 'default',
presentAlert: true,
presentBadge: true,
presentSound: true,
);
final NotificationDetails details =
NotificationDetails(android: android, iOS: ios);
// Schedule the notification to be shown after 1 minute
Timer.periodic(const Duration(seconds: 15), (timer) async {
final now = tz.TZDateTime.now(tz.local);
final scheduledTime = now.add(const Duration(seconds: 10));
Log.print('scheduledTime: ${scheduledTime}');
if (Platform.isAndroid) {
if (await Permission.scheduleExactAlarm.isDenied) {
if (await Permission.scheduleExactAlarm.request().isGranted) {
print('SCHEDULE_EXACT_ALARM permission granted');
} else {
print('SCHEDULE_EXACT_ALARM permission denied');
return;
}
}
}
print('Scheduling notification for: $scheduledTime');
await _flutterLocalNotificationsPlugin.zonedSchedule(
0,
title,
message,
scheduledTime,
details,
androidAllowWhileIdle: true,
uiLocalNotificationDateInterpretation:
UILocalNotificationDateInterpretation.absoluteTime,
matchDateTimeComponents: DateTimeComponents.time,
);
print('Notification scheduled successfully');
});
}
void scheduleDailyNotifications(
String title, String message, String tone) async {
final AndroidNotificationDetails android = AndroidNotificationDetails(
'high_importance_channel',
'High Importance Notifications',
importance: Importance.max,
priority: Priority.high,
sound: RawResourceAndroidNotificationSound(tone),
);
const DarwinNotificationDetails ios = DarwinNotificationDetails(
sound: 'default',
presentAlert: true,
presentBadge: true,
presentSound: true,
);
final NotificationDetails details =
NotificationDetails(android: android, iOS: ios);
// Check for the exact alarm permission on Android 12 and above
if (Platform.isAndroid) {
if (await Permission.scheduleExactAlarm.isDenied) {
if (await Permission.scheduleExactAlarm.request().isGranted) {
print('SCHEDULE_EXACT_ALARM permission granted');
} else {
print('SCHEDULE_EXACT_ALARM permission denied');
return;
}
}
}
// Schedule notifications for 10:00 AM and 3:00 PM daily
await _scheduleNotificationForTime(7, 0, title, message, details);
await _scheduleNotificationForTime(13, 0, title, message, details);
await _scheduleNotificationForTime(18, 0, title, message, details);
// await _scheduleNotificationForTime(0, 22, title, message, details);
print('Daily notifications scheduled successfully');
}
// Helper function to get the next instance of a specific hour and minute
Future<void> _scheduleNotificationForTime(int hour, int minute, String title,
String message, NotificationDetails details) async {
// Initialize and set Cairo timezone
tz.initializeTimeZones();
final cairoLocation = tz.getLocation('Africa/Cairo'); // Set Cairo timezone
final now = tz.TZDateTime.now(
cairoLocation); // Use Cairo timezone for the current time
tz.TZDateTime scheduledDate = tz.TZDateTime(
cairoLocation, now.year, now.month, now.day, hour, minute);
// If scheduled time is already past today, schedule it for the next day
if (scheduledDate.isBefore(now)) {
scheduledDate = scheduledDate.add(const Duration(days: 1));
}
print('Current time (Cairo): $now');
print('Scheduling notification for: $scheduledDate');
await _flutterLocalNotificationsPlugin.zonedSchedule(
0, // Use unique IDs if you want to manage each notification separately
title,
message,
scheduledDate,
details,
androidAllowWhileIdle: true,
uiLocalNotificationDateInterpretation:
UILocalNotificationDateInterpretation.absoluteTime,
matchDateTimeComponents: DateTimeComponents.time,
);
print('Notification scheduled successfully for Cairo timezone');
}
void scheduleNotificationEvery10Hours(
String title, String message, String tone) async {
final AndroidNotificationDetails android = AndroidNotificationDetails(
'high_importance_channel',
'High Importance Notifications',
importance: Importance.max,
priority: Priority.high,
showWhen: false,
sound: RawResourceAndroidNotificationSound(tone),
);
const DarwinNotificationDetails ios = DarwinNotificationDetails(
sound: 'default',
presentAlert: true,
presentBadge: true,
presentSound: true,
);
final NotificationDetails details =
NotificationDetails(android: android, iOS: ios);
if (Platform.isAndroid) {
if (await Permission.scheduleExactAlarm.isDenied) {
if (await Permission.scheduleExactAlarm.request().isGranted) {
print('SCHEDULE_EXACT_ALARM permission granted');
} else {
print('SCHEDULE_EXACT_ALARM permission denied');
return;
}
}
}
Timer.periodic(const Duration(hours: 10), (timer) async {
final now = tz.TZDateTime.now(tz.local);
final scheduledTime = now.add(const Duration(minutes: 10));
print('Scheduling notification for: $scheduledTime');
await _flutterLocalNotificationsPlugin.zonedSchedule(
0,
title.tr,
message.tr,
scheduledTime,
details,
androidAllowWhileIdle: true,
uiLocalNotificationDateInterpretation:
UILocalNotificationDateInterpretation.absoluteTime,
matchDateTimeComponents: DateTimeComponents.time,
);
});
print('Notifications scheduled every 5 seconds');
}
// Callback when the notification is tapped // Callback when the notification is tapped
void onDidReceiveNotificationResponse(NotificationResponse response) { void onDidReceiveNotificationResponse(NotificationResponse response) {
handleNotificationResponse(response); handleNotificationResponse(response);

View File

@@ -626,6 +626,51 @@ class AI extends GetxController {
} }
} }
Future<void> allMethodForAINewCar(
String prompt, String linkPHP, String imagePath, String carID) async {
isLoading = true;
update();
try {
await ImageController().choosImageNewCAr(linkPHP, imagePath);
// if (imagePath == 'driver_license') {
// await ImageController().choosFaceFromDriverLicense(linkPHP, 'face');
// }
await Future.delayed(const Duration(seconds: 2));
var extractedString =
await CRUD().arabicTextExtractByVisionAndAI(imagePath: imagePath);
var json = jsonDecode(extractedString);
var textValues = CRUD().extractTextFromLines(json);
DocumentType detectedType = checkDocumentType(textValues);
String expectedDocument = getExpectedDocument(imagePath);
String detectedDocument = getDetectedDocument(detectedType);
bool isCorrectDocument = (detectedType == getExpectedType(imagePath));
if (!isCorrectDocument) {
MyDialog().getDialog('incorrect_document_title'.tr,
'${'expected'.tr}: $expectedDocument\n${'detected'.tr}: $detectedDocument',
() {
Get.back();
});
} else {
// Process the correct document
await Get.put(AI()).anthropicAI(textValues, prompt, imagePath);
}
} catch (e) {
MyDialog().getDialog('error'.tr, 'error_processing_document'.tr, () {
Get.back();
});
} finally {
isLoading = false;
update();
}
}
String getExpectedDocument(String imagePath) { String getExpectedDocument(String imagePath) {
switch (imagePath) { switch (imagePath) {
case 'car_front': case 'car_front':

View File

@@ -30,8 +30,8 @@ class SmsEgyptController extends GetxController {
Future<dynamic> sendSmsEgypt(String phone, otp) async { Future<dynamic> sendSmsEgypt(String phone, otp) async {
String sender = await getSender(); String sender = await getSender();
var body = jsonEncode({ var body = jsonEncode({
"username": AppInformation.appName, "username": 'Sefer',
"password": AK.smsPasswordEgypt, //'E)Pu=an/@Z', "password": AK.smsPasswordEgypt,
"message": "${AppInformation.appName} app code is $otp\ncopy it to app", "message": "${AppInformation.appName} app code is $otp\ncopy it to app",
"language": box.read(BoxName.lang) == 'en' ? "e" : 'r', "language": box.read(BoxName.lang) == 'en' ? "e" : 'r',
"sender": sender, //"Sefer Egy", // todo add sefer sender name "sender": sender, //"Sefer Egy", // todo add sefer sender name

View File

@@ -139,8 +139,8 @@ class ImageController extends GetxController {
File compressedImage = await compressImage(processedImage); File compressedImage = await compressImage(processedImage);
print('link =$link'); print('link =$link');
Log.print('link: ${link}'); // Log.print('link: ${link}');
//n8u22456
await uploadImage( await uploadImage(
compressedImage, compressedImage,
{ {
@@ -160,6 +160,65 @@ class ImageController extends GetxController {
} }
} }
choosImageNewCAr(String link, String imageType) async {
try {
final pickedImage = await picker.pickImage(
source: ImageSource.camera,
preferredCameraDevice: CameraDevice.rear,
);
if (pickedImage == null) return;
image = File(pickedImage.path);
croppedFile = await ImageCropper().cropImage(
sourcePath: image!.path,
uiSettings: [
AndroidUiSettings(
toolbarTitle: 'Cropper'.tr,
toolbarColor: AppColor.blueColor,
toolbarWidgetColor: AppColor.yellowColor,
initAspectRatio: CropAspectRatioPreset.original,
lockAspectRatio: false,
),
IOSUiSettings(
title: 'Cropper'.tr,
),
],
);
if (croppedFile == null) return;
myImage = File(croppedFile!.path);
isloading = true;
update();
// Rotate the compressed image
File processedImage = await rotateImageIfNeeded(File(croppedFile!.path));
File compressedImage = await compressImage(processedImage);
print('link =$link');
// Log.print('link: ${link}');
//n8u22456
await uploadNewCar(
compressedImage,
{
'driverID':
box.read(BoxName.driverID) ?? box.read(BoxName.passengerID),
'imageType': imageType,
},
link,
);
} catch (e) {
print('Error in choosImage: $e');
Get.snackbar('Image Upload Failed'.tr, e.toString(),
backgroundColor: AppColor.primaryColor);
} finally {
isloading = false;
update();
}
}
// choosFaceFromDriverLicense(String link, String imageType) async { // choosFaceFromDriverLicense(String link, String imageType) async {
// final pickedImage = await picker.pickImage( // final pickedImage = await picker.pickImage(
// source: ImageSource.camera, // source: ImageSource.camera,
@@ -278,6 +337,47 @@ class ImageController extends GetxController {
} }
} }
uploadNewCar(File file, Map data, String link) async {
var request = http.MultipartRequest(
'POST',
Uri.parse(link),
);
var length = await file.length();
var stream = http.ByteStream(file.openRead());
var multipartFile = http.MultipartFile(
'image',
stream,
length,
filename: basename(file.path),
);
request.headers.addAll({
'Authorization':
'Basic ${base64Encode(utf8.encode(AK.basicAuthCredentials.toString()))}',
});
// Set the file name to the driverID
request.files.add(
http.MultipartFile(
'image',
stream,
length,
filename: '${box.read(BoxName.driverID)}.jpg',
),
);
data.forEach((key, value) {
request.fields[key] = value;
});
var myrequest = await request.send();
var res = await http.Response.fromStream(myrequest);
if (res.statusCode == 200) {
Log.print('jsonDecode(res.body): ${jsonDecode(res.body)}');
return jsonDecode(res.body);
} else {
throw Exception(
'Failed to upload image: ${res.statusCode} - ${res.body}');
}
}
choosImagePicture(String link, String imageType) async { choosImagePicture(String link, String imageType) async {
final pickedImage = await picker.pickImage( final pickedImage = await picker.pickImage(
source: ImageSource.gallery, source: ImageSource.gallery,

View File

@@ -300,10 +300,11 @@ class MapDriverController extends GetxController {
} }
// Get.find<HomeCaptainController>().changeToAppliedRide('Applied'); // Get.find<HomeCaptainController>().changeToAppliedRide('Applied');
FirebaseMessagesController().sendNotificationToAnyWithoutData( FirebaseMessagesController().sendNotificationToDriverMAP(
'DriverIsGoingToPassenger', 'DriverIsGoingToPassenger',
box.read(BoxName.name).toString(), box.read(BoxName.name).toString(),
tokenPassenger, tokenPassenger,
[],
'start.wav'); 'start.wav');
} }
@@ -390,11 +391,8 @@ class MapDriverController extends GetxController {
'status': 'Begin', 'status': 'Begin',
}); });
} }
FirebaseMessagesController().sendNotificationToAnyWithoutData( FirebaseMessagesController().sendNotificationToDriverMAP('RideIsBegin',
'RideIsBegin', box.read(BoxName.name).toString(), tokenPassenger, [], 'start.wav');
box.read(BoxName.name).toString(),
tokenPassenger,
'start.wav');
rideIsBeginPassengerTimer(); rideIsBeginPassengerTimer();
// var d = jsonDecode(res); // var d = jsonDecode(res);
@@ -673,7 +671,7 @@ class MapDriverController extends GetxController {
'driverID': box.read(BoxName.driverID).toString(), 'driverID': box.read(BoxName.driverID).toString(),
}); });
Future.delayed(const Duration(milliseconds: 300)); Future.delayed(const Duration(milliseconds: 300));
FirebaseMessagesController().sendNotificationToPassengerToken( FirebaseMessagesController().sendNotificationToDriverMAP(
'Driver Finish Trip', 'Driver Finish Trip',
'${'you will pay to Driver'.tr} $paymentAmount \$', '${'you will pay to Driver'.tr} $paymentAmount \$',
tokenPassenger, tokenPassenger,

View File

@@ -196,14 +196,22 @@ class MyTranslation extends Translations {
"Total Earnings": "إجمالي الأرباح", "Total Earnings": "إجمالي الأرباح",
"Choose from contact": "اختر من جهات الاتصال", "Choose from contact": "اختر من جهات الاتصال",
"Cancel": "إلغاء", "Cancel": "إلغاء",
"Open App": "افتح التطبيق",
"Add new car": "أضف سيارة جديدة",
"Open the app to stay updated and ready for upcoming tasks.":
"افتح التطبيق لتبقى على اطلاع واستعداد للمهام القادمة.",
"No invitation found": "لم يتم العثور على دعوة", "No invitation found": "لم يتم العثور على دعوة",
'You are not near the passenger location': 'You are not near the passenger location':
"أنت لست بالقرب من موقع الراكب", "أنت لست بالقرب من موقع الراكب",
'Please upload this license.': "يرجى تحميل هذه الرخصة.",
'If your car license has the new design, upload the front side with two images.':
"إذا كانت رخصة سيارتك ذات التصميم الجديد، يرجى تحميل الوجه الأمامي بصورتين.",
'If you need assistance, contact us': 'If you need assistance, contact us':
"إذا كنت بحاجة إلى المساعدة، تواصل معنا", "إذا كنت بحاجة إلى المساعدة، تواصل معنا",
'You Can Cancel the Trip and get Cost From ': 'You Can Cancel the Trip and get Cost From ':
"يمكنك إلغاء الرحلة والحصول على التكلفة من", "يمكنك إلغاء الرحلة والحصول على التكلفة من",
'Please make sure to read the license carefully.':
"يرجى التأكد من قراءة الرخصة بعناية",
'Videos Tutorials': "فيديوهات تعليمية", 'Videos Tutorials': "فيديوهات تعليمية",
'Please go to the pickup location exactly': 'Please go to the pickup location exactly':
"يرجى الذهاب إلى موقع الالتقاط بالضبط", "يرجى الذهاب إلى موقع الالتقاط بالضبط",

View File

@@ -87,10 +87,11 @@ class RateController extends GetxController {
// 'token': paymentToken4, // 'token': paymentToken4,
// 'driverID': box.read(BoxName.driverID).toString(), // 'driverID': box.read(BoxName.driverID).toString(),
// }); // });
FirebaseMessagesController().sendNotificationToAnyWithoutData( FirebaseMessagesController().sendNotificationToDriverMAP(
'Wallet Added'.tr, 'Wallet Added'.tr,
'Wallet Added${(remainingFee).toStringAsFixed(0)}'.tr, 'Wallet Added${(remainingFee).toStringAsFixed(0)}'.tr,
Get.find<MapDriverController>().tokenPassenger, Get.find<MapDriverController>().tokenPassenger,
[],
'tone2.wav'); 'tone2.wav');
walletChecked = 'true'; walletChecked = 'true';
// } // }

View File

@@ -1,6 +1,7 @@
import 'dart:async'; import 'dart:async';
import 'dart:convert'; import 'dart:convert';
import 'dart:io'; import 'dart:io';
import 'dart:math';
import 'package:SEFER/constant/box_name.dart'; import 'package:SEFER/constant/box_name.dart';
import 'package:SEFER/controller/payment/paymob/paymob_response.dart'; import 'package:SEFER/controller/payment/paymob/paymob_response.dart';
import 'package:SEFER/views/home/Captin/orderCaptin/order_request_page.dart'; import 'package:SEFER/views/home/Captin/orderCaptin/order_request_page.dart';
@@ -18,6 +19,7 @@ import 'package:permission_handler/permission_handler.dart';
import 'package:wakelock_plus/wakelock_plus.dart'; import 'package:wakelock_plus/wakelock_plus.dart';
import 'constant/api_key.dart'; import 'constant/api_key.dart';
import 'constant/info.dart'; import 'constant/info.dart';
import 'constant/notification.dart';
import 'controller/firebase/firbase_messge.dart'; import 'controller/firebase/firbase_messge.dart';
import 'controller/firebase/local_notification.dart'; import 'controller/firebase/local_notification.dart';
import 'controller/functions/location_controller.dart'; import 'controller/functions/location_controller.dart';
@@ -58,14 +60,13 @@ Future<void> backgroundMessageHandler(RemoteMessage message) async {
Log.print('Error decoding JSON: $e'); Log.print('Error decoding JSON: $e');
myList = []; myList = [];
} }
await Future.delayed(const Duration(seconds: 1));
NotificationController().showNotification( NotificationController().showNotification(
message.notification!.title.toString(), message.notification!.title.toString(),
message.notification!.body.toString(), message.notification!.body.toString(),
'order', 'order',
myListString, myListString,
); );
await Future.delayed(const Duration(seconds: 1));
bool isOverlayActive = await FlutterOverlayWindow.isActive(); bool isOverlayActive = await FlutterOverlayWindow.isActive();
if (isOverlayActive) { if (isOverlayActive) {
@@ -137,9 +138,23 @@ void main() async {
FirebaseMessaging.onBackgroundMessage(backgroundMessageHandler); FirebaseMessaging.onBackgroundMessage(backgroundMessageHandler);
// NotificationController1().initNotifications(); // NotificationController1().initNotifications();
// NotificationController().initNotifications(); // NotificationController().initNotifications();
if (Platform.isAndroid) { // if (Platform.isAndroid) {
await Get.put(NotificationController()).initNotifications(); // await Get.put(NotificationController()).initNotifications();
} // }
NotificationController notificationController =
Get.put(NotificationController());
await notificationController.initNotifications();
// Generate a random index to pick a message
final random = Random();
final randomMessage = driverMessages[random.nextInt(driverMessages.length)];
// Schedule the notification with the random message
notificationController.scheduleDailyNotifications(
randomMessage.split(':')[0],
randomMessage.split(':')[1],
"ding",
);
await Future.wait([ await Future.wait([
FirebaseMessagesController().getNotificationSettings(), FirebaseMessagesController().getNotificationSettings(),

View File

@@ -0,0 +1,76 @@
import 'dart:convert';
import 'package:SEFER/constant/box_name.dart';
import 'package:SEFER/constant/colors.dart';
import 'package:SEFER/constant/links.dart';
import 'package:SEFER/controller/functions/crud.dart';
import 'package:SEFER/main.dart';
import 'package:get/get.dart';
class DriverCarController extends GetxController {
bool isLoading = false;
List cars = [];
int? carId;
fetchCatrsForDrivers() async {
isLoading = true;
update();
var res = await CRUD().get(link: AppLink.getNewCarsDrivers, payload: {
"driverID": box.read(BoxName.driverID).toString(),
});
if (res != 'failure') {
var d = jsonDecode(res)['message'];
cars = d;
carId = cars.isEmpty ? 1 : cars.length + 1;
}
isLoading = false;
update();
}
addCarsForDrivers(
String vin,
String car_plate,
String make,
String model,
String year,
String expiration_date,
String color,
String color_hex,
String address,
String owner,
String registration_date,
String displacement,
String fuel) async {
var res = await CRUD().post(
link: AppLink.addNewCarsDrivers,
payload: {
"driverID": box.read(BoxName.driverID).toString(),
"vin": vin,
"car_plate": car_plate,
"make": make,
"model": model,
"year": year,
"expiration_date": expiration_date,
"color": color,
"owner": owner,
"color_hex": color_hex,
"address": address,
"displacement": displacement,
"fuel": fuel,
"registration_date": registration_date,
},
);
if (res != 'failure') {
Get.snackbar('Success'.tr, '', backgroundColor: AppColor.greenColor);
fetchCatrsForDrivers();
} else {
Get.snackbar('Error'.tr, '', backgroundColor: AppColor.redColor);
}
}
removeCar(String car) async {}
@override
void onInit() {
fetchCatrsForDrivers();
super.onInit();
}
}

View File

@@ -98,7 +98,7 @@ class CupertinoDrawerCaptain extends StatelessWidget {
_buildDrawerItem( _buildDrawerItem(
icon: CupertinoIcons.mail, icon: CupertinoIcons.mail,
text: "Contact Us".tr, text: "Contact Us".tr,
onTap: () => Get.to(() => const SettingsCaptain()), onTap: () => Get.to(() => ContactUsPage()),
), ),
_buildDivider(), _buildDivider(),
_buildDrawerItem( _buildDrawerItem(

View File

@@ -1,4 +1,5 @@
import 'dart:convert'; import 'dart:convert';
import 'dart:math';
import 'package:SEFER/constant/box_name.dart'; import 'package:SEFER/constant/box_name.dart';
import 'package:SEFER/controller/firebase/local_notification.dart'; import 'package:SEFER/controller/firebase/local_notification.dart';
@@ -10,8 +11,12 @@ import 'package:get/get.dart';
import 'package:SEFER/controller/home/captin/home_captain_controller.dart'; import 'package:SEFER/controller/home/captin/home_captain_controller.dart';
import 'package:google_maps_flutter/google_maps_flutter.dart'; import 'package:google_maps_flutter/google_maps_flutter.dart';
import 'package:timezone/data/latest.dart' as tz;
import 'package:timezone/timezone.dart' as tz;
import '../../../../../constant/colors.dart'; import '../../../../../constant/colors.dart';
import '../../../../../constant/notification.dart';
import '../../../../../controller/functions/audio_controller.dart'; import '../../../../../controller/functions/audio_controller.dart';
import '../../../../../print.dart';
import '../../../../Rate/ride_calculate_driver.dart'; import '../../../../Rate/ride_calculate_driver.dart';
import '../../../../../controller/functions/location_controller.dart'; import '../../../../../controller/functions/location_controller.dart';
import '../../driver_map_page.dart'; import '../../driver_map_page.dart';
@@ -180,30 +185,53 @@ GetBuilder<HomeCaptainController> leftMainMenuCaptainIcons() {
), ),
// Platform.isAndroid // Platform.isAndroid
// ? // ?
// AnimatedContainer( AnimatedContainer(
// duration: const Duration(microseconds: 200), duration: const Duration(microseconds: 200),
// width: controller.widthMapTypeAndTraffic, width: controller.widthMapTypeAndTraffic,
// decoration: BoxDecoration( decoration: BoxDecoration(
// color: AppColor.secondaryColor, color: AppColor.secondaryColor,
// border: Border.all(color: AppColor.blueColor), border: Border.all(color: AppColor.blueColor),
// borderRadius: BorderRadius.circular(15)), borderRadius: BorderRadius.circular(15)),
// child: Builder(builder: (context) { child: Builder(builder: (context) {
// return IconButton( return IconButton(
// onPressed: () async { onPressed: () async {
// // NotificationController().showNotification( // NotificationController().showNotification(
// // ' message.notification!.title.toString()', // ' message.notification!.title.toString()',
// // ' message.notification!.body.toString()', // ' message.notification!.body.toString()',
// // 'order', // 'order',
// // ''); // '');
// },
// icon: const Icon( NotificationController notificationController =
// FontAwesome5.window_close, Get.put(NotificationController());
// size: 29, await notificationController.initNotifications();
// color: AppColor.blueColor, final random = Random();
// ), final randomMessage =
driverMessages[random.nextInt(driverMessages.length)];
Log.print(
' randomMessage.split[0]: ${randomMessage.split(':')[0]}');
Log.print(
' randomMessage.split([1]: ${randomMessage.split(':')[1]}');
// Schedule the notification with the random message
notificationController.showNotification(
randomMessage.split(':')[0],
randomMessage.split(':')[1],
"ding",
'');
// notificationController.scheduleNotificationEvery10Hours(
// "افتح التطبيق".tr,
// "افتح التطبيق لتبقى على اطلاع واستعداد للمهام القادمة.".tr,
// "ding",
// ); // );
// }), },
// ), icon: const Icon(
FontAwesome5.window_close,
size: 29,
color: AppColor.blueColor,
),
);
}),
),
// : const SizedBox(), // : const SizedBox(),
// AnimatedContainer( // AnimatedContainer(
// duration: const Duration(microseconds: 200), // duration: const Duration(microseconds: 200),

View File

@@ -101,12 +101,13 @@ class PassengerInfoWindow extends StatelessWidget {
children: [ children: [
InkWell( InkWell(
onTap: () { onTap: () {
FirebaseMessagesController().sendNotificationToAnyWithoutData( FirebaseMessagesController().sendNotificationToDriverMAP(
'message From Driver', 'message From Driver',
"Where are you, sir?" "Where are you, sir?"
.tr, .tr,
controller controller
.tokenPassenger, .tokenPassenger,
[],
'ding.wav'); 'ding.wav');
Get.back(); Get.back();
}, },
@@ -132,12 +133,13 @@ class PassengerInfoWindow extends StatelessWidget {
), ),
InkWell( InkWell(
onTap: () { onTap: () {
FirebaseMessagesController().sendNotificationToAnyWithoutData( FirebaseMessagesController().sendNotificationToDriverMAP(
'message From Driver', 'message From Driver',
"I've been trying to reach you but your phone is off." "I've been trying to reach you but your phone is off."
.tr, .tr,
controller controller
.tokenPassenger, .tokenPassenger,
[],
'ding.wav'); 'ding.wav');
Get.back(); Get.back();
}, },
@@ -163,12 +165,13 @@ class PassengerInfoWindow extends StatelessWidget {
), ),
InkWell( InkWell(
onTap: () { onTap: () {
FirebaseMessagesController().sendNotificationToAnyWithoutData( FirebaseMessagesController().sendNotificationToDriverMAP(
'message From Driver', 'message From Driver',
"Please don't be late, I'm waiting for you at the specified location." "Please don't be late, I'm waiting for you at the specified location."
.tr, .tr,
controller controller
.tokenPassenger, .tokenPassenger,
[],
'ding.wav'); 'ding.wav');
Get.back(); Get.back();
}, },
@@ -194,13 +197,14 @@ class PassengerInfoWindow extends StatelessWidget {
), ),
InkWell( InkWell(
onTap: () { onTap: () {
FirebaseMessagesController().sendNotificationToAnyWithoutData( FirebaseMessagesController().sendNotificationToDriverMAP(
'message From Driver', 'message From Driver',
"Please don't be late" "Please don't be late"
.tr, .tr,
controller controller
.tokenPassenger, .tokenPassenger,
'ding.wav'); [],
'cancel.wav');
Get.back(); Get.back();
}, },
child: Container( child: Container(
@@ -247,10 +251,11 @@ class PassengerInfoWindow extends StatelessWidget {
IconButton( IconButton(
onPressed: onPressed:
() { () {
FirebaseMessagesController().sendNotificationToAnyWithoutData( FirebaseMessagesController().sendNotificationToDriverMAP(
'message From Driver'.tr, 'message From Driver',
controller.messageToPassenger.text, controller.messageToPassenger.text,
controller.tokenPassenger, controller.tokenPassenger,
[],
'ding.wav'); 'ding.wav');
controller controller
.messageToPassenger .messageToPassenger
@@ -471,13 +476,13 @@ class PassengerInfoWindow extends StatelessWidget {
140) { 140) {
// Notify Passenger // Notify Passenger
FirebaseMessagesController() FirebaseMessagesController()
.sendNotificationToPassengerToken( .sendNotificationToDriverMAP(
'Hi, I Arrive at your site', 'Hi ,I Arrive your site',
'I Arrive at your site' 'I Arrive at your site'
.tr, .tr,
controller.tokenPassenger, controller.tokenPassenger,
[], [],
'start.wav', 'ding.wav',
); );
controller controller
.startTimerToShowDriverWaitPassengerDuration(); .startTimerToShowDriverWaitPassengerDuration();
@@ -553,7 +558,7 @@ class PassengerInfoWindow extends StatelessWidget {
'Are you sure to cancel?'.tr, 'Are you sure to cancel?'.tr,
'', () async { '', () async {
FirebaseMessagesController() FirebaseMessagesController()
.sendNotificationToPassengerToken( .sendNotificationToDriverMAP(
'Driver Cancelled Your Trip', 'Driver Cancelled Your Trip',
'You will need to pay the cost to the driver, or it will be deducted from your next trip' 'You will need to pay the cost to the driver, or it will be deducted from your next trip'
.tr, .tr,

View File

@@ -330,7 +330,7 @@ class OrderSpeedRequest extends StatelessWidget {
if (AppLink.endPoint != AppLink.seferCairoServer) { if (AppLink.endPoint != AppLink.seferCairoServer) {
CRUD().post( CRUD().post(
link: link:
"${AppLink.endPoint}/rides/updateStausFromSpeed.php", "${AppLink.endPoint}/ride/rides/updateStausFromSpeed.php",
payload: { payload: {
'id': orderRequestController.myList[16], 'id': orderRequestController.myList[16],
'rideTimeStart': DateTime.now().toString(), 'rideTimeStart': DateTime.now().toString(),
@@ -364,6 +364,17 @@ class OrderSpeedRequest extends StatelessWidget {
box.read(BoxName.nameDriver).toString(), box.read(BoxName.nameDriver).toString(),
box.read(BoxName.tokenDriver).toString(), box.read(BoxName.tokenDriver).toString(),
]; ];
FirebaseMessagesController()
.sendNotificationToPassengerToken(
'Accepted Ride',
'your ride is applied'.tr,
// arguments['DriverList'][9].toString(),
orderRequestController
.arguments['DriverList'][9]
.toString(),
// box.read(BoxName.tokenDriver).toString(),
bodyToPassenger,
'start.wav');
await CRUD().postFromDialogue( await CRUD().postFromDialogue(
link: AppLink.addDriverOrder, link: AppLink.addDriverOrder,
payload: { payload: {
@@ -388,7 +399,7 @@ class OrderSpeedRequest extends StatelessWidget {
if (AppLink.endPoint != AppLink.seferCairoServer) { if (AppLink.endPoint != AppLink.seferCairoServer) {
CRUD().post( CRUD().post(
link: link:
"${AppLink.endPoint}/driver_order/add.php", "${AppLink.endPoint}/ride/driver_order/add.php",
payload: { payload: {
'driver_id': orderRequestController 'driver_id': orderRequestController
.myList[6] .myList[6]
@@ -400,17 +411,7 @@ class OrderSpeedRequest extends StatelessWidget {
'status': 'Apply' 'status': 'Apply'
}); });
} }
FirebaseMessagesController()
.sendNotificationToPassengerToken(
'Apply Ride',
'your ride is applied'.tr,
// arguments['DriverList'][9].toString(),
orderRequestController
.arguments['DriverList'][9]
.toString(),
// box.read(BoxName.tokenDriver).toString(),
bodyToPassenger,
'start.wav');
Get.back(); Get.back();
// 'Arguments passed to PassengerLocationMapPage:'); // 'Arguments passed to PassengerLocationMapPage:');

View File

@@ -1,16 +1,69 @@
import 'dart:convert';
import 'package:SEFER/constant/box_name.dart';
import 'package:SEFER/constant/links.dart';
import 'package:SEFER/controller/functions/crud.dart';
import 'package:SEFER/views/widgets/my_scafold.dart'; import 'package:SEFER/views/widgets/my_scafold.dart';
import 'package:flutter/material.dart'; import 'package:flutter/material.dart';
import 'package:get/get.dart'; import 'package:get/get.dart';
import '../../../../main.dart';
class VipOrderPage extends StatelessWidget { class VipOrderPage extends StatelessWidget {
const VipOrderPage({super.key}); const VipOrderPage({super.key});
@override @override
Widget build(BuildContext context) { Widget build(BuildContext context) {
Get.put(VipOrderController());
return MyScafolld( return MyScafolld(
title: 'VIP Order'.tr, title: 'VIP Order'.tr,
body: [], body: [
GetBuilder<VipOrderController>(builder: (vipOrderController) {
return SafeArea(
child: Column(
children: [],
));
})
],
isleading: true, isleading: true,
); );
} }
} }
class VipOrderController extends GetxController {
bool isLoading = false;
final arguments = Get.arguments;
late String body;
List tripData = [];
var myList;
initilize() {
final myListString = arguments['myListString'];
if (arguments['DriverList'] == null || arguments['DriverList'].isEmpty) {
myList = jsonDecode(myListString);
} else {
myList = arguments['DriverList'];
}
body = arguments['body'];
update();
}
fetchOrder() async {
var res = await CRUD().get(link: AppLink.getMishwari, payload: {
'driverId': box.read(BoxName.driverID).toString(),
});
if (res != 'failure') {
tripData = jsonDecode(res)['message'];
update();
}
}
@override
void onInit() async {
await initilize();
fetchOrder();
super.onInit();
}
}

View File

@@ -0,0 +1,105 @@
import 'package:SEFER/constant/colors.dart';
import 'package:SEFER/constant/style.dart';
import 'package:SEFER/views/widgets/my_scafold.dart';
import 'package:SEFER/views/widgets/mycircular.dart';
import 'package:flutter/material.dart';
import 'package:flutter_font_icons/flutter_font_icons.dart';
import 'package:get/get.dart';
import '../../auth/captin/driver_car_controller.dart';
import '../../widgets/elevated_btn.dart';
import 'cars_inserting_page.dart';
class CaptainsCars extends StatelessWidget {
const CaptainsCars({super.key});
@override
Widget build(BuildContext context) {
Get.put(DriverCarController());
return MyScafolld(
title: "Add new car".tr,
body: [
Column(
children: [
MyElevatedButton(
title: "Add new car".tr,
onPressed: () async {
Get.to(() => CarsInsertingPage());
},
),
Expanded(
child: GetBuilder<DriverCarController>(
builder: (controller) {
return controller.isLoading
? const MyCircularProgressIndicator()
: ListView.builder(
itemCount: controller.cars.length,
itemBuilder: (context, index) {
final car = controller.cars[index];
return Padding(
padding: const EdgeInsets.all(4.0),
child: Card(
elevation: 2,
child: ListTile(
leading: Icon(
Fontisto.car,
size: 50,
color: Color(int.parse(car['color_hex']
.replaceFirst('#', '0xff'))),
),
title: Text(
car['make'],
style: AppStyle.title,
), // Assuming `make` is a field in each car item
subtitle: Row(
mainAxisAlignment:
MainAxisAlignment.spaceBetween,
children: [
Text(
car['model'],
style: AppStyle.title,
),
Container(
decoration: BoxDecoration(
border: Border.all(
color: AppColor.blueColor)),
child: Padding(
padding: const EdgeInsets.symmetric(
horizontal: 4),
child: Text(
car['car_plate'],
style: AppStyle.title,
),
),
),
Text(
car['year'],
style: AppStyle.title,
),
],
), // Assuming `model` is a field in each car item
trailing: IconButton(
icon: const Icon(Icons.delete),
onPressed: () {
// Add logic here to remove a car
controller
.removeCar(car['id'].toString());
},
),
onTap: () {
// Add logic to view or edit the car details
},
),
),
);
},
);
},
),
),
],
)
],
isleading: true);
}
}

View File

@@ -0,0 +1,300 @@
import 'package:SEFER/splash_screen_page.dart';
import 'package:SEFER/views/widgets/elevated_btn.dart';
import 'package:SEFER/views/widgets/my_scafold.dart';
import 'package:flutter/material.dart';
import 'package:get/get.dart';
import '../../../constant/colors.dart';
import '../../../constant/links.dart';
import '../../../constant/style.dart';
import '../../../controller/functions/gemeni.dart';
import '../../auth/captin/driver_car_controller.dart';
class CarsInsertingPage extends StatelessWidget {
CarsInsertingPage({super.key});
final driverCarController = Get.put(DriverCarController());
@override
Widget build(BuildContext context) {
Get.put(AI());
return MyScafolld(
title: 'Insert New Car'.tr,
body: [
Container(
color: AppColor.accentColor.withOpacity(.2),
child: Padding(
padding: const EdgeInsets.all(8.0),
child: Column(
crossAxisAlignment: CrossAxisAlignment.center,
children: [
egyptCarLicenceFront(),
egyptCarLicenceBack(),
const SizedBox(height: 10),
Text('Please make sure to read the license carefully.'.tr),
Text(
'If your car license has the new design, upload the front side with two images.'
.tr),
const SizedBox(height: 10),
MyElevatedButton(
title: 'Please upload this license.'.tr,
onPressed: () {
final aiFront =
Get.find<AI>().responseIdCardDriverEgyptFront;
final aiBack =
Get.find<AI>().responseIdCardDriverEgyptBack;
driverCarController.addCarsForDrivers(
aiBack['vin'].toString(),
aiBack['car_plate'].toString(),
aiBack['make'].toString(),
aiBack['model'].toString(),
aiBack['year'].toString(),
aiFront['expiration_date'].toString(),
aiBack['color'].toString(),
aiBack['color_hex'].toString(),
aiFront['address'].toString(),
aiFront['owner'].toString(),
aiBack['registration_date'].toString(),
aiBack['displacement'].toString(),
aiBack['fuel'].toString(),
);
})
],
),
),
)
],
isleading: true);
}
}
GetBuilder<AI> egyptCarLicenceFront() {
return GetBuilder<AI>(
builder: (ai) {
if (ai.responseIdCardDriverEgyptFront.isNotEmpty) {
// No need to access ai.responseIdCardDriverEgyptBack anymore
final licenseExpiryDate = DateTime.parse(
ai.responseIdCardDriverEgyptFront['LicenseExpirationDate']);
// Check if license has expired
final today = DateTime.now();
final isLicenseExpired = licenseExpiryDate.isBefore(today);
return Card(
elevation: 4.0,
shape: RoundedRectangleBorder(
borderRadius: BorderRadius.circular(16.0),
),
child: Padding(
padding: const EdgeInsets.all(16.0),
child: Column(
crossAxisAlignment: CrossAxisAlignment.start,
children: [
Row(
children: [
Text('Vehicle Details Front'.tr,
style: AppStyle.headTitle2),
IconButton(
onPressed: () async {
ai.allMethodForAI(ai.prompts[3]['prompt'].toString(),
AppLink.uploadEgypt, 'car_front');
},
icon: const Icon(Icons.refresh),
),
],
),
const SizedBox(height: 8.0),
const Divider(color: AppColor.accentColor),
const SizedBox(height: 8.0),
// Removed Make, Model, etc. as they are not available
Text(
'${'Plate Number'.tr}: ${ai.responseIdCardDriverEgyptFront['car_plate']}',
),
const SizedBox(height: 8.0),
Text(
'${'Owner Name'.tr}: ${ai.responseIdCardDriverEgyptFront['owner']}',
),
const SizedBox(height: 8.0),
Text(
'${'Address'.tr}: ${ai.responseIdCardDriverEgyptFront['address']}',
),
const SizedBox(height: 8.0),
Row(
mainAxisAlignment: MainAxisAlignment.spaceBetween,
children: [
Text(
'${'License Expiry Date'.tr}: ${licenseExpiryDate.toString().substring(0, 10)}',
style: TextStyle(
color: isLicenseExpired ? Colors.red : Colors.green,
),
),
// Removed Fuel as it's not available
],
),
// Removed Inspection Date as it's not available
],
),
),
);
}
return Card(
child: InkWell(
onTap: () async {
ai.allMethodForAINewCar(ai.prompts[3]['prompt'].toString(),
AppLink.uploadEgypt, 'car_front', 'carId'); //todo
},
child: Column(
children: [
Image.asset(
'assets/images/3.png',
height: Get.height * .25,
width: double.maxFinite,
fit: BoxFit.fitHeight,
),
Text(
'Capture an Image of Your car license front '.tr,
style: AppStyle.title,
),
],
),
),
);
},
);
}
GetBuilder<AI> egyptCarLicenceBack() {
return GetBuilder<AI>(
builder: (ai) {
if (ai.responseIdCardDriverEgyptBack.isNotEmpty) {
// Get the tax expiry date from the response
final taxExpiryDate =
ai.responseIdCardDriverEgyptBack['tax_expiry'].toString();
// final displacement = ai.responseIdCardDriverEgyptBack['displacement'];
// if (int.parse(displacement) < 1000) {}
// Get the inspection date from the response
final inspectionDate =
ai.responseIdCardDriverEgyptBack['inspection_date'].toString();
final year = int.parse(inspectionDate.toString().split('-')[0]);
// Set inspectionDateTime to December 31st of the given year
final inspectionDateTime = DateTime(year, 12, 31);
String carBackLicenseExpired =
inspectionDateTime.toString().split(' ')[0];
// Get the current date
final today = DateTime.now();
// Try parsing the tax expiry date. If it fails, set it to null.
final taxExpiryDateTime = DateTime.tryParse(taxExpiryDate ?? '');
final isExpired =
taxExpiryDateTime != null && taxExpiryDateTime.isBefore(today);
// Check if the inspection date is before today
bool isInspectionExpired = inspectionDateTime.isBefore(today);
return Card(
elevation: 4.0,
shape: RoundedRectangleBorder(
borderRadius: BorderRadius.circular(16.0),
),
child: Padding(
padding: const EdgeInsets.all(16.0),
child: Column(
crossAxisAlignment: CrossAxisAlignment.start,
children: [
Row(
mainAxisAlignment: MainAxisAlignment.spaceBetween,
children: [
Text('Vehicle Details Back'.tr, style: AppStyle.headTitle2),
IconButton(
onPressed: () async {
ai.allMethodForAI(ai.prompts[4]['prompt'].toString(),
AppLink.uploadEgypt, 'car_back');
},
icon: const Icon(Icons.refresh),
),
],
),
const SizedBox(height: 8.0),
const Divider(color: AppColor.accentColor),
const SizedBox(height: 8.0),
Row(
mainAxisAlignment: MainAxisAlignment.spaceBetween,
children: [
Text(
'${'Make'.tr}: ${ai.responseIdCardDriverEgyptBack['make']}'),
Text(
'${'Model'.tr}: ${ai.responseIdCardDriverEgyptBack['model']}'),
],
),
const SizedBox(height: 8.0),
Row(
mainAxisAlignment: MainAxisAlignment.spaceBetween,
children: [
Text(
'${'Year'.tr}: ${ai.responseIdCardDriverEgyptBack['year']}'),
Text(
'${'Chassis'.tr}: ${ai.responseIdCardDriverEgyptBack['chassis']}'),
],
),
const SizedBox(height: 8.0),
Row(
mainAxisAlignment: MainAxisAlignment.spaceBetween,
children: [
Text(
'${'Color'.tr}: ${ai.responseIdCardDriverEgyptBack['color']}'),
Text(
'${'Displacement'.tr}: ${ai.responseIdCardDriverEgyptBack['displacement']} cc'),
],
),
const SizedBox(height: 8.0),
Text(
'${'Fuel'.tr}: ${ai.responseIdCardDriverEgyptBack['fuel']}'),
const SizedBox(height: 8.0),
if (taxExpiryDateTime != null)
Text(
'${'Tax Expiry Date'.tr}: $taxExpiryDate',
style: TextStyle(
color: isExpired ? Colors.red : Colors.green,
),
),
const SizedBox(height: 8.0),
Row(
mainAxisAlignment: MainAxisAlignment.spaceBetween,
children: [
Text(
'${'Inspection Date'.tr}: $carBackLicenseExpired',
style: TextStyle(
color: isInspectionExpired ? Colors.red : Colors.green,
),
),
],
),
],
),
),
);
}
return Card(
child: InkWell(
onTap: () async {
ai.allMethodForAI(ai.prompts[4]['prompt'].toString(),
AppLink.uploadEgypt, 'car_back');
},
child: Column(
children: [
Image.asset(
'assets/images/4.png',
height: Get.height * .25,
width: double.maxFinite,
fit: BoxFit.fitHeight,
),
Text(
'Capture an Image of Your car license back'.tr,
style: AppStyle.title,
),
],
),
),
);
},
);
}

View File

@@ -1,5 +1,6 @@
import 'package:SEFER/constant/style.dart'; import 'package:SEFER/constant/style.dart';
import 'package:SEFER/controller/home/payment/captain_wallet_controller.dart'; import 'package:SEFER/controller/home/payment/captain_wallet_controller.dart';
import 'package:SEFER/views/widgets/elevated_btn.dart';
import 'package:SEFER/views/widgets/mycircular.dart'; import 'package:SEFER/views/widgets/mycircular.dart';
import 'package:flutter/material.dart'; import 'package:flutter/material.dart';
import 'package:get/get.dart'; import 'package:get/get.dart';
@@ -7,6 +8,7 @@ import 'package:SEFER/controller/profile/captain_profile_controller.dart';
import 'package:SEFER/views/widgets/my_scafold.dart'; import 'package:SEFER/views/widgets/my_scafold.dart';
import '../my_wallet/walet_captain.dart'; import '../my_wallet/walet_captain.dart';
import 'captains_cars.dart';
class ProfileCaptain extends StatelessWidget { class ProfileCaptain extends StatelessWidget {
ProfileCaptain({super.key}); ProfileCaptain({super.key});
@@ -41,6 +43,15 @@ class ProfileCaptain extends StatelessWidget {
), ),
), ),
), ),
const SizedBox(
height: 5,
),
MyElevatedButton(
title: 'Show my Cars'.tr,
onPressed: () async {
Get.to(() => CaptainsCars());
},
),
SizedBox( SizedBox(
height: Get.height * .8, height: Get.height * .8,
child: DriverProfileCard( child: DriverProfileCard(