diff --git a/android/build/reports/problems/problems-report.html b/android/build/reports/problems/problems-report.html
new file mode 100644
index 0000000..5294026
--- /dev/null
+++ b/android/build/reports/problems/problems-report.html
@@ -0,0 +1,663 @@
+
+
+
+
+
+
+
+
+
+
+
+
+ Gradle Configuration Cache
+
+
+
+
+
+
+ Loading...
+
+
+
+
+
+
+
diff --git a/ios/Podfile.lock b/ios/Podfile.lock
index ce821a3..60af84f 100644
--- a/ios/Podfile.lock
+++ b/ios/Podfile.lock
@@ -45,6 +45,9 @@ PODS:
- SDWebImage (5.21.3):
- SDWebImage/Core (= 5.21.3)
- SDWebImage/Core (5.21.3)
+ - shared_preferences_foundation (0.0.1):
+ - Flutter
+ - FlutterMacOS
- SwiftyGif (5.4.5)
DEPENDENCIES:
@@ -53,6 +56,7 @@ DEPENDENCIES:
- flutter_native_splash (from `.symlinks/plugins/flutter_native_splash/ios`)
- mobile_scanner (from `.symlinks/plugins/mobile_scanner/darwin`)
- path_provider_foundation (from `.symlinks/plugins/path_provider_foundation/darwin`)
+ - shared_preferences_foundation (from `.symlinks/plugins/shared_preferences_foundation/darwin`)
SPEC REPOS:
trunk:
@@ -72,16 +76,19 @@ EXTERNAL SOURCES:
:path: ".symlinks/plugins/mobile_scanner/darwin"
path_provider_foundation:
:path: ".symlinks/plugins/path_provider_foundation/darwin"
+ shared_preferences_foundation:
+ :path: ".symlinks/plugins/shared_preferences_foundation/darwin"
SPEC CHECKSUMS:
DKImagePickerController: 946cec48c7873164274ecc4624d19e3da4c1ef3c
DKPhotoGallery: b3834fecb755ee09a593d7c9e389d8b5d6deed60
- file_picker: b159e0c068aef54932bb15dc9fd1571818edaf49
+ file_picker: a0560bc09d61de87f12d246fc47d2119e6ef37be
Flutter: cabc95a1d2626b1b06e7179b784ebcf0c0cde467
- flutter_native_splash: df59bb2e1421aa0282cb2e95618af4dcb0c56c29
- mobile_scanner: 77265f3dc8d580810e91849d4a0811a90467ed5e
- path_provider_foundation: 0b743cbb62d8e47eab856f09262bb8c1ddcfe6ba
+ flutter_native_splash: c32d145d68aeda5502d5f543ee38c192065986cf
+ mobile_scanner: 9157936403f5a0644ca3779a38ff8404c5434a93
+ path_provider_foundation: bb55f6dbba17d0dccd6737fe6f7f34fbd0376880
SDWebImage: 16309af6d214ba3f77a7c6f6fdda888cb313a50a
+ shared_preferences_foundation: 7036424c3d8ec98dfe75ff1667cb0cd531ec82bb
SwiftyGif: 706c60cf65fa2bc5ee0313beece843c8eb8194d4
PODFILE CHECKSUM: 251cb053df7158f337c0712f2ab29f4e0fa474ce
diff --git a/lib/all_bloc_poviders/all_bloc_providers.dart b/lib/all_bloc_poviders/all_bloc_providers.dart
index 6be4eeb..5a9ca79 100644
--- a/lib/all_bloc_poviders/all_bloc_providers.dart
+++ b/lib/all_bloc_poviders/all_bloc_providers.dart
@@ -6,6 +6,20 @@ import '../login/blocs/reset_password/reset_password_bloc.dart';
import '../splash/bloc/splash_bloc.dart';
import '../profile/blocs/profile/profile_bloc.dart';
import '../profile/repository/profile_repository.dart';
+import '../support/blocs/support_details/support_details_bloc.dart';
+import '../support/repository/support_details_repository.dart';
+import '../support/blocs/raise_ticket/raise_ticket_bloc.dart';
+import '../support/repository/raise_ticket_repository.dart';
+import '../scan/bloc/submit_qr_code/submit_qr_code_bloc.dart';
+import '../scan/repository/submit_qr_code_repository.dart';
+import '../scan_history/blocs/scan_history/scan_history_bloc.dart';
+
+import '../scan_history/blocs/scan_history_details/scan_history_details_bloc.dart';
+import '../scan_history/repositories/scan_history_repository.dart';
+import '../scan/bloc/recent_scan_history/recent_scan_history_bloc.dart';
+import '../scan/repository/recent_scan_history_repository.dart';
+
+
class AllBlocProviders {
AllBlocProviders._(); // Private constructor — not meant to be instantiated
@@ -32,6 +46,29 @@ class AllBlocProviders {
BlocProvider(
create: (_) => ProfileBloc(profileRepository: ProfileRepository()),
),
+ // ─── Support ─────────────────────────────────────────────────────────
+ BlocProvider(
+ create: (_) => SupportDetailsBloc(repository: SupportDetailsRepository()),
+ ),
+ BlocProvider(
+ create: (_) => RaiseTicketBloc(raiseTicketRepository: RaiseTicketRepository()),
+ ),
+ // ─── Scan History ────────────────────────────────────────────────────
+ BlocProvider(
+ create: (_) => ScanHistoryBloc(repository: ScanHistoryRepository(),),
+ ),
+ BlocProvider(
+ create: (_) => ScanHistoryDetailsBloc(ScanHistoryRepository()),
+ ),
+ BlocProvider(
+ create: (_) => RecentScanHistoryBloc(RecentScanHistoryRepository()),
+ ),
+ BlocProvider(
+ create: (_) => SubmitQrCodeBloc(repository: SubmitQrCodeRepository()),
+ ),
];
+
+
+
}
}
\ No newline at end of file
diff --git a/lib/core/app_router.dart b/lib/core/app_router.dart
index c22212f..d1add29 100644
--- a/lib/core/app_router.dart
+++ b/lib/core/app_router.dart
@@ -61,9 +61,10 @@ class AppRouter {
case splashScreen:
return MaterialPageRoute(builder: (_) => const SplashScreen());
case scanHistoryDetailPage:
+ final passId = settings.arguments as int? ?? 0;
return MaterialPageRoute(
- builder: (_) => const ScanHistoryDetailPage(
- passId: 'P214125125',
+ builder: (_) => ScanHistoryDetailPage(
+ passId: passId,
));
case selectedTimeSlotPage:
return MaterialPageRoute(builder: (_) => const SelectedTimeSlotPage());
diff --git a/lib/local_peference/local_preference.dart b/lib/local_peference/local_preference.dart
index 8bc55de..8573001 100644
--- a/lib/local_peference/local_preference.dart
+++ b/lib/local_peference/local_preference.dart
@@ -44,6 +44,11 @@ class LocalPreference {
return prefs.getString(_keyAccessToken) ?? "";
}
+ static Future clearAccessToken() async {
+ final SharedPreferences prefs = await SharedPreferences.getInstance();
+ await prefs.remove(_keyAccessToken);
+ }
+
// -------------------- REFRESH TOKEN --------------------
static Future setRefreshToken(String token) async {
diff --git a/lib/login/blocs/forgot_password_bloc.dart b/lib/login/blocs/forgot_password_bloc.dart
deleted file mode 100644
index 7d1e848..0000000
--- a/lib/login/blocs/forgot_password_bloc.dart
+++ /dev/null
@@ -1,82 +0,0 @@
-import 'package:flutter_bloc/flutter_bloc.dart';
-
-// ---------------- EVENTS ----------------
-abstract class ForgotPasswordEvent {}
-
-class EmailChanged extends ForgotPasswordEvent {
- final String email;
- EmailChanged(this.email);
-}
-
-class SendResetLink extends ForgotPasswordEvent {}
-
-// ---------------- STATE ----------------
-class ForgotPasswordState {
- final String email;
- final bool isValidEmail;
- final bool isLoading;
- final bool isSuccess;
- final String message;
-
- const ForgotPasswordState({
- required this.email,
- required this.isValidEmail,
- required this.isLoading,
- required this.isSuccess,
- required this.message,
- });
-
- ForgotPasswordState copyWith({
- String? email,
- bool? isValidEmail,
- bool? isLoading,
- bool? isSuccess,
- String? message,
- }) {
- return ForgotPasswordState(
- email: email ?? this.email,
- isValidEmail: isValidEmail ?? this.isValidEmail,
- isLoading: isLoading ?? this.isLoading,
- isSuccess: isSuccess ?? this.isSuccess,
- message: message ?? this.message,
- );
- }
-
- factory ForgotPasswordState.initial() => const ForgotPasswordState(
- email: '',
- isValidEmail: false,
- isLoading: false,
- isSuccess: false,
- message: '',
- );
-}
-
-// ---------------- BLOC ----------------
-class ForgotPasswordBloc
- extends Bloc {
- ForgotPasswordBloc() : super(ForgotPasswordState.initial()) {
- // when email changes
- on((event, emit) {
- final isValid = _isValidEmail(event.email);
- emit(state.copyWith(email: event.email, isValidEmail: isValid));
- });
-
- // when button clicked
- on((event, emit) async {
- if (!state.isValidEmail) return;
-
- emit(state.copyWith(isLoading: true, message: ''));
- await Future.delayed(const Duration(seconds: 2)); // simulate API delay
- emit(state.copyWith(
- isLoading: false,
- isSuccess: true,
- message: 'Reset link sent successfully!',
- ));
- });
- }
-
- bool _isValidEmail(String email) {
- final regex = RegExp(r'^[\w-\.]+@([\w-]+\.)+[\w-]{2,4}$');
- return regex.hasMatch(email);
- }
-}
diff --git a/lib/login/blocs/login/login_bloc.dart b/lib/login/blocs/login/login_bloc.dart
index 91a7724..dc0d587 100644
--- a/lib/login/blocs/login/login_bloc.dart
+++ b/lib/login/blocs/login/login_bloc.dart
@@ -1,7 +1,8 @@
import 'package:equatable/equatable.dart';
+import 'package:flutter/foundation.dart';
import 'package:flutter_bloc/flutter_bloc.dart';
import '../../../local_peference/local_preference.dart';
-import '../../models/login.dart';
+import '../../models/login_model.dart';
import '../../repositories/login_repository.dart';
part 'login_event.dart';
part 'login_state.dart';
@@ -32,7 +33,10 @@ class LoginBloc extends Bloc {
password: event.password,
rememberMe: event.rememberMe,
);
-
+ if (kDebugMode) {
+ print('🔍 Login response accessToken: ${loginData.accessToken}');
+ print('🔍 Login response refreshToken: ${loginData.refreshToken}');
+ }
// ── Save to local preference ──────────────────────────────────────
await Future.wait([
LocalPreference.setAccessToken(loginData.accessToken),
diff --git a/lib/login/blocs/login_bloc.dart b/lib/login/blocs/login_bloc.dart
deleted file mode 100644
index e69de29..0000000
diff --git a/lib/login/blocs/otp_bloc.dart b/lib/login/blocs/otp_bloc.dart
deleted file mode 100644
index 96cfcfd..0000000
--- a/lib/login/blocs/otp_bloc.dart
+++ /dev/null
@@ -1,103 +0,0 @@
-import 'package:flutter_bloc/flutter_bloc.dart';
-
-// --------------------- EVENTS ---------------------
-abstract class OtpEvent {}
-
-/// Triggered when user types or pastes OTP
-class OtpChanged extends OtpEvent {
- final String otp;
- OtpChanged(this.otp);
-}
-
-/// Triggered when user presses Verify button
-class OtpVerify extends OtpEvent {}
-
-/// (Optional for later) Triggered when user taps "Resend OTP"
-class OtpResend extends OtpEvent {}
-
-
-// --------------------- STATE ---------------------
-class OtpState {
- final String otp;
- final bool isVerified;
- final bool isLoading;
- final bool isResending;
- final String message;
-
- /// Computed property to know if OTP input is complete (6 digits)
- bool get isOtpFilled => otp.length == 6;
-
- const OtpState({
- required this.otp,
- required this.isVerified,
- required this.isLoading,
- required this.isResending,
- required this.message,
- });
-
- OtpState copyWith({
- String? otp,
- bool? isVerified,
- bool? isLoading,
- bool? isResending,
- String? message,
- }) {
- return OtpState(
- otp: otp ?? this.otp,
- isVerified: isVerified ?? this.isVerified,
- isLoading: isLoading ?? this.isLoading,
- isResending: isResending ?? this.isResending,
- message: message ?? this.message,
- );
- }
-
- factory OtpState.initial() => const OtpState(
- otp: '',
- isVerified: false,
- isLoading: false,
- isResending: false,
- message: '',
- );
-}
-
-
-// --------------------- BLOC ---------------------
-class OtpBloc extends Bloc {
- OtpBloc() : super(OtpState.initial()) {
- // Handle typing input
- on((event, emit) {
- emit(state.copyWith(otp: event.otp, message: ''));
- });
-
- // Handle Verify
- on((event, emit) async {
- if (!state.isOtpFilled) return; // no action if OTP incomplete
-
- emit(state.copyWith(isLoading: true, message: ''));
-
- await Future.delayed(const Duration(seconds: 2)); // simulate API delay
-
- // Mock success condition — replace with API later
- if (state.otp == "123456") {
- emit(state.copyWith(
- isVerified: true,
- isLoading: false,
- message: "OTP verified successfully!",
- ));
- } else {
- emit(state.copyWith(
- isVerified: false,
- isLoading: false,
- message: "Invalid OTP. Please try again.",
- ));
- }
- });
-
- // Handle Resend OTP (optional for later)
- on((event, emit) async {
- emit(state.copyWith(isResending: true, message: 'Resending OTP...'));
- await Future.delayed(const Duration(seconds: 3)); // simulate resend
- emit(state.copyWith(isResending: false, message: 'OTP resent successfully!'));
- });
- }
-}
diff --git a/lib/login/blocs/reset_password_bloc.dart b/lib/login/blocs/reset_password_bloc.dart
deleted file mode 100644
index f206d8e..0000000
--- a/lib/login/blocs/reset_password_bloc.dart
+++ /dev/null
@@ -1,93 +0,0 @@
-import 'package:flutter_bloc/flutter_bloc.dart';
-
-/// EVENTS
-abstract class ResetPasswordEvent {}
-
-class PasswordChanged extends ResetPasswordEvent {
- final String password;
- PasswordChanged(this.password);
-}
-
-class ConfirmPasswordChanged extends ResetPasswordEvent {
- final String confirmPassword;
- ConfirmPasswordChanged(this.confirmPassword);
-}
-
-/// STATE
-class ResetPasswordState {
- final String password;
- final String confirmPassword;
- final bool hasMinLength;
- final bool hasUppercase;
- final bool hasNumber;
- final int strengthLevel; // 0–4 based on password strength
-
- const ResetPasswordState({
- required this.password,
- required this.confirmPassword,
- required this.hasMinLength,
- required this.hasUppercase,
- required this.hasNumber,
- required this.strengthLevel,
- });
-
- factory ResetPasswordState.initial() => const ResetPasswordState(
- password: '',
- confirmPassword: '',
- hasMinLength: false,
- hasUppercase: false,
- hasNumber: false,
- strengthLevel: 0,
- );
-
- ResetPasswordState copyWith({
- String? password,
- String? confirmPassword,
- bool? hasMinLength,
- bool? hasUppercase,
- bool? hasNumber,
- int? strengthLevel,
- }) {
- return ResetPasswordState(
- password: password ?? this.password,
- confirmPassword: confirmPassword ?? this.confirmPassword,
- hasMinLength: hasMinLength ?? this.hasMinLength,
- hasUppercase: hasUppercase ?? this.hasUppercase,
- hasNumber: hasNumber ?? this.hasNumber,
- strengthLevel: strengthLevel ?? this.strengthLevel,
- );
- }
-}
-
-/// BLOC
-class ResetPasswordBloc extends Bloc {
- ResetPasswordBloc() : super(ResetPasswordState.initial()) {
- on((event, emit) {
- final pwd = event.password;
- final hasMin = pwd.length >= 8;
- final hasUp = pwd.contains(RegExp(r'[A-Z]'));
- final hasNum = pwd.contains(RegExp(r'[0-9]'));
-
- // count how many validations passed (max 3)
- int passed = [hasMin, hasUp, hasNum].where((e) => e).length;
-
- // convert to 4-box level (0–4)
- int level = 0;
- if (passed == 1) level = 1;
- if (passed == 2) level = 2;
- if (passed == 3) level = 4; // all conditions passed => full bar
-
- emit(state.copyWith(
- password: pwd,
- hasMinLength: hasMin,
- hasUppercase: hasUp,
- hasNumber: hasNum,
- strengthLevel: level,
- ));
- });
-
- on((event, emit) {
- emit(state.copyWith(confirmPassword: event.confirmPassword));
- });
- }
-}
diff --git a/lib/login/blocs/verify_otp/verify_otp_bloc.dart b/lib/login/blocs/verify_otp/verify_otp_bloc.dart
index 242e871..d5fd623 100644
--- a/lib/login/blocs/verify_otp/verify_otp_bloc.dart
+++ b/lib/login/blocs/verify_otp/verify_otp_bloc.dart
@@ -11,9 +11,14 @@ class VerifyOtpBloc extends Bloc {
VerifyOtpBloc({OtpRepository? otpRepository})
: _otpRepository = otpRepository ?? OtpRepository(),
super(const VerifyOtpState()) {
+ on(_onOtpChanged);
on(_onVerifyOtpSubmitted);
}
+ void _onOtpChanged(OtpChanged event, Emitter emit) {
+ emit(state.copyWith(otp: event.otp));
+ }
+
Future _onVerifyOtpSubmitted(
VerifyOtpSubmitted event,
Emitter emit,
diff --git a/lib/login/blocs/verify_otp/verify_otp_event.dart b/lib/login/blocs/verify_otp/verify_otp_event.dart
index 0abe38d..bbc8fd0 100644
--- a/lib/login/blocs/verify_otp/verify_otp_event.dart
+++ b/lib/login/blocs/verify_otp/verify_otp_event.dart
@@ -7,6 +7,15 @@ abstract class VerifyOtpEvent extends Equatable {
List