This commit is contained in:
Hamza-Ayed
2023-10-12 14:16:55 +03:00
parent bf9fce363d
commit c1e4c74356
14 changed files with 416 additions and 39 deletions

View File

@@ -14,7 +14,7 @@ if (flutterRoot == null) {
def flutterVersionCode = localProperties.getProperty('flutter.versionCode') def flutterVersionCode = localProperties.getProperty('flutter.versionCode')
if (flutterVersionCode == null) { if (flutterVersionCode == null) {
flutterVersionCode = '3' flutterVersionCode = '6'
} }
def flutterVersionName = localProperties.getProperty('flutter.versionName') def flutterVersionName = localProperties.getProperty('flutter.versionName')
@@ -55,8 +55,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.
minSdkVersion 23 minSdkVersion 23
targetSdkVersion flutter.targetSdkVersion targetSdkVersion flutter.targetSdkVersion
versionCode 6 versionCode 7
versionName '1.0.6' versionName '1.0.7'
} }
signingConfigs { signingConfigs {

View File

@@ -8,10 +8,8 @@
<key>NSCameraUsageDescription</key> <key>NSCameraUsageDescription</key>
<string>Sefer app requires access to your camera in order to scan QR codes and capture images for uploading.</string> <string>Sefer app requires access to your camera in order to scan QR codes and capture images for uploading.</string>
<key>NSLocationAlwaysAndWhenInUseUsageDescription</key> <key>NSLocationAlwaysAndWhenInUseUsageDescription</key>
<string>Sefer app needs access to your location to provide you with accurate directions and location-based services.</string>
<key>FirebaseAppDelegateProxyEnabled</key>
<key>NSLocationWhenInUseUsageDescription</key>
<string>This app needs access to your location to provide you with the best ride experience. Your location data will be used to find the nearest available cars and connect you with the closest captain for efficient and convenient rides.</string> <string>This app needs access to your location to provide you with the best ride experience. Your location data will be used to find the nearest available cars and connect you with the closest captain for efficient and convenient rides.</string>
<key>FirebaseAppDelegateProxyEnabled</key>
<string>NO</string> <string>NO</string>
<key>CFBundleGetInfoString</key> <key>CFBundleGetInfoString</key>
<string></string> <string></string>
@@ -62,5 +60,7 @@
<true/> <true/>
<key>UIApplicationSupportsIndirectInputEvents</key> <key>UIApplicationSupportsIndirectInputEvents</key>
<true/> <true/>
<key>NSLocationWhenInUseUsageDescription</key>
<string>This app needs access to your location to provide you with the best ride experience. Your location data will be used to find the nearest available cars and connect you with the closest captain for efficient and convenient rides.</string>
</dict> </dict>
</plist> </plist>

View File

@@ -45,6 +45,11 @@ class AppLink {
static const String updateDriverOrder = "$ride/driver_order/update.php"; static const String updateDriverOrder = "$ride/driver_order/update.php";
static const String deleteDriverOrder = "$ride/driver_order/delete.php"; static const String deleteDriverOrder = "$ride/driver_order/delete.php";
// =====================================
static const String addRateToPassenger = "$ride/rate/add.php";
static const String addRateToDriver = "$ride/rate/addRateToDriver.php";
// ===========================================
static const String pathImage = "$server/upload/types/"; static const String pathImage = "$server/upload/types/";
static const String uploadImage = "$server/uploadImage.php"; static const String uploadImage = "$server/uploadImage.php";
static const String uploadImageType = "$server/uploadImageType.php"; static const String uploadImageType = "$server/uploadImageType.php";

View File

@@ -36,14 +36,14 @@ class AppStyle {
BoxShadow( BoxShadow(
color: AppColor.accentColor, color: AppColor.accentColor,
offset: Offset(-3, -3), offset: Offset(-3, -3),
blurRadius: 0, blurRadius: 1,
spreadRadius: 0, spreadRadius: 1,
blurStyle: BlurStyle.outer), blurStyle: BlurStyle.outer),
BoxShadow( BoxShadow(
color: AppColor.accentColor, color: AppColor.accentColor,
offset: Offset(3, 3), offset: Offset(3, 3),
blurRadius: 0, blurRadius: 1,
spreadRadius: 0, spreadRadius: 1,
blurStyle: BlurStyle.outer) blurStyle: BlurStyle.outer)
]); ]);
} }

