diff --git a/assets/images/ic_car.svg b/assets/images/ic_car.svg
new file mode 100644
index 0000000..804f607
--- /dev/null
+++ b/assets/images/ic_car.svg
@@ -0,0 +1,11 @@
+
diff --git a/assets/images/ic_edit.svg b/assets/images/ic_edit.svg
new file mode 100644
index 0000000..c14165f
--- /dev/null
+++ b/assets/images/ic_edit.svg
@@ -0,0 +1,4 @@
+
diff --git a/assets/images/ic_lock.svg b/assets/images/ic_lock.svg
new file mode 100644
index 0000000..1273157
--- /dev/null
+++ b/assets/images/ic_lock.svg
@@ -0,0 +1,3 @@
+
diff --git a/assets/images/ic_logout.svg b/assets/images/ic_logout.svg
new file mode 100644
index 0000000..2be107f
--- /dev/null
+++ b/assets/images/ic_logout.svg
@@ -0,0 +1,11 @@
+
diff --git a/assets/images/ic_mobile.svg b/assets/images/ic_mobile.svg
new file mode 100644
index 0000000..068cf7a
--- /dev/null
+++ b/assets/images/ic_mobile.svg
@@ -0,0 +1,10 @@
+
diff --git a/assets/images/ic_notes.svg b/assets/images/ic_notes.svg
new file mode 100644
index 0000000..009cf17
--- /dev/null
+++ b/assets/images/ic_notes.svg
@@ -0,0 +1,12 @@
+
diff --git a/assets/images/ic_notification.svg b/assets/images/ic_notification.svg
new file mode 100644
index 0000000..e45bab2
--- /dev/null
+++ b/assets/images/ic_notification.svg
@@ -0,0 +1,4 @@
+
diff --git a/assets/images/ic_settings.svg b/assets/images/ic_settings.svg
new file mode 100644
index 0000000..83b64c9
--- /dev/null
+++ b/assets/images/ic_settings.svg
@@ -0,0 +1,4 @@
+
diff --git a/lib/api/api_client.dart b/lib/api/api_client.dart
index f6d65ea..e2433be 100644
--- a/lib/api/api_client.dart
+++ b/lib/api/api_client.dart
@@ -92,7 +92,14 @@ class ApiClient {
return await _postForResponse(url, requestBody, token: token, queryParameters: queryParameters, headers: headers, retryTimes: retryTimes);
}
- Future _postForResponse(String url, requestBody, {String? token, Map? queryParameters, Map? headers, int retryTimes = 0}) async {
+ Future _postForResponse(
+ String url,
+ requestBody, {
+ String? token,
+ Map? queryParameters,
+ Map? headers,
+ int retryTimes = 0,
+ }) async {
try {
var _headers = {};
if (token != null) {
@@ -107,7 +114,11 @@ class ApiClient {
var queryString = new Uri(queryParameters: queryParameters).query;
url = url + '?' + queryString;
}
- var response = await _post(Uri.parse(url), body: requestBody, headers: _headers).timeout(Duration(seconds: 100));
+
+ var response;
+
+ response = await _post(Uri.parse(url), body: requestBody, headers: _headers).timeout(Duration(seconds: 100));
+
if (!kReleaseMode) {
print("Url:$url");
print("body:$requestBody");
@@ -160,4 +171,93 @@ class ApiClient {
}
Future _post(url, {Map? headers, body, Encoding? encoding}) => _withClient((client) => client.post(url, headers: headers, body: body, encoding: encoding));
+
+ Future getJsonForObject(FactoryConstructor factoryConstructor, String url,
+ {String? token, Map? queryParameters, Map? headers, int retryTimes = 0}) async {
+ var _headers = {'Accept': 'application/json'};
+ if (headers != null && headers.isNotEmpty) {
+ _headers.addAll(headers);
+ }
+ var response = await getJsonForResponse(url, token: token, queryParameters: queryParameters, headers: _headers, retryTimes: retryTimes);
+ try {
+ if (!kReleaseMode) {
+ print("res:" + response.body);
+ }
+ var jsonData = jsonDecode(response.body);
+ return factoryConstructor(jsonData);
+ } catch (ex) {
+ print("exception:" + response.body);
+ throw APIException(APIException.BAD_RESPONSE_FORMAT, arguments: ex);
+ }
+ }
+
+ Future getJsonForResponse(String url, {String? token, Map? queryParameters, Map? headers, int retryTimes = 0}) async {
+ if (headers == null) {
+ headers = {'Content-Type': 'application/json'};
+ } else {
+ headers['Content-Type'] = 'application/json';
+ }
+ return await _getForResponse(url, token: token, queryParameters: queryParameters, headers: headers, retryTimes: retryTimes);
+ }
+
+ Future _getForResponse(String url, {String? token, Map? queryParameters, Map? headers, int retryTimes = 0}) async {
+ try {
+ var _headers = {};
+ if (token != null) {
+ _headers['Authorization'] = 'Bearer $token';
+ }
+
+ if (headers != null && headers.isNotEmpty) {
+ _headers.addAll(headers);
+ }
+ if (queryParameters != null) {
+ String queryString = new Uri(queryParameters: queryParameters).query;
+ url = url + '?' + queryString.toString();
+ }
+
+ if (!kReleaseMode) {
+ print("Url:$url");
+ print("queryParameters:$queryParameters");
+ }
+ var response = await _get(Uri.parse(url), headers: _headers).timeout(Duration(seconds: 60));
+
+ if (!kReleaseMode) {
+ print("res: " + response.body.toString());
+ }
+ if (response.statusCode >= 200 && response.statusCode < 300) {
+ return response;
+ } else {
+ throw _throwAPIException(response);
+ }
+ } on SocketException catch (e) {
+ if (retryTimes > 0) {
+ print('will retry after 3 seconds...');
+ await Future.delayed(Duration(seconds: 3));
+ return await _getForResponse(url, token: token, queryParameters: queryParameters, headers: headers, retryTimes: retryTimes - 1);
+ } else {
+ throw APIException(APIException.OTHER, arguments: e);
+ }
+ } on HttpException catch (e) {
+ if (retryTimes > 0) {
+ print('will retry after 3 seconds...');
+ await Future.delayed(Duration(seconds: 3));
+ return await _getForResponse(url, token: token, queryParameters: queryParameters, headers: headers, retryTimes: retryTimes - 1);
+ } else {
+ throw APIException(APIException.OTHER, arguments: e);
+ }
+ } on TimeoutException catch (e) {
+ throw APIException(APIException.TIMEOUT, arguments: e);
+ } on ClientException catch (e) {
+ if (retryTimes > 0) {
+ await Future.delayed(Duration(seconds: 3));
+ return await _getForResponse(url, token: token, queryParameters: queryParameters, headers: headers, retryTimes: retryTimes - 1);
+ } else {
+ throw APIException(APIException.OTHER, arguments: e);
+ }
+ } catch (e) {
+ throw APIException(APIException.OTHER, arguments: e);
+ }
+ }
+
+ Future _get(url, {Map? headers}) => _withClient((client) => client.get(url, headers: headers));
}
diff --git a/lib/api/client/profile_api_client.dart b/lib/api/client/profile_api_client.dart
new file mode 100644
index 0000000..68227c5
--- /dev/null
+++ b/lib/api/client/profile_api_client.dart
@@ -0,0 +1,40 @@
+import 'dart:async';
+import 'package:car_provider_app/classes/app_state.dart';
+import 'package:car_provider_app/models/profile/document.dart';
+import 'package:car_provider_app/models/user/country.dart';
+import 'package:car_provider_app/models/user/role.dart';
+import 'package:http/http.dart';
+import 'package:car_provider_app/classes/consts.dart';
+import 'package:car_provider_app/models/content_info_model.dart';
+import 'package:car_provider_app/models/member_model.dart';
+import 'package:car_provider_app/models/surah_model.dart';
+import 'package:car_provider_app/models/user/basic_otp.dart';
+import 'package:car_provider_app/models/user/register_user.dart';
+
+import '../api_client.dart';
+
+class ProfileApiClent {
+ static final ProfileApiClent _instance = ProfileApiClent._internal();
+
+ ProfileApiClent._internal();
+
+ factory ProfileApiClent() => _instance;
+
+ Future getServiceProviderDocument(dynamic userId) async {
+ var queryParameters = {
+ "ServiceProviderID": userId.toString(),
+ };
+ String? token = AppState().getUser.data?.accessToken;
+ print(token);
+ return await ApiClient().getJsonForObject((json) => Document.fromJson(json), ApiConsts.GetProviderDocument, queryParameters: queryParameters, token: AppState().getUser.data!.accessToken ?? "");
+ }
+
+ Future basicVerify(String phoneNo, String otp, String userToken) async {
+ var postParams = {
+ "userMobileNo": phoneNo,
+ "userOTP": otp,
+ "userToken": userToken,
+ };
+ return await ApiClient().postJsonForObject((json) => RegisterUser.fromJson(json), ApiConsts.BasicVerify, postParams);
+ }
+}
diff --git a/lib/api/user_api_client.dart b/lib/api/client/user_api_client.dart
similarity index 76%
rename from lib/api/user_api_client.dart
rename to lib/api/client/user_api_client.dart
index 95935e7..135b017 100644
--- a/lib/api/user_api_client.dart
+++ b/lib/api/client/user_api_client.dart
@@ -1,4 +1,6 @@
import 'dart:async';
+import 'package:car_provider_app/models/user/country.dart';
+import 'package:car_provider_app/models/user/role.dart';
import 'package:http/http.dart';
import 'package:car_provider_app/classes/consts.dart';
import 'package:car_provider_app/models/content_info_model.dart';
@@ -7,7 +9,7 @@ import 'package:car_provider_app/models/surah_model.dart';
import 'package:car_provider_app/models/user/basic_otp.dart';
import 'package:car_provider_app/models/user/register_user.dart';
-import 'api_client.dart';
+import '../api_client.dart';
class UserApiClent {
static final UserApiClent _instance = UserApiClent._internal();
@@ -16,8 +18,8 @@ class UserApiClent {
factory UserApiClent() => _instance;
- Future basicOtp(String phoneNo, {int otpType = 1}) async {
- var postParams = {"countryID": 1, "userMobileNo": phoneNo, "otpType": otpType, "userRole": 4};
+ Future basicOtp(String phoneNo, {int otpType = 1, int roleId = 4, int countryId = 1}) async {
+ var postParams = {"countryID": countryId, "userMobileNo": phoneNo, "otpType": otpType, "userRole": roleId};
return await ApiClient().postJsonForObject((json) => BasicOtp.fromJson(json), ApiConsts.BasicOTP, postParams);
}
@@ -56,4 +58,14 @@ class UserApiClent {
var postParams = {"userToken": userToken, "userOTP": otp};
return await ApiClient().postJsonForResponse(ApiConsts.Login_V2_OTPVerify, postParams);
}
+
+ Future getAllCountries() async {
+ var postParams = {};
+ return await ApiClient().getJsonForObject((json) => Country.fromJson(json), ApiConsts.GetAllCountry);
+ }
+
+ Future getRoles() async {
+ var postParams = {};
+ return await ApiClient().getJsonForObject((json) => Role.fromJson(json), ApiConsts.GetProviderRoles);
+ }
}
diff --git a/lib/api/login_api_client.dart b/lib/api/login_api_client.dart
deleted file mode 100644
index 6cf0954..0000000
--- a/lib/api/login_api_client.dart
+++ /dev/null
@@ -1,27 +0,0 @@
-
-class LoginApiClient {
- static final LoginApiClient _instance = LoginApiClient._internal();
-
- LoginApiClient._internal();
-
- factory LoginApiClient() => _instance;
-
- // Future checkMobileAppVersion() async {
- // String url = "${ApiConsts.utilitiesRest}CheckMobileAppVersion";
- // Map postParams = {};
- // postParams.addAll(AppState().postParamsJson);
- // return await ApiClient().postJsonForObject((json) => CheckMobileAppVersionModel.fromJson(json), url, postParams);
- // }
- //
- // Future memberLogin(String username, String password) async {
- // String url = "${ApiConsts.erpRest}MemberLogin";
- // Map postParams = {"P_APP_VERSION": "CS", "P_LANGUAGE": "US", "P_PASSWORD": password, "P_USER_NAME": username};
- // postParams.addAll(AppState().postParamsJson);
- // return await ApiClient().postJsonForObject((json) {
- // GenericResponseModel responseData = GenericResponseModel.fromJson(json);
- // AppState().postParamsObject?.setLogInTokenID = responseData.logInTokenID;
- // return responseData.memberLoginList;
- // }, url, postParams);
- // }
-
-}
diff --git a/lib/api/tangheem_user_api_client.dart b/lib/api/tangheem_user_api_client.dart
deleted file mode 100644
index bfe32a9..0000000
--- a/lib/api/tangheem_user_api_client.dart
+++ /dev/null
@@ -1,34 +0,0 @@
-import 'dart:async';
-
-import 'package:car_provider_app/classes/consts.dart';
-import 'package:car_provider_app/models/content_info_model.dart';
-import 'package:car_provider_app/models/member_model.dart';
-import 'package:car_provider_app/models/surah_model.dart';
-
-import 'api_client.dart';
-
-class TangheemUserApiClient {
- static final TangheemUserApiClient _instance = TangheemUserApiClient._internal();
-
- TangheemUserApiClient._internal();
-
- factory TangheemUserApiClient() => _instance;
-
- Future getSurahs() async {
- String url = "${ApiConsts.baseUrl}AlSuar_Get";
- var postParams = {};
- return await ApiClient().postJsonForObject((json) => SurahModel.fromJson(json), url, postParams);
- }
-
- Future getMembers() async {
- String url = "${ApiConsts.baseUrl}Committee_Get";
- var postParams = {};
- return await ApiClient().postJsonForObject((json) => MemberModel.fromJson(json), url, postParams);
- }
-
- Future getContentInfo(int contentId) async {
- String url = "${ApiConsts.baseUrl}ContentInfo_Get";
- var postParams = {"contentTypeId": contentId};
- return await ApiClient().postJsonForObject((json) => ContentInfoModel.fromJson(json), url, postParams);
- }
-}
diff --git a/lib/classes/app_state.dart b/lib/classes/app_state.dart
new file mode 100644
index 0000000..d73e33a
--- /dev/null
+++ b/lib/classes/app_state.dart
@@ -0,0 +1,21 @@
+import 'package:car_provider_app/models/user/user.dart';
+
+class AppState {
+ static final AppState _instance = AppState._internal();
+
+ AppState._internal();
+
+ factory AppState() => _instance;
+
+ bool isLogged = false;
+
+ set setLogged(v) => isLogged = v;
+
+ bool? get getIsLogged => isLogged;
+
+ User? _user = null;
+
+ set setUser(v) => _user = v;
+
+ User get getUser => _user??User();
+}
diff --git a/lib/classes/consts.dart b/lib/classes/consts.dart
index 0615648..3b12d24 100644
--- a/lib/classes/consts.dart
+++ b/lib/classes/consts.dart
@@ -2,18 +2,24 @@ class ApiConsts {
// static String baseUrl = "http://10.200.204.20:2801/"; // Local server
static String baseUrl = "https://mdlaboratories.com"; // production server
static String baseUrlServices = baseUrl + "/mc/"; // production server
- // static String baseUrlServices = "https://api.cssynapses.com/tangheem/"; // Live server
static String BasicOTP = baseUrlServices + "api/Register/BasicOTP";
static String BasicVerify = baseUrlServices + "api/Register/BasicVerify";
static String BasicComplete = baseUrlServices + "api/Register/BasicComplete";
+
+ //User
static String Login_V1 = baseUrlServices + "api/Account/Login_V1";
static String Login_V2_OTP = baseUrlServices + "api/Account/Login_V2_OTP";
static String Login_V2_OTPVerify = baseUrlServices + "api/Account/Login_V2_OTPVerify";
static String user = baseUrlServices + "api/User/";
-}
+ static String GetAllCountry = baseUrlServices + "api/Master/Country_Get";
+ static String GetProviderRoles = baseUrlServices + "api/Master/RoleServiceProvider_Get";
+ //Profile
+ static String GetProviderDocument = baseUrlServices + "api/ServiceProviders/ServiceProviderDocument_Get";
+}
+
class GlobalConsts {
static String isRememberMe = "remember_me";
static String email = "email";
diff --git a/lib/config/routes.dart b/lib/config/routes.dart
index 16f7736..6b5deea 100644
--- a/lib/config/routes.dart
+++ b/lib/config/routes.dart
@@ -6,6 +6,7 @@ import 'package:car_provider_app/pages/user/login_method_selection_page.dart';
import 'package:car_provider_app/pages/user/login_verification_page.dart';
import 'package:car_provider_app/pages/user/login_verify_account_page.dart';
import 'package:car_provider_app/pages/user/login_with_password_page.dart';
+import 'package:car_provider_app/pages/user/profile/define_license_page.dart';
import 'package:car_provider_app/pages/user/profile/profile_1_page.dart';
import 'package:car_provider_app/pages/user/profile/profile_2_page.dart';
import 'package:car_provider_app/pages/user/profile/profile_3_page.dart';
@@ -28,6 +29,7 @@ class AppRoutes {
static final String profile1 = "/profile1";
static final String profile2 = "/profile2";
static final String profile3 = "/profile3";
+ static final String defineLicense = "/defineLicese";
static final String dashboard = "/dashboard";
@@ -47,6 +49,7 @@ class AppRoutes {
profile1: (context) => Profile1Page(),
profile2: (context) => Profile2Page(),
profile3: (context) => Profile3Page(),
+ defineLicense: (context) => DefineLicensePage(),
//Home page
dashboard: (context) => DashboardPage(),
diff --git a/lib/models/profile/document.dart b/lib/models/profile/document.dart
new file mode 100644
index 0000000..ff568c9
--- /dev/null
+++ b/lib/models/profile/document.dart
@@ -0,0 +1,80 @@
+// To parse this JSON data, do
+//
+// final document = documentFromJson(jsonString);
+
+import 'dart:convert';
+
+Document documentFromJson(String str) => Document.fromJson(json.decode(str));
+
+String documentToJson(Document data) => json.encode(data.toJson());
+
+class Document {
+ Document({
+ this.totalItemsCount,
+ this.data,
+ this.messageStatus,
+ this.message,
+ });
+
+ int? totalItemsCount;
+ List? data;
+ int? messageStatus;
+ String? message;
+
+ factory Document.fromJson(Map json) => Document(
+ totalItemsCount: json["totalItemsCount"] == null ? null : json["totalItemsCount"],
+ data: json["data"] == null ? null : List.from(json["data"].map((x) => Datum.fromJson(x))),
+ messageStatus: json["messageStatus"] == null ? null : json["messageStatus"],
+ message: json["message"] == null ? null : json["message"],
+ );
+
+ Map toJson() => {
+ "totalItemsCount": totalItemsCount == null ? null : totalItemsCount,
+ "data": data == null ? null : List.from(data!.map((x) => x.toJson())),
+ "messageStatus": messageStatus == null ? null : messageStatus,
+ "message": message == null ? null : message,
+ };
+}
+
+class Datum {
+ Datum({
+ this.id,
+ this.serviceProviderId,
+ this.documentId,
+ this.documentUrl,
+ this.status,
+ this.comment,
+ this.isActive,
+ this.document,
+ });
+
+ int? id;
+ int? serviceProviderId;
+ int? documentId;
+ dynamic? documentUrl;
+ int? status;
+ dynamic? comment;
+ bool? isActive;
+ String? document;
+
+ factory Datum.fromJson(Map json) => Datum(
+ id: json["id"] == null ? null : json["id"],
+ serviceProviderId: json["serviceProviderID"] == null ? null : json["serviceProviderID"],
+ documentId: json["documentID"] == null ? null : json["documentID"],
+ documentUrl: json["documentURL"],
+ status: json["status"] == null ? null : json["status"],
+ comment: json["comment"],
+ isActive: json["isActive"] == null ? null : json["isActive"],
+ document: null,
+ );
+
+ Map toJson() => {
+ "id": id == null ? null : id,
+ "serviceProviderID": serviceProviderId == null ? null : serviceProviderId,
+ "documentID": documentId == null ? null : documentId,
+ "documentURL": documentUrl,
+ "status": status == null ? null : status,
+ "comment": comment,
+ "isActive": isActive == null ? null : isActive,
+ };
+}
diff --git a/lib/models/user.dart b/lib/models/user.dart
deleted file mode 100644
index e09c282..0000000
--- a/lib/models/user.dart
+++ /dev/null
@@ -1,9 +0,0 @@
-class User {
- int id;
-
- User(this.id, this.userName, this.userImage, this.createdDate);
-
- String userName;
- String userImage;
- String createdDate;
-}
diff --git a/lib/models/user/country.dart b/lib/models/user/country.dart
new file mode 100644
index 0000000..f4036cf
--- /dev/null
+++ b/lib/models/user/country.dart
@@ -0,0 +1,81 @@
+// To parse this JSON data, do
+//
+// final country = countryFromJson(jsonString);
+
+import 'dart:convert';
+
+Country countryFromJson(String str) => Country.fromJson(json.decode(str));
+
+String countryToJson(Country data) => json.encode(data.toJson());
+
+class Country {
+ Country({
+ this.totalItemsCount,
+ this.data,
+ this.messageStatus,
+ this.message,
+ });
+
+ int? totalItemsCount;
+ List? data;
+ int? messageStatus;
+ String? message;
+
+ factory Country.fromJson(Map json) => Country(
+ totalItemsCount: json["totalItemsCount"] == null ? null : json["totalItemsCount"],
+ data: json["data"] == null ? null : List.from(json["data"].map((x) => CountryData.fromJson(x))),
+ messageStatus: json["messageStatus"] == null ? null : json["messageStatus"],
+ message: json["message"] == null ? null : json["message"],
+ );
+
+ Map toJson() => {
+ "totalItemsCount": totalItemsCount == null ? null : totalItemsCount,
+ "data": data == null ? null : List.from(data!.map((x) => x.toJson())),
+ "messageStatus": messageStatus == null ? null : messageStatus,
+ "message": message == null ? null : message,
+ };
+}
+
+class CountryData {
+ CountryData({
+ this.id,
+ this.countryName,
+ this.countryNameN,
+ this.nationality,
+ this.nationalityN,
+ this.countryCode,
+ this.alpha2Code,
+ this.alpha3Code,
+ });
+
+ int? id;
+ String? countryName;
+ String? countryNameN;
+ String? nationality;
+ String? nationalityN;
+ String? countryCode;
+ String? alpha2Code;
+ String? alpha3Code;
+
+ factory CountryData.fromJson(Map json) => CountryData(
+ id: json["id"] == null ? null : json["id"],
+ countryName: json["countryName"] == null ? null : json["countryName"],
+ countryNameN: json["countryNameN"] == null ? null : json["countryNameN"],
+ nationality: json["nationality"] == null ? null : json["nationality"],
+ nationalityN: json["nationalityN"] == null ? null : json["nationalityN"],
+ countryCode: json["countryCode"] == null ? null : json["countryCode"],
+ alpha2Code: json["alpha2Code"] == null ? null : json["alpha2Code"],
+ alpha3Code: json["alpha3Code"] == null ? null : json["alpha3Code"],
+ );
+
+ Map toJson() => {
+ "id": id == null ? null : id,
+ "countryName": countryName == null ? null : countryName,
+ "countryNameN": countryNameN == null ? null : countryNameN,
+ "nationality": nationality == null ? null : nationality,
+ "nationalityN": nationalityN == null ? null : nationalityN,
+ "countryCode": countryCode == null ? null : countryCode,
+ "alpha2Code": alpha2Code == null ? null : alpha2Code,
+ "alpha3Code": alpha3Code == null ? null : alpha3Code,
+ };
+}
diff --git a/lib/models/user/role.dart b/lib/models/user/role.dart
new file mode 100644
index 0000000..2ea0054
--- /dev/null
+++ b/lib/models/user/role.dart
@@ -0,0 +1,65 @@
+// To parse this JSON data, do
+//
+// final role = roleFromJson(jsonString);
+
+import 'dart:convert';
+
+Role roleFromJson(String str) => Role.fromJson(json.decode(str));
+
+String roleToJson(Role data) => json.encode(data.toJson());
+
+class Role {
+ Role({
+ this.totalItemsCount,
+ this.data,
+ this.messageStatus,
+ this.message,
+ });
+
+ int? totalItemsCount;
+ List? data;
+ int? messageStatus;
+ String? message;
+
+ factory Role.fromJson(Map json) => Role(
+ totalItemsCount: json["totalItemsCount"] == null ? null : json["totalItemsCount"],
+ data: json["data"] == null ? null : List.from(json["data"].map((x) => RoleData.fromJson(x))),
+ messageStatus: json["messageStatus"] == null ? null : json["messageStatus"],
+ message: json["message"] == null ? null : json["message"],
+ );
+
+ Map toJson() => {
+ "totalItemsCount": totalItemsCount == null ? null : totalItemsCount,
+ "data": data == null ? null : List.from(data!.map((x) => x.toJson())),
+ "messageStatus": messageStatus == null ? null : messageStatus,
+ "message": message == null ? null : message,
+ };
+}
+
+class RoleData {
+ RoleData({
+ this.id,
+ this.roleName,
+ this.roleNameN,
+ this.isActive,
+ });
+
+ int? id;
+ String? roleName;
+ String? roleNameN;
+ bool? isActive;
+
+ factory RoleData.fromJson(Map json) => RoleData(
+ id: json["id"] == null ? null : json["id"],
+ roleName: json["roleName"] == null ? null : json["roleName"],
+ roleNameN: json["roleNameN"] == null ? null : json["roleNameN"],
+ isActive: json["isActive"] == null ? null : json["isActive"],
+ );
+
+ Map toJson() => {
+ "id": id == null ? null : id,
+ "roleName": roleName == null ? null : roleName,
+ "roleNameN": roleNameN == null ? null : roleNameN,
+ "isActive": isActive == null ? null : isActive,
+ };
+}
diff --git a/lib/pages/dashboard/dashboard_page.dart b/lib/pages/dashboard/dashboard_page.dart
index a0726b6..b9ed74e 100644
--- a/lib/pages/dashboard/dashboard_page.dart
+++ b/lib/pages/dashboard/dashboard_page.dart
@@ -1,4 +1,5 @@
import 'package:car_provider_app/api/shared_prefrence.dart';
+import 'package:car_provider_app/config/routes.dart';
import 'package:car_provider_app/theme/colors.dart';
import 'package:car_provider_app/utils/navigator.dart';
import 'package:car_provider_app/widgets/app_bar.dart';
@@ -7,6 +8,7 @@ import 'package:car_provider_app/extensions/int_extensions.dart';
import 'package:car_provider_app/extensions/string_extensions.dart';
import 'package:car_provider_app/extensions/widget_extensions.dart';
import 'package:flutter/material.dart';
+import 'package:flutter_svg/flutter_svg.dart';
class DashboardPage extends StatefulWidget {
@override
@@ -82,19 +84,34 @@ class _DashboardPageState extends State {
),
),
ListTile(
- leading: Icon(Icons.notifications),
+ leading: SvgPicture.asset("assets/images/ic_notification.svg"),
title: "Notifications".toText12(),
),
ListTile(
- leading: Icon(Icons.settings),
+ leading: SvgPicture.asset("assets/images/ic_settings.svg"),
title: "General".toText12(),
),
ListTile(
- leading: Icon(Icons.person),
- title: "Account".toText12(),
+ leading: SvgPicture.asset("assets/images/ic_notes.svg"),
+ title: "Define Licenses".toText12(),
+ onTap: (){
+ navigateWithName(context, AppRoutes.defineLicense);
+ },
+ ),
+ ListTile(
+ leading: SvgPicture.asset("assets/images/ic_car.svg"),
+ title: "Dealership Settings".toText12(),
+ ),
+ ListTile(
+ leading: SvgPicture.asset("assets/images/ic_lock.svg"),
+ title: "Change Password".toText12(),
+ ),
+ ListTile(
+ leading: SvgPicture.asset("assets/images/ic_mobile.svg"),
+ title: "Change Mobile".toText12(),
),
ListTile(
- leading: Icon(Icons.logout),
+ leading: SvgPicture.asset("assets/images/ic_logout.svg"),
title: "Sign Out".toText12(),
onTap: () {
pop(context);
diff --git a/lib/pages/user/complete_profile_page.dart b/lib/pages/user/complete_profile_page.dart
index 161371e..4c9f21c 100644
--- a/lib/pages/user/complete_profile_page.dart
+++ b/lib/pages/user/complete_profile_page.dart
@@ -1,4 +1,4 @@
-import 'package:car_provider_app/api/user_api_client.dart';
+import 'package:car_provider_app/api/client/user_api_client.dart';
import 'package:car_provider_app/classes/utils.dart';
import 'package:car_provider_app/config/routes.dart';
import 'package:car_provider_app/models/user/basic_otp.dart';
diff --git a/lib/pages/user/login_method_selection_page.dart b/lib/pages/user/login_method_selection_page.dart
index 68ef39a..87fb136 100644
--- a/lib/pages/user/login_method_selection_page.dart
+++ b/lib/pages/user/login_method_selection_page.dart
@@ -1,7 +1,7 @@
import 'dart:convert';
import 'package:car_provider_app/api/shared_prefrence.dart';
-import 'package:car_provider_app/api/user_api_client.dart';
+import 'package:car_provider_app/api/client/user_api_client.dart';
import 'package:car_provider_app/classes/utils.dart';
import 'package:car_provider_app/config/constants.dart';
import 'package:car_provider_app/config/routes.dart';
diff --git a/lib/pages/user/login_verification_page.dart b/lib/pages/user/login_verification_page.dart
index f7579a2..b217367 100644
--- a/lib/pages/user/login_verification_page.dart
+++ b/lib/pages/user/login_verification_page.dart
@@ -1,7 +1,8 @@
import 'dart:convert';
import 'package:car_provider_app/api/shared_prefrence.dart';
-import 'package:car_provider_app/api/user_api_client.dart';
+import 'package:car_provider_app/api/client/user_api_client.dart';
+import 'package:car_provider_app/classes/app_state.dart';
import 'package:car_provider_app/classes/utils.dart';
import 'package:car_provider_app/config/constants.dart';
import 'package:car_provider_app/config/routes.dart';
@@ -69,6 +70,8 @@ class _LoginVerificationPageState extends State {
RegisterUser verifiedUser = RegisterUser.fromJson(jsonDecode(response2.body));
if (verifiedUser.messageStatus == 1) {
User user = User.fromJson(jsonDecode(response2.body));
+ AppState().setUser = user;
+ print(user.data!.userInfo!.providerId.toString());
navigateReplaceWithName(context, AppRoutes.dashboard);
} else {
Utils.showToast(verifiedUser.message ?? "");
diff --git a/lib/pages/user/login_verify_account_page.dart b/lib/pages/user/login_verify_account_page.dart
index 4acdb5c..ec1aee3 100644
--- a/lib/pages/user/login_verify_account_page.dart
+++ b/lib/pages/user/login_verify_account_page.dart
@@ -1,4 +1,4 @@
-import 'package:car_provider_app/api/user_api_client.dart';
+import 'package:car_provider_app/api/client/user_api_client.dart';
import 'package:car_provider_app/classes/utils.dart';
import 'package:car_provider_app/config/constants.dart';
import 'package:car_provider_app/config/routes.dart';
diff --git a/lib/pages/user/login_with_password_page.dart b/lib/pages/user/login_with_password_page.dart
index ba83bf3..f4d9646 100644
--- a/lib/pages/user/login_with_password_page.dart
+++ b/lib/pages/user/login_with_password_page.dart
@@ -1,7 +1,7 @@
import 'dart:convert';
import 'package:car_provider_app/api/shared_prefrence.dart';
-import 'package:car_provider_app/api/user_api_client.dart';
+import 'package:car_provider_app/api/client/user_api_client.dart';
import 'package:car_provider_app/classes/utils.dart';
import 'package:car_provider_app/config/constants.dart';
import 'package:car_provider_app/config/routes.dart';
diff --git a/lib/pages/user/profile/define_license_page.dart b/lib/pages/user/profile/define_license_page.dart
new file mode 100644
index 0000000..e54076c
--- /dev/null
+++ b/lib/pages/user/profile/define_license_page.dart
@@ -0,0 +1,96 @@
+import 'dart:io';
+
+import 'package:car_provider_app/api/client/profile_api_client.dart';
+import 'package:car_provider_app/classes/app_state.dart';
+import 'package:car_provider_app/models/profile/document.dart';
+import 'package:car_provider_app/widgets/txt_field.dart';
+import 'package:file_picker/file_picker.dart';
+import 'package:flutter/material.dart';
+import 'package:car_provider_app/extensions/int_extensions.dart';
+
+class DefineLicensePage extends StatefulWidget {
+ @override
+ State createState() => _DefineLicensePageState();
+}
+
+class _DefineLicensePageState extends State {
+ Document? document;
+
+ @override
+ void initState() {
+ // TODO: implement initState
+ super.initState();
+ getDocuments();
+ }
+
+ getDocuments() async {
+ document = await ProfileApiClent().getServiceProviderDocument(AppState().getUser.data!.userInfo!.providerId ?? 0);
+ setState(() {});
+ }
+
+ @override
+ Widget build(BuildContext context) {
+ return Scaffold(
+ appBar: AppBar(
+ title: Text("Define Licenses"),
+ ),
+ body: Container(
+ width: double.infinity,
+ height: double.infinity,
+ child: showWidget(),
+ ),
+ );
+ }
+
+ Widget showWidget() {
+ if (document != null) {
+ return document!.data!.length == 0
+ ? Text("Something went wrong")
+ : ListView.separated(
+ itemBuilder: (context, index) {
+ return Row(
+ children: [
+ Flexible(
+ child: TxtField(
+ hint: "Select Attachment",
+ value: document?.data![index].documentUrl ?? "",
+ isNeedClickAll: true,
+ maxLines: 2,
+ ),
+ ),
+ IconButton(
+ onPressed: () {
+ selectFile(index);
+ },
+ icon: Icon(Icons.insert_link_rounded),
+ )
+ ],
+ );
+ },
+ separatorBuilder: (context, index) {
+ return 12.height;
+ },
+ padding: EdgeInsets.all(12),
+ itemCount: document!.data!.length,
+ );
+ } else {
+ return Center(
+ child: CircularProgressIndicator(),
+ );
+ }
+ }
+
+ selectFile(int index) async {
+ FilePickerResult? result = await FilePicker.platform.pickFiles(type: FileType.custom, allowedExtensions: ['png', 'pdf', 'jpeg']);
+
+ if (result != null) {
+ File file = File(result.files.single.path ?? "");
+
+ setState(() {
+ document!.data![index].documentUrl = result.files.single.path ?? "";
+ });
+ } else {
+ // User canceled the picker
+ }
+ }
+}
diff --git a/lib/pages/user/profile/profile_3_page.dart b/lib/pages/user/profile/profile_3_page.dart
index a6e9824..2acb565 100644
--- a/lib/pages/user/profile/profile_3_page.dart
+++ b/lib/pages/user/profile/profile_3_page.dart
@@ -25,13 +25,13 @@ class Profile3Page extends StatelessWidget {
"Complete Profile 3/3".toText16(),
"Branch Info and Services".toText14(),
12.height,
- DropdownField(
- hint: "Country",
- ),
- 12.height,
- DropdownField(
- hint: "City",
- ),
+ // DropdownField(
+ // hint: "Country",
+ // ),
+ // 12.height,
+ // DropdownField(
+ // hint: "City",
+ // ),
12.height,
TxtField(
hint: "Address",
diff --git a/lib/pages/user/register_page.dart b/lib/pages/user/register_page.dart
index 35a8511..4531c52 100644
--- a/lib/pages/user/register_page.dart
+++ b/lib/pages/user/register_page.dart
@@ -1,14 +1,18 @@
import 'package:car_provider_app/api/api_client.dart';
-import 'package:car_provider_app/api/user_api_client.dart';
+import 'package:car_provider_app/api/client/user_api_client.dart';
import 'package:car_provider_app/classes/utils.dart';
import 'package:car_provider_app/config/routes.dart';
import 'package:car_provider_app/models/user/basic_otp.dart';
+import 'package:car_provider_app/models/user/country.dart';
import 'package:car_provider_app/models/user/register_user.dart';
+import 'package:car_provider_app/models/user/role.dart';
+import 'package:car_provider_app/provider/counter.dart';
import 'package:car_provider_app/utils/navigator.dart';
import 'package:car_provider_app/utils/utils.dart';
import 'package:car_provider_app/widgets/app_bar.dart';
import 'package:car_provider_app/widgets/dialog/dialogs.dart';
import 'package:car_provider_app/widgets/dialog/otp_dialog.dart';
+import 'package:car_provider_app/widgets/dropdown/dropdow_field.dart';
import 'package:car_provider_app/widgets/show_fill_button.dart';
import 'package:car_provider_app/extensions/int_extensions.dart';
import 'package:car_provider_app/extensions/string_extensions.dart';
@@ -17,7 +21,8 @@ import 'package:car_provider_app/widgets/txt_field.dart';
import 'package:flutter/material.dart';
class RegisterPage extends StatelessWidget {
- String phoneNum = "";
+ String phoneNum = "", countryCode = "";
+ int role = -1, countryId = -1;
@override
Widget build(BuildContext context) {
@@ -31,6 +36,40 @@ class RegisterPage extends StatelessWidget {
children: [
"Enter Phone Number".toText24(),
12.height,
+ FutureBuilder(
+ future: UserApiClent().getRoles(),
+ builder: (context, snapshot) {
+ if (snapshot.hasData) {
+ List dropList = [];
+ snapshot.data?.data?.forEach((element) {
+ dropList.add(new DropValue(element.id ?? 0, element.roleName ?? "", ""));
+ });
+ return DropdownField((DropValue value) {
+ role = value.id;
+ }, list: dropList, hint: "Chosse Role");
+ } else {
+ return CircularProgressIndicator();
+ }
+ },
+ ),
+ 12.height,
+ FutureBuilder(
+ future: UserApiClent().getAllCountries(),
+ builder: (context, snapshot) {
+ if (snapshot.hasData) {
+ List dropList = [];
+ snapshot.data?.data?.forEach((element) {
+ dropList.add(new DropValue(element.id ?? 0, (element.countryName ?? "") + " " + (element.countryCode ?? ""), element.countryCode ?? ""));
+ });
+ return DropdownField((DropValue value) {
+ countryCode = value.subValue;
+ countryId = value.id;
+ }, list: dropList, hint: "Chosse Country");
+ } else {
+ return CircularProgressIndicator();
+ }
+ },
+ ),
TxtField(
hint: "Enter Phone number to Register",
onChanged: (v) {
@@ -42,7 +81,7 @@ class RegisterPage extends StatelessWidget {
title: "Continue",
width: double.infinity,
onPressed: () {
- performBasicOtp(context);
+ if (validation()) performBasicOtp(context);
},
),
],
@@ -53,36 +92,40 @@ class RegisterPage extends StatelessWidget {
Future performBasicOtp(BuildContext context) async {
Utils.showLoading(context);
- BasicOtp basicOtp = await UserApiClent().basicOtp(phoneNum);
+ BasicOtp basicOtp = await UserApiClent().basicOtp(countryCode + phoneNum,roleId: role);
Utils.hideLoading(context);
if (basicOtp.messageStatus == 1) {
showMDialog(context, child: OtpDialog(
onClick: (String code) async {
pop(context);
Utils.showLoading(context);
- RegisterUser user = await UserApiClent().basicVerify(phoneNum, code, basicOtp.data!.userToken ?? "");
+ RegisterUser user = await UserApiClent().basicVerify(countryCode + phoneNum, code, basicOtp.data!.userToken ?? "");
Utils.hideLoading(context);
if (user.messageStatus == 1) {
Utils.showToast(user.message ?? "");
- navigateReplaceWithName(context, AppRoutes.completeProfile,arguments: user);
+ navigateReplaceWithName(context, AppRoutes.completeProfile, arguments: user);
} else {
Utils.showToast(user.message ?? "");
}
- // delay(300).then(
- // (value) => showMDialog(
- // context,
- // child: MessageDialog(
- // title: "Phone Number Verified",
- // onClick: () {
- // navigateWithName(context, AppRoutes.completeProfile);
- // },
- // ),
- // ),
- // );
},
));
} else {
Utils.showToast(basicOtp.message ?? "");
}
}
+
+ bool validation() {
+ bool isValid = true;
+ if (role == -1) {
+ Utils.showToast("Please select Provider Role");
+ isValid = false;
+ } else if (countryCode.isEmpty) {
+ Utils.showToast("Please select Country Code");
+ isValid = false;
+ } else if (phoneNum.isEmpty) {
+ Utils.showToast("Please add Phone No");
+ isValid = false;
+ }
+ return isValid;
+ }
}
diff --git a/lib/widgets/dropdown/dropdow_field.dart b/lib/widgets/dropdown/dropdow_field.dart
index 3edb326..0aa6239 100644
--- a/lib/widgets/dropdown/dropdow_field.dart
+++ b/lib/widgets/dropdown/dropdow_field.dart
@@ -3,18 +3,31 @@ import 'package:car_provider_app/utils/utils.dart';
import 'package:car_provider_app/widgets/extensions/string_extensions.dart';
import 'package:flutter/material.dart';
+class DropValue {
+ int id;
+ String value;
+ String subValue;
+
+ DropValue(this.id, this.value,this.subValue);
+}
+
class DropdownField extends StatefulWidget {
String? hint;
- List? list;
+ List? list;
+ Function(DropValue) onSelect;
- DropdownField({this.hint, this.list});
+ DropdownField(this.onSelect, {this.hint, this.list});
@override
State createState() => _DropdownFieldState();
}
class _DropdownFieldState extends State {
- String? dropdownValue;
+ DropValue? dropdownValue;
+ List defaultV = [
+ new DropValue(1, "One",""),
+ new DropValue(2, "Two",""),
+ ];
@override
Widget build(BuildContext context) {
@@ -27,7 +40,7 @@ class _DropdownFieldState extends State {
),
margin: EdgeInsets.all(2),
padding: EdgeInsets.only(left: 8, right: 8),
- child: DropdownButton(
+ child: DropdownButton(
value: dropdownValue,
icon: const Icon(Icons.keyboard_arrow_down_sharp),
elevation: 16,
@@ -36,27 +49,21 @@ class _DropdownFieldState extends State {
iconDisabledColor: borderColor,
isExpanded: true,
style: const TextStyle(color: Colors.black),
- hint: (widget.hint ?? "").toText24(color: borderColor),
+ hint: (widget.hint ?? "").toText12(color: borderColor),
underline: Container(
height: 0,
),
- onChanged: (String? newValue) {
+ onChanged: (DropValue? newValue) {
setState(() {
dropdownValue = newValue!;
+ widget.onSelect(newValue);
});
},
- items: (widget.list ??
- [
- 'One',
- 'Two',
- 'Free',
- 'Four',
- ])
- .map>(
- (String value) {
- return DropdownMenuItem(
+ items: (widget.list ?? defaultV).map>(
+ (DropValue value) {
+ return DropdownMenuItem(
value: value,
- child: value.toText24(),
+ child: value.value.toText12(),
);
},
).toList(),
diff --git a/pubspec.lock b/pubspec.lock
index aa18217..66b0312 100644
--- a/pubspec.lock
+++ b/pubspec.lock
@@ -99,6 +99,13 @@ packages:
url: "https://pub.dartlang.org"
source: hosted
version: "6.1.2"
+ file_picker:
+ dependency: "direct main"
+ description:
+ name: file_picker
+ url: "https://pub.dartlang.org"
+ source: hosted
+ version: "4.4.0"
flutter:
dependency: "direct main"
description: flutter
@@ -116,13 +123,20 @@ packages:
description: flutter
source: sdk
version: "0.0.0"
+ flutter_plugin_android_lifecycle:
+ dependency: transitive
+ description:
+ name: flutter_plugin_android_lifecycle
+ url: "https://pub.dartlang.org"
+ source: hosted
+ version: "2.0.5"
flutter_svg:
dependency: "direct main"
description:
name: flutter_svg
url: "https://pub.dartlang.org"
source: hosted
- version: "0.22.0"
+ version: "1.0.3"
flutter_test:
dependency: "direct dev"
description: flutter
@@ -216,14 +230,14 @@ packages:
name: path_drawing
url: "https://pub.dartlang.org"
source: hosted
- version: "0.5.1+1"
+ version: "1.0.0"
path_parsing:
dependency: transitive
description:
name: path_parsing
url: "https://pub.dartlang.org"
source: hosted
- version: "0.2.1"
+ version: "1.0.0"
path_provider:
dependency: "direct main"
description:
diff --git a/pubspec.yaml b/pubspec.yaml
index 61ec9bf..cc926b4 100644
--- a/pubspec.yaml
+++ b/pubspec.yaml
@@ -40,10 +40,12 @@ dependencies:
easy_localization: ^3.0.0
http: ^0.13.3
permission_handler: 7.1.0
- flutter_svg: ^0.22.0
+ flutter_svg: ^1.0.3
sizer: ^2.0.15
fluttertoast: ^8.0.8
shared_preferences: ^2.0.6
+ file_picker: ^4.4.0
+
dev_dependencies:
flutter_test: