diff --git a/android/app/build.gradle.kts b/android/app/build.gradle.kts index 19de2ad..005d2b7 100644 --- a/android/app/build.gradle.kts +++ b/android/app/build.gradle.kts @@ -1,12 +1,12 @@ plugins { - id("com.android.application") id("kotlin-android") - // The Flutter Gradle Plugin must be applied after the Android and Kotlin Gradle plugins. + id("com.android.application") + id("com.google.gms.google-services") id("dev.flutter.flutter-gradle-plugin") } android { - namespace = "com.example.yimaru_app" + namespace = "com.yimaru.lms.app" compileSdk = flutter.compileSdkVersion ndkVersion = flutter.ndkVersion @@ -15,25 +15,24 @@ android { targetCompatibility = JavaVersion.VERSION_17 } - kotlinOptions { - jvmTarget = JavaVersion.VERSION_17.toString() + kotlin { + compilerOptions { + jvmTarget.set(org.jetbrains.kotlin.gradle.dsl.JvmTarget.JVM_17) + } } + defaultConfig { - // TODO: Specify your own unique Application ID (https://developer.android.com/studio/build/application-id.html). - applicationId = "com.example.yimaru_app" - // You can update the following values to match your application needs. - // For more information, see: https://flutter.dev/to/review-gradle-config. minSdk = flutter.minSdkVersion - targetSdk = flutter.targetSdkVersion + applicationId = "com.yimaru.lms.app" versionCode = flutter.versionCode versionName = flutter.versionName + targetSdk = flutter.targetSdkVersion + } buildTypes { release { - // TODO: Add your own signing config for the release build. - // Signing with the debug keys for now, so `flutter run --release` works. signingConfig = signingConfigs.getByName("debug") } } diff --git a/android/app/google-services.json b/android/app/google-services.json new file mode 100644 index 0000000..cd2ee71 --- /dev/null +++ b/android/app/google-services.json @@ -0,0 +1,51 @@ +{ + "project_info": { + "project_number": "574860813475", + "project_id": "yimaru-lms-e834e", + "storage_bucket": "yimaru-lms-e834e.firebasestorage.app" + }, + "client": [ + { + "client_info": { + "mobilesdk_app_id": "1:574860813475:android:cd7fa6cf3a0527d97acb16", + "android_client_info": { + "package_name": "com.yimaru.lms.app" + } + }, + "oauth_client": [ + { + "client_id": "574860813475-01gh5tk0bu5bgj68r02sgh5pk5greoku.apps.googleusercontent.com", + "client_type": 1, + "android_info": { + "package_name": "com.yimaru.lms.app", + "certificate_hash": "fc91f52846d27c62bba3e16bc98982fb9953eca1" + } + }, + { + "client_id": "574860813475-631s3mo8ha2qc2jeb5e2aosn0967niik.apps.googleusercontent.com", + "client_type": 1, + "android_info": { + "package_name": "com.yimaru.lms.app", + "certificate_hash": "928ead08b5e39d6a861a55ae7cceb8c402d1ee7a" + } + } + ], + "api_key": [ + { + "current_key": "AIzaSyC7QlhcuSNte49CERnRKPrQbyLbwErIRmk" + } + ], + "services": { + "appinvite_service": { + "other_platform_oauth_client": [ + { + "client_id": "574860813475-n5o17gpprdqmhcml99tiqhafb17rob0r.apps.googleusercontent.com", + "client_type": 3 + } + ] + } + } + } + ], + "configuration_version": "1" +} \ No newline at end of file diff --git a/android/app/src/main/AndroidManifest.xml b/android/app/src/main/AndroidManifest.xml index 1dc40a9..e39aa8a 100644 --- a/android/app/src/main/AndroidManifest.xml +++ b/android/app/src/main/AndroidManifest.xml @@ -7,7 +7,7 @@ + + + + diff --git a/assets/icons/a_2.svg b/assets/icons/a_2.svg new file mode 100644 index 0000000..9bdbd2e --- /dev/null +++ b/assets/icons/a_2.svg @@ -0,0 +1,5 @@ + + + + + diff --git a/assets/icons/b1.svg b/assets/icons/b1.svg deleted file mode 100644 index 4a75083..0000000 --- a/assets/icons/b1.svg +++ /dev/null @@ -1,10 +0,0 @@ - - - - - - - - - - diff --git a/assets/icons/b_1.svg b/assets/icons/b_1.svg new file mode 100644 index 0000000..85f988e --- /dev/null +++ b/assets/icons/b_1.svg @@ -0,0 +1,5 @@ + + + + + diff --git a/assets/icons/b_2.svg b/assets/icons/b_2.svg new file mode 100644 index 0000000..40dfb5d --- /dev/null +++ b/assets/icons/b_2.svg @@ -0,0 +1,5 @@ + + + + + diff --git a/firebase.json b/firebase.json new file mode 100644 index 0000000..4d7ff66 --- /dev/null +++ b/firebase.json @@ -0,0 +1 @@ +{"flutter":{"platforms":{"android":{"default":{"projectId":"yimaru-lms-e834e","appId":"1:574860813475:android:cd7fa6cf3a0527d97acb16","fileOutput":"android/app/google-services.json"}},"dart":{"lib/firebase_options.dart":{"projectId":"yimaru-lms-e834e","configurations":{"android":"1:574860813475:android:cd7fa6cf3a0527d97acb16","ios":"1:574860813475:ios:3ac9f7c4ae1771287acb16"}}}}}} \ No newline at end of file diff --git a/ios/Runner.xcodeproj/project.pbxproj b/ios/Runner.xcodeproj/project.pbxproj index 79e3510..f72da0a 100644 --- a/ios/Runner.xcodeproj/project.pbxproj +++ b/ios/Runner.xcodeproj/project.pbxproj @@ -368,7 +368,7 @@ "$(inherited)", "@executable_path/Frameworks", ); - PRODUCT_BUNDLE_IDENTIFIER = com.example.yimaruApp; + PRODUCT_BUNDLE_IDENTIFIER = com.yimaru.lms.app; PRODUCT_NAME = "$(TARGET_NAME)"; SWIFT_OBJC_BRIDGING_HEADER = "Runner/Runner-Bridging-Header.h"; SWIFT_VERSION = 5.0; @@ -384,7 +384,7 @@ CURRENT_PROJECT_VERSION = 1; GENERATE_INFOPLIST_FILE = YES; MARKETING_VERSION = 1.0; - PRODUCT_BUNDLE_IDENTIFIER = com.example.yimaruApp.RunnerTests; + PRODUCT_BUNDLE_IDENTIFIER = com.yimaru.lms.app.RunnerTests; PRODUCT_NAME = "$(TARGET_NAME)"; SWIFT_ACTIVE_COMPILATION_CONDITIONS = DEBUG; SWIFT_OPTIMIZATION_LEVEL = "-Onone"; @@ -401,7 +401,7 @@ CURRENT_PROJECT_VERSION = 1; GENERATE_INFOPLIST_FILE = YES; MARKETING_VERSION = 1.0; - PRODUCT_BUNDLE_IDENTIFIER = com.example.yimaruApp.RunnerTests; + PRODUCT_BUNDLE_IDENTIFIER = com.yimaru.lms.app.RunnerTests; PRODUCT_NAME = "$(TARGET_NAME)"; SWIFT_VERSION = 5.0; TEST_HOST = "$(BUILT_PRODUCTS_DIR)/Runner.app/$(BUNDLE_EXECUTABLE_FOLDER_PATH)/Runner"; @@ -416,7 +416,7 @@ CURRENT_PROJECT_VERSION = 1; GENERATE_INFOPLIST_FILE = YES; MARKETING_VERSION = 1.0; - PRODUCT_BUNDLE_IDENTIFIER = com.example.yimaruApp.RunnerTests; + PRODUCT_BUNDLE_IDENTIFIER = com.yimaru.lms.app.RunnerTests; PRODUCT_NAME = "$(TARGET_NAME)"; SWIFT_VERSION = 5.0; TEST_HOST = "$(BUILT_PRODUCTS_DIR)/Runner.app/$(BUNDLE_EXECUTABLE_FOLDER_PATH)/Runner"; @@ -547,7 +547,7 @@ "$(inherited)", "@executable_path/Frameworks", ); - PRODUCT_BUNDLE_IDENTIFIER = com.example.yimaruApp; + PRODUCT_BUNDLE_IDENTIFIER = com.yimaru.lms.app; PRODUCT_NAME = "$(TARGET_NAME)"; SWIFT_OBJC_BRIDGING_HEADER = "Runner/Runner-Bridging-Header.h"; SWIFT_OPTIMIZATION_LEVEL = "-Onone"; @@ -569,7 +569,7 @@ "$(inherited)", "@executable_path/Frameworks", ); - PRODUCT_BUNDLE_IDENTIFIER = com.example.yimaruApp; + PRODUCT_BUNDLE_IDENTIFIER = com.yimaru.lms.app; PRODUCT_NAME = "$(TARGET_NAME)"; SWIFT_OBJC_BRIDGING_HEADER = "Runner/Runner-Bridging-Header.h"; SWIFT_VERSION = 5.0; diff --git a/lib/app/app.dart b/lib/app/app.dart index 2b42eff..0130a88 100644 --- a/lib/app/app.dart +++ b/lib/app/app.dart @@ -33,6 +33,8 @@ import 'package:yimaru_app/ui/views/learn_lesson/learn_lesson_view.dart'; import 'package:yimaru_app/ui/views/failure/failure_view.dart'; import 'package:yimaru_app/services/permission_handler_service.dart'; import 'package:yimaru_app/services/image_picker_service.dart'; +import 'package:yimaru_app/services/google_auth_service.dart'; +import 'package:yimaru_app/services/image_downloader_service.dart'; // @stacked-import @StackedApp( @@ -74,6 +76,8 @@ import 'package:yimaru_app/services/image_picker_service.dart'; LazySingleton(classType: StatusCheckerService), LazySingleton(classType: PermissionHandlerService), LazySingleton(classType: ImagePickerService), + LazySingleton(classType: GoogleAuthService), + LazySingleton(classType: ImageDownloaderService), // @stacked-service ], bottomsheets: [ diff --git a/lib/app/app.locator.dart b/lib/app/app.locator.dart index ccdd10f..77ac6ff 100644 --- a/lib/app/app.locator.dart +++ b/lib/app/app.locator.dart @@ -14,6 +14,8 @@ import 'package:stacked_shared/stacked_shared.dart'; import '../services/api_service.dart'; import '../services/authentication_service.dart'; import '../services/dio_service.dart'; +import '../services/google_auth_service.dart'; +import '../services/image_downloader_service.dart'; import '../services/image_picker_service.dart'; import '../services/permission_handler_service.dart'; import '../services/secure_storage_service.dart'; @@ -40,4 +42,6 @@ Future setupLocator({ locator.registerLazySingleton(() => StatusCheckerService()); locator.registerLazySingleton(() => PermissionHandlerService()); locator.registerLazySingleton(() => ImagePickerService()); + locator.registerLazySingleton(() => GoogleAuthService()); + locator.registerLazySingleton(() => ImageDownloaderService()); } diff --git a/lib/firebase_options.dart b/lib/firebase_options.dart new file mode 100644 index 0000000..f2470b8 --- /dev/null +++ b/lib/firebase_options.dart @@ -0,0 +1,70 @@ +// File generated by FlutterFire CLI. +// ignore_for_file: type=lint +import 'package:firebase_core/firebase_core.dart' show FirebaseOptions; +import 'package:flutter/foundation.dart' + show defaultTargetPlatform, kIsWeb, TargetPlatform; + +/// Default [FirebaseOptions] for use with your Firebase apps. +/// +/// Example: +/// ```dart +/// import 'firebase_options.dart'; +/// // ... +/// await Firebase.initializeApp( +/// options: DefaultFirebaseOptions.currentPlatform, +/// ); +/// ``` +class DefaultFirebaseOptions { + static FirebaseOptions get currentPlatform { + if (kIsWeb) { + throw UnsupportedError( + 'DefaultFirebaseOptions have not been configured for web - ' + 'you can reconfigure this by running the FlutterFire CLI again.', + ); + } + switch (defaultTargetPlatform) { + case TargetPlatform.android: + return android; + case TargetPlatform.iOS: + return ios; + case TargetPlatform.macOS: + throw UnsupportedError( + 'DefaultFirebaseOptions have not been configured for macos - ' + 'you can reconfigure this by running the FlutterFire CLI again.', + ); + case TargetPlatform.windows: + throw UnsupportedError( + 'DefaultFirebaseOptions have not been configured for windows - ' + 'you can reconfigure this by running the FlutterFire CLI again.', + ); + case TargetPlatform.linux: + throw UnsupportedError( + 'DefaultFirebaseOptions have not been configured for linux - ' + 'you can reconfigure this by running the FlutterFire CLI again.', + ); + default: + throw UnsupportedError( + 'DefaultFirebaseOptions are not supported for this platform.', + ); + } + } + + static const FirebaseOptions android = FirebaseOptions( + apiKey: 'AIzaSyC7QlhcuSNte49CERnRKPrQbyLbwErIRmk', + appId: '1:574860813475:android:cd7fa6cf3a0527d97acb16', + messagingSenderId: '574860813475', + projectId: 'yimaru-lms-e834e', + storageBucket: 'yimaru-lms-e834e.firebasestorage.app', + ); + + static const FirebaseOptions ios = FirebaseOptions( + apiKey: 'AIzaSyBBcQ17JB6RBTjD7G7mh6Xf_FMUGxP5cC8', + appId: '1:574860813475:ios:3ac9f7c4ae1771287acb16', + messagingSenderId: '574860813475', + projectId: 'yimaru-lms-e834e', + storageBucket: 'yimaru-lms-e834e.firebasestorage.app', + androidClientId: + '574860813475-01gh5tk0bu5bgj68r02sgh5pk5greoku.apps.googleusercontent.com', + iosBundleId: 'com.yimaru.lms.app', + ); +} diff --git a/lib/models/assessment.dart b/lib/models/assessment.dart index e1cc5e5..9a6da65 100644 --- a/lib/models/assessment.dart +++ b/lib/models/assessment.dart @@ -1,17 +1,35 @@ import 'package:json_annotation/json_annotation.dart'; import 'package:yimaru_app/models/option.dart'; -import 'package:yimaru_app/models/question.dart'; part 'assessment.g.dart'; @JsonSerializable() class Assessment { - @JsonKey(name: 'Question') - final Question? question; + final int? id; + + final int? points; + + final String? status; + + @JsonKey(name: 'question_type') + final String? questionType; + + @JsonKey(name: 'question_text') + final String? questionText; + + @JsonKey(name: 'difficulty_level') + final String? difficultyLevel; - @JsonKey(name: 'Options') final List