View File

@@ -9,9 +9,11 @@ import 'package:ride/constant/colors.dart';
import 'package:ride/controller/firebase/firbase_messge.dart'; import 'package:ride/controller/firebase/firbase_messge.dart';
import 'package:ride/controller/functions/location_controller.dart'; import 'package:ride/controller/functions/location_controller.dart';
import 'package:ride/main.dart'; import 'package:ride/main.dart';
import 'package:ride/views/Rate/rate_passenger.dart';
import '../../../constant/credential.dart'; import '../../../constant/credential.dart';
import '../../../constant/links.dart'; import '../../../constant/links.dart';
import '../../../views/home/Captin/home_captin.dart';
import '../../functions/crud.dart'; import '../../functions/crud.dart';
class MapDriverController extends GetxController { class MapDriverController extends GetxController {
@@ -28,6 +30,8 @@ class MapDriverController extends GetxController {
late String name; late String name;
late String phone; late String phone;
late String rideId; late String rideId;
late String passengerId;
late String driverId;
late String tokenPassenger; late String tokenPassenger;
late String durationToPassenger; late String durationToPassenger;
late String walletChecked; late String walletChecked;
@@ -35,6 +39,7 @@ class MapDriverController extends GetxController {
bool isPassengerInfoWindow = false; bool isPassengerInfoWindow = false;
bool isBtnRideBegin = false; bool isBtnRideBegin = false;
bool isRideFinished = false; bool isRideFinished = false;
bool isRideStarted = false;
double passengerInfoWindow = Get.height * .32; double passengerInfoWindow = Get.height * .32;
double progress = 0; double progress = 0;
double progressToPassenger = 0; double progressToPassenger = 0;
@@ -156,10 +161,11 @@ class MapDriverController extends GetxController {
tokenPassenger); tokenPassenger);
} }
void beginRideFromDriver() async { void startRideFromDriver() async {
changeRideToBeginToPassenger(); changeRideToBeginToPassenger();
isPassengerInfoWindow = false; isPassengerInfoWindow = false;
isRideFinished = true; isRideStarted = true;
isRideFinished = false;
update(); update();
await CRUD().post(link: AppLink.updateRides, payload: { await CRUD().post(link: AppLink.updateRides, payload: {
'id': rideId, 'id': rideId,
@@ -171,14 +177,23 @@ class MapDriverController extends GetxController {
} }
void finishRideFromDriver() async { void finishRideFromDriver() async {
isRideFinished = true;
isRideStarted = false;
// changeRideToBeginToPassenger(); // changeRideToBeginToPassenger();
await CRUD().post(link: AppLink.updateRides, payload: { await CRUD().post(link: AppLink.updateRides, payload: {
'id': rideId, 'id': rideId,
'rideTimeStart': DateTime.now().toString(), 'rideTimeFinish': DateTime.now().toString(),
'status': 'Finished' 'status': 'Finished'
}); });
FirebaseMessagesController().sendNotificationToAnyWithoutData( Get.back();
'isRideFinished', box.read(BoxName.name).toString(), tokenPassenger); Future.delayed(const Duration(milliseconds: 300));
Get.to(() => RatePassenger(), arguments: {
'rideId': rideId,
'passengerId': passengerId,
'driverId': driverId
});
// FirebaseMessagesController().sendNotificationToAnyWithoutData(
// 'isRideFinished', box.read(BoxName.name).toString(), tokenPassenger);
} }
void updateMarker() { void updateMarker() {
@@ -277,6 +292,8 @@ class MapDriverController extends GetxController {
// Get the passenger location from the arguments. // Get the passenger location from the arguments.
passengerLocation = Get.arguments['passengerLocation']; passengerLocation = Get.arguments['passengerLocation'];
duration = Get.arguments['Duration']; duration = Get.arguments['Duration'];
passengerId = Get.arguments['passengerId'];
driverId = Get.arguments['driverId'];
distance = Get.arguments['Distance']; distance = Get.arguments['Distance'];
name = Get.arguments['name']; name = Get.arguments['name'];
phone = Get.arguments['phone']; phone = Get.arguments['phone'];

View File

@@ -9,11 +9,11 @@ import 'package:location/location.dart';
import 'package:ride/constant/box_name.dart'; import 'package:ride/constant/box_name.dart';
import 'package:ride/constant/credential.dart'; import 'package:ride/constant/credential.dart';
import 'package:ride/constant/links.dart'; import 'package:ride/constant/links.dart';
import 'package:ride/constant/style.dart';
import 'package:ride/controller/firebase/firbase_messge.dart'; import 'package:ride/controller/firebase/firbase_messge.dart';
import 'package:ride/controller/functions/crud.dart'; import 'package:ride/controller/functions/crud.dart';
import 'package:ride/controller/functions/secure_storage.dart'; import 'package:ride/controller/functions/secure_storage.dart';
import 'package:ride/controller/payment/payment_controller.dart'; import 'package:ride/controller/payment/payment_controller.dart';
import 'package:ride/views/Rate/rate_captain.dart';
import 'package:ride/views/widgets/elevated_btn.dart'; import 'package:ride/views/widgets/elevated_btn.dart';
import '../../main.dart'; import '../../main.dart';
import '../../models/model/locations.dart'; import '../../models/model/locations.dart';
@@ -175,22 +175,23 @@ class MapPassengerController extends GetxController {
update(); update();
print('rideTimerBegin: $rideTimerBegin'); print('rideTimerBegin: $rideTimerBegin');
print('isRideFinished: $isRideFinished'); print('isRideFinished: $isRideFinished');
Get.to(() => RateCaptain());
Get.defaultDialog( // Get.defaultDialog(
title: 'Ride Is Finished.'.tr, // title: 'Ride Is Finished.'.tr,
titleStyle: AppStyle.title, // titleStyle: AppStyle.title,
content: Text( // content: Text(
'Rate the Captain Please?'.tr, // 'Rate the Captain Please?'.tr,
style: AppStyle.title, // style: AppStyle.title,
), // ),
confirm: MyElevatedButton( // confirm: MyElevatedButton(
title: 'Ok'.tr, // title: 'Ok'.tr,
onPressed: () { // onPressed: () {
Get.back(); //todo make Rate page //
}, // Get.back(); //todo make Rate page
), // },
barrierDismissible: false, // ),
); // barrierDismissible: false,
// );
} }
void getBeginRideFromDriver() async { void getBeginRideFromDriver() async {
@@ -260,8 +261,9 @@ class MapPassengerController extends GetxController {
"endtime": durationToAdd.toString(), "endtime": durationToAdd.toString(),
"price": totalPassenger.toString(), "price": totalPassenger.toString(),
"passenger_id": box.read(BoxName.pasengerID).toString(), "passenger_id": box.read(BoxName.pasengerID).toString(),
"driver_id": "driver_id": dataCarsLocationByPassenger['message'][carsOrder]
dataCarsLocationByPassenger['message'][carsOrder]['id'].toString(), ['driver_id']
.toString(),
"status": "waiting", "status": "waiting",
"price_for_driver": totalDriver.toString(), "price_for_driver": totalDriver.toString(),
"price_for_passenger": totalME.toString(), "price_for_passenger": totalME.toString(),
@@ -289,6 +291,8 @@ class MapPassengerController extends GetxController {
duration1.toString(), duration1.toString(),
rideId, rideId,
rideTimerBegin.toString(), rideTimerBegin.toString(),
dataCarsLocationByPassenger['message'][carsOrder]['driver_id']
.toString()
]; ];
FirebaseMessagesController().sendNotificationToDriverMAP( FirebaseMessagesController().sendNotificationToDriverMAP(
'Order', 'Order',

View File

@@ -0,0 +1,75 @@
import 'package:flutter/cupertino.dart';
import 'package:get/get.dart';
import 'package:ride/constant/box_name.dart';
import 'package:ride/constant/colors.dart';
import 'package:ride/constant/links.dart';
import 'package:ride/constant/style.dart';
import 'package:ride/controller/functions/crud.dart';
import 'package:ride/controller/home/map_passenger_controller.dart';
import 'package:ride/main.dart';
import 'package:ride/views/home/Captin/home_captin.dart';
import 'package:ride/views/home/map_page.dart';
import 'package:ride/views/widgets/elevated_btn.dart';
class RatePassengerController extends GetxController {
double selectedRateItemId = -1;
TextEditingController comment = TextEditingController();
late String rideId, passengerId, driverId;
@override
void onInit() {
if (box.read(BoxName.driverID).toString() != '' ||
box.read(BoxName.driverID).toString() != null) {
passengerId = Get.arguments['passengerId'];
rideId = Get.arguments['rideId'];
} else {
driverId = Get.arguments['driverId'];
rideId = Get.find<MapPassengerController>().rideId;
}
super.onInit();
}
void selectRateItem(double id) {
selectedRateItemId = id;
update();
}
void addRateToPassenger() async {
if (selectedRateItemId < 1) {
Get.defaultDialog(
title: 'You Should choose rate figure'.tr,
titleStyle: AppStyle.title,
middleText: '',
confirm: MyElevatedButton(title: 'Ok', onPressed: () => Get.back()));
} else {
await CRUD().post(link: AppLink.addRateToPassenger, payload: {
'passenger_id': passengerId,
'driverID': box.read(BoxName.driverID).toString(),
'rideId': rideId,
'rating': selectedRateItemId.toString(),
'comment': comment.text,
}).then((value) {
Get.offAll(const HomeCaptain());
});
}
}
void addRateToDriver() async {
if (selectedRateItemId < 1) {
Get.defaultDialog(
title: 'You Should choose rate figure'.tr,
titleStyle: AppStyle.title,
middleText: '',
confirm: MyElevatedButton(title: 'Ok', onPressed: () => Get.back()));
} else {
await CRUD().post(link: AppLink.addRateToDriver, payload: {
'passenger_id': box.read(BoxName.pasengerID).toString(),
'driverID': driverId,
'rideId': rideId,
'rating': selectedRateItemId.toString(),
'comment': comment.text,
}).then((value) {
Get.offAll(const MapPage());
});
}
}
}

View File

@@ -0,0 +1,130 @@
import 'package:flutter/material.dart';
import 'package:flutter_rating_bar/flutter_rating_bar.dart';
import 'package:get/get.dart';
import '../../constant/colors.dart';
import '../../constant/style.dart';
import '../../controller/rate/rate_conroller.dart';
import '../widgets/elevated_btn.dart';
import '../widgets/my_scafold.dart';
class RateCaptain extends StatelessWidget {
RateCaptain({super.key});
final RatePassengerController controller = Get.put(RatePassengerController());
@override
Widget build(BuildContext context) {
return MyScafolld(
title: 'Rate Captain'.tr,
body: [
Positioned(
top: 40,
left: Get.width * .1,
right: Get.width * .1,
child: Container(
decoration: AppStyle.boxDecoration,
child: Column(
children: [
Center(
child: RatingBar.builder(
initialRating: 0,
itemCount: 5,
itemSize: 50,
itemPadding: const EdgeInsets.symmetric(horizontal: 2),
itemBuilder: (context, index) {
switch (index) {
case 0:
return const Icon(
Icons.sentiment_very_dissatisfied,
color: Colors.red,
);
case 1:
return const Icon(
Icons.sentiment_dissatisfied,
color: Colors.redAccent,
);
case 2:
return const Icon(
Icons.sentiment_neutral,
color: Colors.amber,
);
case 3:
return const Icon(
Icons.sentiment_satisfied,
color: Colors.lightGreen,
);
case 4:
return const Icon(
Icons.sentiment_very_satisfied,
color: Colors.green,
);
default:
return const Icon(
Icons.sentiment_neutral,
color: Colors.amber,
);
} //
},
onRatingUpdate: (rating) {
controller.selectRateItem(rating);
},
),
),
const SizedBox(
height: 20,
),
Form(
child: SizedBox(
width: Get.width * .75,
child: TextFormField(
maxLines: 4,
minLines: 1,
keyboardType: TextInputType.multiline,
controller: controller.comment,
decoration: InputDecoration(
labelText: 'Enter your Note'.tr,
hintText: 'Type something...',
prefixIcon: const Icon(
Icons.rate_review), // Add an icon as a prefix
suffixIcon: IconButton(
icon: const Icon(
Icons.clear,
color: AppColor.redColor,
), // Add an icon as a suffix
onPressed: () {
controller.comment.clear();
},
),
border:
const OutlineInputBorder(), // Add a border around the input field
enabledBorder: const OutlineInputBorder(
borderSide: BorderSide(
color: Colors
.blue), // Customize the border color
),
focusedBorder: const OutlineInputBorder(
borderSide: BorderSide(
color: Colors
.green), // Customize the border color when focused
),
errorBorder: const OutlineInputBorder(
borderSide: BorderSide(
color: Colors
.red), // Customize the border color when there's an error
),
),
),
),
),
const SizedBox(
height: 20,
),
MyElevatedButton(
title: 'Submit rating'.tr,
onPressed: () => controller.addRateToPassenger())
],
),
)),
],
isleading: false);
}
}

View File

@@ -0,0 +1,134 @@
import 'package:flutter/material.dart';
import 'package:flutter_rating_bar/flutter_rating_bar.dart';
import 'package:geolocator/geolocator.dart';
import 'package:get/get.dart';
import 'package:ride/constant/colors.dart';
import 'package:ride/views/widgets/elevated_btn.dart';
import 'package:ride/views/widgets/my_scafold.dart';
import '../../constant/style.dart';
import '../../controller/rate/rate_conroller.dart';
class RatePassenger extends StatelessWidget {
final RatePassengerController controller = Get.put(RatePassengerController());
RatePassenger({super.key});
@override
Widget build(BuildContext context) {
return MyScafolld(
title: 'Rate Passenger'.tr,
body: [
Positioned(
top: 40,
left: Get.width * .1,
right: Get.width * .1,
child: Container(
decoration: AppStyle.boxDecoration,
child: Column(
children: [
Center(
child: RatingBar.builder(
initialRating: 0,
itemCount: 5,
itemSize: 50,
itemPadding: const EdgeInsets.symmetric(horizontal: 2),
itemBuilder: (context, index) {
switch (index) {
case 0:
return const Icon(
Icons.sentiment_very_dissatisfied,
color: Colors.red,
);
case 1:
return const Icon(
Icons.sentiment_dissatisfied,
color: Colors.redAccent,
);
case 2:
return const Icon(
Icons.sentiment_neutral,
color: Colors.amber,
);
case 3:
return const Icon(
Icons.sentiment_satisfied,
color: Colors.lightGreen,
);
case 4:
return const Icon(
Icons.sentiment_very_satisfied,
color: Colors.green,
);
default:
return const Icon(
Icons.sentiment_neutral,
color: Colors.amber,
);
} //
},
onRatingUpdate: (rating) {
controller.selectRateItem(rating);
},
),
),
const SizedBox(
height: 20,
),
Form(
child: SizedBox(
width: Get.width * .75,
child: TextFormField(
maxLines: 4,
minLines: 1,
keyboardType: TextInputType.multiline,
controller: controller.comment,
decoration: InputDecoration(
labelText: 'Enter your Note'.tr,
hintText: 'Type something...',
prefixIcon: const Icon(
Icons.rate_review), // Add an icon as a prefix
suffixIcon: IconButton(
icon: const Icon(
Icons.clear,
color: AppColor.redColor,
), // Add an icon as a suffix
onPressed: () {
controller.comment.clear();
},
),
border:
const OutlineInputBorder(), // Add a border around the input field
enabledBorder: const OutlineInputBorder(
borderSide: BorderSide(
color:
Colors.blue), // Customize the border color
),
focusedBorder: const OutlineInputBorder(
borderSide: BorderSide(
color: Colors
.green), // Customize the border color when focused
),
errorBorder: const OutlineInputBorder(
borderSide: BorderSide(
color: Colors
.red), // Customize the border color when there's an error
),
),
),
),
),
const SizedBox(
height: 20,
),
MyElevatedButton(
title: 'Submit rating'.tr,
onPressed: () => controller.addRateToPassenger())
],
),
)),
],
isleading: false,
);
}
}

View File

@@ -178,7 +178,7 @@ class PassengerInfoWindow extends StatelessWidget {
: MyElevatedButton( : MyElevatedButton(
title: 'Start the Ride'.tr, title: 'Start the Ride'.tr,
onPressed: () { onPressed: () {
controller.beginRideFromDriver(); controller.startRideFromDriver();
}), }),
], ],
), ),

View File

@@ -19,7 +19,6 @@ class PassengerLocationDirection extends StatelessWidget {
Widget build(BuildContext context) { Widget build(BuildContext context) {
Get.put(MapDriverController()); Get.put(MapDriverController());
// mapDirection.getMap();//todo get this argument
return MyScafolld( return MyScafolld(
title: 'Map'.tr, title: 'Map'.tr,
body: [ body: [
@@ -72,7 +71,7 @@ class PassengerLocationDirection extends StatelessWidget {
const PassengerInfoWindow(), const PassengerInfoWindow(),
GetBuilder<MapDriverController>( GetBuilder<MapDriverController>(
builder: (mapDriverController) => mapDriverController builder: (mapDriverController) => mapDriverController
.isRideFinished .isRideStarted
? Positioned( ? Positioned(
left: 5, left: 5,
top: 5, top: 5,
@@ -97,7 +96,9 @@ class PassengerLocationDirection extends StatelessWidget {
), ),
MyElevatedButton( MyElevatedButton(
title: 'End Ride'.tr, title: 'End Ride'.tr,
onPressed: () {}, onPressed: () {
mapDriverController.finishRideFromDriver();
},
kolor: AppColor.redColor, kolor: AppColor.redColor,
), ),
Column( Column(

View File

@@ -199,6 +199,8 @@ class OrderRequestPage extends StatelessWidget {
'https://www.google.com/maps/dir/${myList[0]}/${myList[1]}/', 'https://www.google.com/maps/dir/${myList[0]}/${myList[1]}/',
'DurationToPassenger': myList[15].toString(), 'DurationToPassenger': myList[15].toString(),
'rideId': myList[16].toString(), 'rideId': myList[16].toString(),
'passengerId': myList[7].toString(),
'driverId': myList[18].toString(),
}); });
}, },
), ),

View File

@@ -270,6 +270,14 @@ packages:
url: "https://pub.dev" url: "https://pub.dev"
source: hosted source: hosted
version: "2.0.15" version: "2.0.15"
flutter_rating_bar:
dependency: "direct main"
description:
name: flutter_rating_bar
sha256: d2af03469eac832c591a1eba47c91ecc871fe5708e69967073c043b2d775ed93
url: "https://pub.dev"
source: hosted
version: "4.0.1"
flutter_secure_storage: flutter_secure_storage:
dependency: "direct main" dependency: "direct main"
description: description:

View File

@@ -36,6 +36,7 @@ dependencies:
flutter_paypal: ^0.2.0 flutter_paypal: ^0.2.0
flutter_launcher_icons: ^0.13.1 flutter_launcher_icons: ^0.13.1
crypto: ^3.0.3 crypto: ^3.0.3
flutter_rating_bar: ^4.0.1
dev_dependencies: dev_dependencies: