Browse Source

Merge pull request 'feature/centrifugo' (#17) from feature/centrifugo into develop

Reviewed-on: #17
pull/18/head
amirreza.chegini 2 weeks ago
parent
commit
bfa063240c
  1. 10
      ios/Podfile.lock
  2. 9
      lib/core/constants/my_api.dart
  3. 19
      lib/core/error_handler/error_handler.dart
  4. 1
      lib/core/network/http_request_impl.dart
  5. 4
      lib/core/network/interceptors/logging_interceptor.dart
  6. 2
      lib/core/network/interceptors/token_interceptor.dart
  7. 8
      lib/core/params/awards_params.dart
  8. 5
      lib/core/params/battle_league_params.dart
  9. 8
      lib/core/params/bl_question_params.dart
  10. 14
      lib/core/params/home_params.dart
  11. 8
      lib/core/params/intro_params.dart
  12. 8
      lib/core/params/master_params.dart
  13. 8
      lib/core/params/profile_params.dart
  14. 8
      lib/core/params/sample_params.dart
  15. 8
      lib/core/params/shop_params.dart
  16. 13
      lib/core/params/topic_params.dart
  17. 9
      lib/core/status/base_status.dart
  18. 16
      lib/core/utils/local_storage.dart
  19. 66
      lib/core/widgets/container/my_container.dart
  20. 20
      lib/core/widgets/input/my_input.dart
  21. 13
      lib/core/widgets/loading/my_loading.dart
  22. 23
      lib/features/battle_league/first_part/data/datasource/battle_league_datasource.dart
  23. 41
      lib/features/battle_league/first_part/data/model/topics_model.dart
  24. 13
      lib/features/battle_league/first_part/data/repository_impl/battle_league_repository_impl.dart
  25. 50
      lib/features/battle_league/first_part/domain/entity/topics_entity.dart
  26. 9
      lib/features/battle_league/first_part/domain/repository/battle_league_repository.dart
  27. 14
      lib/features/battle_league/first_part/domain/usecases/get_topics_usecase.dart
  28. 39
      lib/features/battle_league/first_part/presentation/controller/battle_league_controller.dart
  29. 63
      lib/features/battle_league/first_part/presentation/ui/battle_league_topic_page.dart
  30. 11
      lib/features/battle_league/first_part/presentation/ui/widgets/topic_page/topic_widget.dart
  31. 19
      lib/features/home/data/datasource/home_datasource.dart
  32. 23
      lib/features/home/data/model/guest_player_model.dart
  33. 13
      lib/features/home/data/model/home_model.dart
  34. 10
      lib/features/home/data/repository_impl/home_repository_impl.dart
  35. 26
      lib/features/home/domain/entity/guest_player_entity.dart
  36. 14
      lib/features/home/domain/entity/home_entity.dart
  37. 4
      lib/features/home/domain/repository/home_repository.dart
  38. 10
      lib/features/home/domain/usecases/login_guest_usecase.dart
  39. 66
      lib/features/home/presentation/controller/home_controller.dart
  40. 16
      lib/features/home/presentation/pages/home_page.dart
  41. 80
      lib/features/home/presentation/pages/widgets/home_username_dialog.dart
  42. 14
      lib/init_bindings.dart
  43. 5
      lib/l10n/app_en.arb
  44. 18
      lib/l10n/app_localizations.dart
  45. 10
      lib/l10n/app_localizations_en.dart
  46. 6
      lib/main.dart
  47. 159
      pubspec.lock
  48. 4
      pubspec.yaml

10
ios/Podfile.lock

@ -1,22 +1,22 @@
PODS:
- Flutter (1.0.0)
- path_provider_foundation (0.0.1):
- shared_preferences_foundation (0.0.1):
- Flutter
- FlutterMacOS
DEPENDENCIES:
- Flutter (from `Flutter`)
- path_provider_foundation (from `.symlinks/plugins/path_provider_foundation/darwin`)
- shared_preferences_foundation (from `.symlinks/plugins/shared_preferences_foundation/darwin`)
EXTERNAL SOURCES:
Flutter:
:path: Flutter
path_provider_foundation:
:path: ".symlinks/plugins/path_provider_foundation/darwin"
shared_preferences_foundation:
:path: ".symlinks/plugins/shared_preferences_foundation/darwin"
SPEC CHECKSUMS:
Flutter: cabc95a1d2626b1b06e7179b784ebcf0c0cde467
path_provider_foundation: 080d55be775b7414fd5a5ef3ac137b97b097e564
shared_preferences_foundation: 7036424c3d8ec98dfe75ff1667cb0cd531ec82bb
PODFILE CHECKSUM: 3c63482e143d1b91d2d2560aee9fb04ecc74ac7e

9
lib/core/constants/my_api.dart

@ -7,5 +7,12 @@ class MyApi {
static const String contentType = 'application/json';
static const String defaultError = 'An unexpected error has occurred.';
static const String baseUrl = 'https://api.BASE_URL.com';
static const String baseUrl = 'https://shiamind.newhorizonco.uk/backend/api';
/// Player Auth
static const String guestToken = '/player/guest-token/';
static const String centrifugoToken = '/player/centrifugo-connect/';
/// Quiz
static const String topics = '/quiz/topics/';
}

19
lib/core/error_handler/error_handler.dart

@ -1,6 +1,8 @@
import 'package:dio/dio.dart';
import 'package:get/get.dart';
import 'package:shia_game_flutter/core/constants/my_api.dart';
import 'package:shia_game_flutter/core/error_handler/my_exception.dart';
import 'package:shia_game_flutter/core/utils/my_localization.dart';
class ErrorHandler {
static const ErrorHandler _i = ErrorHandler._internal();
@ -8,22 +10,23 @@ class ErrorHandler {
factory ErrorHandler() => _i;
static void handleError(DioException e) {
if (e.response == null) {
if (e.type == DioExceptionType.connectionTimeout ||
e.type == DioExceptionType.connectionError ||
e.type == DioExceptionType.receiveTimeout ||
e.type == DioExceptionType.sendTimeout) {
throw MyException(
errorMessage: e.message ?? MyApi.defaultError,
statusCode: e.response?.statusCode,
errorMessage: Get.context!.translate.check_internet_connection,
statusCode: 0,
);
} else {
if (e.response?.data['message'] == null) {
if (e.response?.data?['message'] == null) {
throw MyException(
errorMessage:
e.response?.statusMessage ?? e.message ?? MyApi.defaultError,
errorMessage: e.response?.statusMessage ?? e.message ?? MyApi.defaultError,
statusCode: e.response?.statusCode,
);
} else {
throw MyException(
errorMessage:
e.response?.data['message'] ?? e.message ?? MyApi.defaultError,
errorMessage: e.response?.data?['message'] ?? e.message ?? MyApi.defaultError,
statusCode: e.response?.statusCode,
);
}

1
lib/core/network/http_request_impl.dart

@ -17,6 +17,7 @@ class HttpRequestImpl implements IHttpRequest {
),
)..interceptors.addAll([
LoggingInterceptor.prettyDioLogger,
LoggingInterceptor.curlDioLogger,
TokenInterceptor(),
]);

4
lib/core/network/interceptors/logging_interceptor.dart

@ -1,5 +1,6 @@
import 'package:flutter/foundation.dart';
import 'package:pretty_dio_logger/pretty_dio_logger.dart';
import 'package:curl_logger_dio_interceptor/curl_logger_dio_interceptor.dart';
class LoggingInterceptor {
static const LoggingInterceptor _i = LoggingInterceptor._internal();
@ -16,4 +17,7 @@ class LoggingInterceptor {
maxWidth: 90,
enabled: kDebugMode,
);
static final CurlLoggerDioInterceptor curlDioLogger =
CurlLoggerDioInterceptor();
}

2
lib/core/network/interceptors/token_interceptor.dart

@ -4,7 +4,7 @@ import 'package:shia_game_flutter/core/auth_storage/auth_storage.dart';
class TokenInterceptor extends Interceptor {
@override
void onRequest(RequestOptions options, RequestInterceptorHandler handler) {
options.headers['Authorization'] = 'Bearer ${AuthStorage.token}';
options.headers['X-Player-Token'] = AuthStorage.token;
handler.next(options);
}
}

8
lib/core/params/awards_params.dart

@ -2,12 +2,4 @@ class AwardsParams {
int? id;
AwardsParams({this.id});
AwardsParams copyWith({
int? id,
}) {
return AwardsParams(
id: id ?? this.id,
);
}
}

5
lib/core/params/battle_league_params.dart

@ -0,0 +1,5 @@
class BattleLeagueParams {
int? id;
BattleLeagueParams({this.id});
}

8
lib/core/params/bl_question_params.dart

@ -2,12 +2,4 @@ class BLQuestionParams {
int? id;
BLQuestionParams({this.id});
BLQuestionParams copyWith({
int? id,
}) {
return BLQuestionParams(
id: id ?? this.id,
);
}
}

14
lib/core/params/home_params.dart

@ -1,13 +1,9 @@
class HomeParams {
int? id;
String? username;
HomeParams({this.id});
HomeParams({this.username});
HomeParams copyWith({
int? id,
}) {
return HomeParams(
id: id ?? this.id,
);
}
Map<String, dynamic> get toGuestJson => {
if (username != null) 'username': username,
};
}

8
lib/core/params/intro_params.dart

@ -2,12 +2,4 @@ class IntroParams {
int? id;
IntroParams({this.id});
IntroParams copyWith({
int? id,
}) {
return IntroParams(
id: id ?? this.id,
);
}
}

8
lib/core/params/master_params.dart

@ -2,12 +2,4 @@ class MasterParams {
int? id;
MasterParams({this.id});
MasterParams copyWith({
int? id,
}) {
return MasterParams(
id: id ?? this.id,
);
}
}

8
lib/core/params/profile_params.dart

@ -2,12 +2,4 @@ class ProfileParams {
int? id;
ProfileParams({this.id});
ProfileParams copyWith({
int? id,
}) {
return ProfileParams(
id: id ?? this.id,
);
}
}

8
lib/core/params/sample_params.dart

@ -2,12 +2,4 @@ class SampleParams {
int? id;
SampleParams({this.id});
SampleParams copyWith({
int? id,
}) {
return SampleParams(
id: id ?? this.id,
);
}
}

8
lib/core/params/shop_params.dart

@ -2,12 +2,4 @@ class ShopParams {
int? id;
ShopParams({this.id});
ShopParams copyWith({
int? id,
}) {
return ShopParams(
id: id ?? this.id,
);
}
}

13
lib/core/params/topic_params.dart

@ -1,13 +0,0 @@
class TopicParams {
int? id;
TopicParams({this.id});
TopicParams copyWith({
int? id,
}) {
return TopicParams(
id: id ?? this.id,
);
}
}

9
lib/core/status/base_status.dart

@ -18,14 +18,11 @@ class BaseNotAuth extends BaseStatus {
const BaseNotAuth();
}
class BaseComplete<T> extends BaseStatus {
final T data;
const BaseComplete(this.data);
class BaseComplete extends BaseStatus {
const BaseComplete();
}
class BaseError extends BaseStatus {
final String errorMessage;
const BaseError(this.errorMessage);
const BaseError({required this.errorMessage});
}

16
lib/core/utils/local_storage.dart

@ -1,18 +1,22 @@
import 'package:get_storage/get_storage.dart';
import 'package:shared_preferences/shared_preferences.dart';
class LocalStorage {
static const LocalStorage _i = LocalStorage._internal();
const LocalStorage._internal();
factory LocalStorage() => _i;
static final GetStorage _box = GetStorage();
static late final SharedPreferences _box;
static Future<void> saveData({required String key, required dynamic value}) async {
await _box.write(key, value);
static Future<void> init() async {
_box = await SharedPreferences.getInstance();
}
static Future<void> saveData({required String key, required String value}) async {
await _box.setString(key, value);
}
static String? readData({required String key}) {
return _box.read<String>(key);
return _box.getString(key);
}
static Future<void> deleteData({required String key}) async {
@ -20,6 +24,6 @@ class LocalStorage {
}
static Future<void> clearAll() async {
await _box.erase();
await _box.clear();
}
}

66
lib/core/widgets/container/my_container.dart

@ -1,5 +1,6 @@
import 'package:flutter/material.dart';
import 'package:shia_game_flutter/common_ui/theme/my_theme.dart';
import 'package:shia_game_flutter/core/widgets/loading/my_loading.dart';
class MyContainer extends StatelessWidget {
const MyContainer({
@ -7,6 +8,7 @@ class MyContainer extends StatelessWidget {
this.width,
this.height,
this.padding,
this.margin,
this.boxShape,
this.borderGradient,
this.borderRadius,
@ -17,12 +19,13 @@ class MyContainer extends StatelessWidget {
this.gradient,
this.borderColor,
this.onTap,
this.inset,
this.loading = false,
});
final double? width;
final double? height;
final EdgeInsetsGeometry? padding;
final EdgeInsetsGeometry? margin;
final BoxShape? boxShape;
final Gradient? borderGradient;
final Gradient? gradient;
@ -33,44 +36,47 @@ class MyContainer extends StatelessWidget {
final Widget? child;
final DecorationImage? image;
final VoidCallback? onTap;
final bool? inset;
final bool loading;
@override
Widget build(BuildContext context) {
return Material(
color: context.noColor,
borderRadius: boxShape == BoxShape.circle
? const BorderRadius.all(Radius.circular(100))
: borderRadius,
shadowColor: boxShadow?.first.color,
elevation: boxShadow?.first.blurRadius ?? 0,
child: InkWell(
onTap: onTap,
customBorder: RoundedRectangleBorder(
borderRadius: boxShape == BoxShape.circle
? const BorderRadius.all(Radius.circular(100))
: borderRadius ?? BorderRadius.zero,
),
child: Ink(
padding: const EdgeInsets.all(1),
width: width,
height: height,
decoration: BoxDecoration(
shape: boxShape ?? BoxShape.rectangle,
gradient: borderGradient,
borderRadius: borderRadius,
color: borderColor,
return Padding(
padding: margin ?? EdgeInsets.zero,
child: Material(
color: context.noColor,
borderRadius: boxShape == BoxShape.circle
? const BorderRadius.all(Radius.circular(100))
: borderRadius,
shadowColor: boxShadow?.first.color,
elevation: boxShadow?.first.blurRadius ?? 0,
child: InkWell(
onTap: loading ? null : onTap,
customBorder: RoundedRectangleBorder(
borderRadius: boxShape == BoxShape.circle
? const BorderRadius.all(Radius.circular(100))
: borderRadius ?? BorderRadius.zero,
),
child: Ink(
padding: padding,
padding: const EdgeInsets.all(1),
width: width,
height: height,
decoration: BoxDecoration(
shape: boxShape ?? BoxShape.rectangle,
gradient: gradient,
gradient: borderGradient,
borderRadius: borderRadius,
color: color,
image: image,
color: borderColor,
),
child: Ink(
padding: padding,
decoration: BoxDecoration(
shape: boxShape ?? BoxShape.rectangle,
gradient: gradient,
borderRadius: borderRadius,
color: color,
image: image,
),
child: Center(child: loading ? const MyLoading() : child),
),
child: Center(child: child),
),
),
),

20
lib/core/widgets/input/my_input.dart

@ -14,7 +14,7 @@ class MyInput extends StatelessWidget {
this.validator,
this.onChanged,
this.onTap,
this.onEditingComplete,
this.onFieldSubmitted,
this.onTapOutside,
this.enabled,
this.readOnly,
@ -28,11 +28,11 @@ class MyInput extends StatelessWidget {
final bool? obscureText;
final TextInputType? keyboardType;
final TextInputAction? action;
final String? Function(String?)? validator;
final void Function(String)? onChanged;
final String? Function(String? value)? validator;
final void Function(String value)? onChanged;
final void Function()? onTap;
final void Function()? onEditingComplete;
final void Function(PointerDownEvent)? onTapOutside;
final void Function(String value)? onFieldSubmitted;
final void Function(PointerDownEvent event)? onTapOutside;
final bool? enabled;
final bool? readOnly;
final int? maxLines;
@ -52,16 +52,16 @@ class MyInput extends StatelessWidget {
TextFormField(
controller: controller,
obscureText: obscureText ?? false,
keyboardType: keyboardType,
textInputAction: action,
keyboardType: keyboardType ?? TextInputType.text,
textInputAction: action ?? TextInputAction.done,
validator: validator,
onChanged: onChanged,
onTap: onTap,
onEditingComplete: onEditingComplete,
onFieldSubmitted: onFieldSubmitted,
enabled: enabled,
readOnly: readOnly ?? false,
maxLines: maxLines,
minLines: minLines,
maxLines: maxLines ?? 1,
minLines: minLines ?? 1,
style: Lexend.extraBold.copyWith(fontSize: 12),
cursorColor: context.primaryColor,
decoration: InputDecoration(

13
lib/core/widgets/loading/my_loading.dart

@ -0,0 +1,13 @@
import 'package:flutter/cupertino.dart';
import 'package:shia_game_flutter/common_ui/resources/my_colors.dart';
class MyLoading extends StatelessWidget {
const MyLoading({super.key});
@override
Widget build(BuildContext context) {
return const Center(
child: CupertinoActivityIndicator(color: MyColors.white),
);
}
}

23
lib/features/battle_league/first_part/data/datasource/battle_league_datasource.dart

@ -1,12 +1,12 @@
import 'package:shia_game_flutter/core/constants/my_api.dart';
import 'package:shia_game_flutter/core/network/http_request.dart';
import 'package:shia_game_flutter/core/params/sample_params.dart';
import 'package:shia_game_flutter/core/params/battle_league_params.dart';
import 'package:shia_game_flutter/core/response/base_response.dart';
import 'package:shia_game_flutter/features/battle_league/first_part/data/model/battle_league_model.dart';
import 'package:shia_game_flutter/features/battle_league/first_part/domain/entity/battle_league_entity.dart';
import 'package:shia_game_flutter/features/battle_league/first_part/data/model/topics_model.dart';
import 'package:shia_game_flutter/features/battle_league/first_part/domain/entity/topics_entity.dart';
abstract class IBattleLeagueDatasource {
Future<BattleLeagueEntity> getData({required SampleParams params});
Future<List<TopicsEntity>> getTopics({required BattleLeagueParams params});
}
class BattleLeagueDatasourceImpl implements IBattleLeagueDatasource {
@ -15,15 +15,14 @@ class BattleLeagueDatasourceImpl implements IBattleLeagueDatasource {
const BattleLeagueDatasourceImpl(this.httpRequest);
@override
Future<BattleLeagueEntity> getData({required SampleParams params}) async {
final response = await httpRequest.get(
path: MyApi.baseUrl,
);
Future<List<TopicsEntity>> getTopics({
required BattleLeagueParams params,
}) async {
final response = await httpRequest.get(path: MyApi.topics);
return BaseResponse.getData<BattleLeagueEntity>(
response?['data'],
(json) => BattleLeagueModel.fromJson(json),
return BaseResponse.getDataList<TopicsEntity>(
response?['results'],
(json) => TopicsModel.fromJson(json),
);
}
}

41
lib/features/battle_league/first_part/data/model/topics_model.dart

@ -0,0 +1,41 @@
import 'package:shia_game_flutter/features/battle_league/first_part/domain/entity/topics_entity.dart';
class TopicsModel extends TopicsEntity {
const TopicsModel({
super.id,
super.slug,
super.title,
super.description,
super.icon,
super.iconUrl,
super.order,
super.isActive,
super.difficultyLevel,
super.difficultyDisplay,
super.questionsCount,
super.createdAt,
super.updatedAt,
});
factory TopicsModel.fromJson(Map<String, dynamic> json) {
return TopicsModel(
id: json['id'],
slug: json['slug'],
title: json['title'],
description: json['description'],
icon: json['icon'],
iconUrl: json['icon_url'],
order: json['order'],
isActive: json['is_active'],
difficultyLevel: json['difficulty_level'],
difficultyDisplay: json['difficulty_display'],
questionsCount: json['questions_count'],
createdAt: json['created_at'] == null
? null
: DateTime.parse(json['created_at']),
updatedAt: json['updated_at'] == null
? null
: DateTime.parse(json['updated_at']),
);
}
}

13
lib/features/battle_league/first_part/data/repository_impl/battle_league_repository_impl.dart

@ -1,9 +1,9 @@
import 'package:flutter/foundation.dart';
import 'package:shia_game_flutter/core/error_handler/my_exception.dart';
import 'package:shia_game_flutter/core/params/sample_params.dart';
import 'package:shia_game_flutter/core/params/battle_league_params.dart';
import 'package:shia_game_flutter/core/utils/data_state.dart';
import 'package:shia_game_flutter/features/battle_league/first_part/data/datasource/battle_league_datasource.dart';
import 'package:shia_game_flutter/features/battle_league/first_part/domain/entity/battle_league_entity.dart';
import 'package:shia_game_flutter/features/battle_league/first_part/domain/entity/topics_entity.dart';
import 'package:shia_game_flutter/features/battle_league/first_part/domain/repository/battle_league_repository.dart';
class BattleLeagueRepositoryImpl implements IBattleLeagueRepository {
@ -12,9 +12,13 @@ class BattleLeagueRepositoryImpl implements IBattleLeagueRepository {
const BattleLeagueRepositoryImpl(this.datasource);
@override
Future<DataState<BattleLeagueEntity, MyException>> getData({required SampleParams params}) async {
Future<DataState<List<TopicsEntity>, MyException>> getTopics({
required BattleLeagueParams params,
}) async {
try {
final BattleLeagueEntity response = await datasource.getData(params: params);
final List<TopicsEntity> response = await datasource.getTopics(
params: params,
);
return DataState.success(response);
} on MyException catch (e) {
return DataState.error(e);
@ -27,4 +31,3 @@ class BattleLeagueRepositoryImpl implements IBattleLeagueRepository {
}
}
}

50
lib/features/battle_league/first_part/domain/entity/topics_entity.dart

@ -0,0 +1,50 @@
import 'package:equatable/equatable.dart';
class TopicsEntity extends Equatable {
final int? id;
final String? slug;
final String? title;
final String? description;
final String? icon;
final String? iconUrl;
final int? order;
final bool? isActive;
final String? difficultyLevel;
final String? difficultyDisplay;
final int? questionsCount;
final DateTime? createdAt;
final DateTime? updatedAt;
const TopicsEntity({
this.id,
this.slug,
this.title,
this.description,
this.icon,
this.iconUrl,
this.order,
this.isActive,
this.difficultyLevel,
this.difficultyDisplay,
this.questionsCount,
this.createdAt,
this.updatedAt,
});
@override
List<Object?> get props => [
id,
slug,
title,
description,
icon,
iconUrl,
order,
isActive,
difficultyLevel,
difficultyDisplay,
questionsCount,
createdAt,
updatedAt,
];
}

9
lib/features/battle_league/first_part/domain/repository/battle_league_repository.dart

@ -1,9 +1,10 @@
import 'package:shia_game_flutter/core/error_handler/my_exception.dart';
import 'package:shia_game_flutter/core/params/sample_params.dart';
import 'package:shia_game_flutter/core/params/battle_league_params.dart';
import 'package:shia_game_flutter/core/utils/data_state.dart';
import 'package:shia_game_flutter/features/battle_league/first_part/domain/entity/battle_league_entity.dart';
import 'package:shia_game_flutter/features/battle_league/first_part/domain/entity/topics_entity.dart';
abstract class IBattleLeagueRepository {
Future<DataState<BattleLeagueEntity, MyException>> getData({required SampleParams params});
Future<DataState<List<TopicsEntity>, MyException>> getTopics({
required BattleLeagueParams params,
});
}

14
lib/features/battle_league/first_part/domain/usecases/get_battle_league_usecase.dart → lib/features/battle_league/first_part/domain/usecases/get_topics_usecase.dart

@ -1,18 +1,18 @@
import 'package:shia_game_flutter/core/error_handler/my_exception.dart';
import 'package:shia_game_flutter/core/params/sample_params.dart';
import 'package:shia_game_flutter/core/params/battle_league_params.dart';
import 'package:shia_game_flutter/core/usecase/usecase.dart';
import 'package:shia_game_flutter/core/utils/data_state.dart';
import 'package:shia_game_flutter/features/battle_league/first_part/domain/entity/battle_league_entity.dart';
import 'package:shia_game_flutter/features/battle_league/first_part/domain/entity/topics_entity.dart';
import 'package:shia_game_flutter/features/battle_league/first_part/domain/repository/battle_league_repository.dart';
class GetBattleLeagueUseCase implements UseCase<BattleLeagueEntity, SampleParams> {
class GetTopicsUseCase
implements UseCase<List<TopicsEntity>, BattleLeagueParams> {
final IBattleLeagueRepository repository;
const GetBattleLeagueUseCase(this.repository);
const GetTopicsUseCase(this.repository);
@override
Future<DataState<BattleLeagueEntity, MyException>> call(SampleParams params) {
return repository.getData(params: params);
Future<DataState<List<TopicsEntity>, MyException>> call(BattleLeagueParams params,) {
return repository.getTopics(params: params);
}
}

39
lib/features/battle_league/first_part/presentation/controller/battle_league_controller.dart

@ -1,20 +1,19 @@
import 'package:flutter/material.dart';
import 'package:shia_game_flutter/core/params/sample_params.dart';
import 'package:get/get.dart';
import 'package:shia_game_flutter/core/params/battle_league_params.dart';
import 'package:shia_game_flutter/core/routers/my_routes.dart';
import 'package:shia_game_flutter/core/status/base_status.dart';
import 'package:get/get.dart';
import 'package:shia_game_flutter/features/battle_league/first_part/domain/entity/battle_league_entity.dart';
import 'package:shia_game_flutter/features/battle_league/first_part/domain/usecases/get_battle_league_usecase.dart';
import 'package:shia_game_flutter/features/battle_league/first_part/domain/entity/topics_entity.dart';
import 'package:shia_game_flutter/features/battle_league/first_part/domain/usecases/get_topics_usecase.dart';
class BattleLeagueController extends GetxController
with StateMixin, GetSingleTickerProviderStateMixin {
/// ----- Constructor -----
BattleLeagueController(this.getBattleLeagueUseCase);
BattleLeagueController(this._getTopicsUseCase);
@override
void onInit() {
super.onInit();
change('', status: RxStatus.success());
tabController = TabController(length: 2, vsync: this);
}
@ -25,11 +24,11 @@ class BattleLeagueController extends GetxController
}
/// ----- UseCases -----
final GetBattleLeagueUseCase getBattleLeagueUseCase;
final GetTopicsUseCase _getTopicsUseCase;
/// ----- Variables -----
final Rx<SampleParams> battleLeagueParams = Rx(SampleParams());
final Rx<BattleLeagueEntity> battleLeagueEntity = Rx(const BattleLeagueEntity());
final BattleLeagueParams battleLeagueParams = BattleLeagueParams();
final RxList<TopicsEntity> topicList = RxList.empty();
/// ------ Controllers ------
final TextEditingController textEditingController = TextEditingController();
@ -37,33 +36,35 @@ class BattleLeagueController extends GetxController
/// ------ Statuses ------
final Rx<BaseStatus> getBattleLeagueStatus = Rx(const BaseInit());
final Rx<BaseStatus> getTopicsStatus = Rx(const BaseInit());
/// ------ Functions ------
void goToTopicPage(){
void goToTopicPage() {
getTopics();
Get.toNamed(Routes.battleLeagueTopicPage);
}
void goToFindingPage(){
void goToFindingPage() {
Get.toNamed(Routes.battleLeagueFindingPage);
}
void goToFoundedPage(){
void goToFoundedPage() {
Get.toNamed(Routes.battleLeagueFoundedPage);
}
/// ------ Api Calls ------
Future<void> getBattleLeague() async {
change('', status: RxStatus.loading());
await getBattleLeagueUseCase(battleLeagueParams.value).then(
Future<void> getTopics() async {
getTopicsStatus.value = const BaseLoading();
await _getTopicsUseCase(battleLeagueParams).then(
(value) => value.fold(
(data) {
battleLeagueEntity.value = data;
change('', status: RxStatus.success());
topicList.value = data;
getTopicsStatus.value = const BaseComplete();
},
(error) {
change('', status: RxStatus.error(error.errorMessage));
getTopicsStatus.value = BaseError(errorMessage: error.errorMessage);
},
),
);
}
}

63
lib/features/battle_league/first_part/presentation/ui/battle_league_topic_page.dart

@ -3,11 +3,13 @@ import 'package:get/get.dart';
import 'package:shia_game_flutter/common_ui/resources/my_assets.dart';
import 'package:shia_game_flutter/common_ui/resources/my_colors.dart';
import 'package:shia_game_flutter/common_ui/resources/my_text_style.dart';
import 'package:shia_game_flutter/core/status/base_status.dart';
import 'package:shia_game_flutter/core/utils/gap.dart';
import 'package:shia_game_flutter/core/utils/my_localization.dart';
import 'package:shia_game_flutter/core/utils/screen_size.dart';
import 'package:shia_game_flutter/core/widgets/app_bar/enums/app_bar_type.dart';
import 'package:shia_game_flutter/core/widgets/app_bar/my_app_bar.dart';
import 'package:shia_game_flutter/core/widgets/loading/my_loading.dart';
import 'package:shia_game_flutter/features/battle_league/first_part/presentation/controller/battle_league_controller.dart';
import 'package:shia_game_flutter/features/battle_league/first_part/presentation/ui/widgets/button/battle_golden_button.dart';
import 'package:shia_game_flutter/features/battle_league/first_part/presentation/ui/widgets/button/battle_grey_button.dart';
@ -26,18 +28,32 @@ class BattleLeagueTopicPage extends GetView<BattleLeagueController> {
title: context.translate.choose_3_topics,
),
body: SafeArea(
child: Column(
crossAxisAlignment: CrossAxisAlignment.center,
children: [
20.h.gapHeight,
_title(context),
27.h.gapHeight,
_topicList(context),
20.h.gapHeight,
_randomButton(context),
const Spacer(),
_startButton(context),
],
child: Obx(
() {
if(controller.getTopicsStatus.value is BaseComplete){
return Column(
crossAxisAlignment: CrossAxisAlignment.center,
children: [
20.h.gapHeight,
_title(context),
27.h.gapHeight,
_topicList(context),
20.h.gapHeight,
_randomButton(context),
const Spacer(),
_startButton(context),
],
);
}
if(controller.getTopicsStatus.value is BaseLoading){
return const MyLoading();
}
if(controller.getTopicsStatus.value is BaseError){
return Text(
(controller.getTopicsStatus.value as BaseError).errorMessage);
}
return const SizedBox.shrink();
}
),
),
);
@ -73,17 +89,18 @@ class BattleLeagueTopicPage extends GetView<BattleLeagueController> {
SizedBox _topicList(BuildContext context) {
return SizedBox(
width: context.widthScreen,
child: Wrap(
spacing: 20,
runSpacing: 14,
direction: Axis.horizontal,
alignment: WrapAlignment.center,
children: List.generate(
10,
(index) => TopicWidget(
label: context.translate.art,
image: MyAssets.iconArt,
onTap: () {},
child: Obx(
() => Wrap(
spacing: 20,
runSpacing: 14,
direction: Axis.horizontal,
alignment: WrapAlignment.center,
children: List.generate(
controller.topicList.length,
(index) => TopicWidget(
topic: controller.topicList[index],
onTap: () {},
),
),
),
),

11
lib/features/battle_league/first_part/presentation/ui/widgets/topic_page/topic_widget.dart

@ -3,18 +3,17 @@ import 'package:shia_game_flutter/common_ui/resources/my_text_style.dart';
import 'package:shia_game_flutter/core/utils/screen_size.dart';
import 'package:shia_game_flutter/core/widgets/container/my_container.dart';
import 'package:shia_game_flutter/core/widgets/image/my_image.dart';
import 'package:shia_game_flutter/features/battle_league/first_part/domain/entity/topics_entity.dart';
class TopicWidget extends StatelessWidget {
const TopicWidget({
super.key,
this.onTap,
this.label,
this.image,
required this.topic,
});
final VoidCallback? onTap;
final String? label;
final String? image;
final TopicsEntity topic;
@override
Widget build(BuildContext context) {
@ -51,10 +50,10 @@ class TopicWidget extends StatelessWidget {
spacing: 4,
children: [
MyImage(
asset: image ?? '',
asset: topic.iconUrl ?? '',
),
Text(
label ?? '',
topic.title ?? '',
style: Lexend.medium.copyWith(fontSize: 12),
),
],

19
lib/features/home/data/datasource/home_datasource.dart

@ -2,11 +2,11 @@ import 'package:shia_game_flutter/core/constants/my_api.dart';
import 'package:shia_game_flutter/core/network/http_request.dart';
import 'package:shia_game_flutter/core/params/home_params.dart';
import 'package:shia_game_flutter/core/response/base_response.dart';
import 'package:shia_game_flutter/features/home/data/model/home_model.dart';
import 'package:shia_game_flutter/features/home/domain/entity/home_entity.dart';
import 'package:shia_game_flutter/features/home/data/model/guest_player_model.dart';
import 'package:shia_game_flutter/features/home/domain/entity/guest_player_entity.dart';
abstract class IHomeDatasource {
Future<HomeEntity> getData({required HomeParams params});
Future<GuestPlayerEntity> loginGuest({required HomeParams params});
}
class HomeDatasourceImpl implements IHomeDatasource {
@ -15,14 +15,15 @@ class HomeDatasourceImpl implements IHomeDatasource {
const HomeDatasourceImpl(this.httpRequest);
@override
Future<HomeEntity> getData({required HomeParams params}) async {
final response = await httpRequest.get(
path: MyApi.baseUrl,
Future<GuestPlayerEntity> loginGuest({required HomeParams params}) async {
final response = await httpRequest.post(
path: MyApi.guestToken,
data: params.toGuestJson,
);
return BaseResponse.getData<HomeEntity>(
response?['data'],
(json) => HomeModel.fromJson(json),
return BaseResponse.getData<GuestPlayerEntity>(
response,
(json) => GuestPlayerModel.fromJson(json),
);
}
}

23
lib/features/home/data/model/guest_player_model.dart

@ -0,0 +1,23 @@
import 'package:shia_game_flutter/features/home/domain/entity/guest_player_entity.dart';
class GuestPlayerModel extends GuestPlayerEntity {
const GuestPlayerModel({
super.playerID,
super.playerToken,
super.username,
super.isGuest,
super.createdAt,
});
factory GuestPlayerModel.fromJson(Map<String, dynamic> json) {
return GuestPlayerModel(
playerID: json['player_id'],
playerToken: json['player_token'],
username: json['username'],
isGuest: json['is_guest'],
createdAt: json['created_at'] == null
? null
: DateTime.parse(json['created_at']),
);
}
}

13
lib/features/home/data/model/home_model.dart

@ -1,13 +0,0 @@
import 'package:shia_game_flutter/features/home/domain/entity/home_entity.dart';
class HomeModel extends HomeEntity {
const HomeModel({
super.id,
});
factory HomeModel.fromJson(Map<String, dynamic> json) {
return HomeModel(
id: json['id'],
);
}
}

10
lib/features/home/data/repository_impl/home_repository_impl.dart

@ -3,7 +3,7 @@ import 'package:shia_game_flutter/core/error_handler/my_exception.dart';
import 'package:shia_game_flutter/core/params/home_params.dart';
import 'package:shia_game_flutter/core/utils/data_state.dart';
import 'package:shia_game_flutter/features/home/data/datasource/home_datasource.dart';
import 'package:shia_game_flutter/features/home/domain/entity/home_entity.dart';
import 'package:shia_game_flutter/features/home/domain/entity/guest_player_entity.dart';
import 'package:shia_game_flutter/features/home/domain/repository/home_repository.dart';
class HomeRepositoryImpl implements IHomeRepository {
@ -12,9 +12,13 @@ class HomeRepositoryImpl implements IHomeRepository {
const HomeRepositoryImpl(this.datasource);
@override
Future<DataState<HomeEntity, MyException>> getData({required HomeParams params}) async {
Future<DataState<GuestPlayerEntity, MyException>> loginGuest({
required HomeParams params,
}) async {
try {
final HomeEntity response = await datasource.getData(params: params);
final GuestPlayerEntity response = await datasource.loginGuest(
params: params,
);
return DataState.success(response);
} on MyException catch (e) {
return DataState.error(e);

26
lib/features/home/domain/entity/guest_player_entity.dart

@ -0,0 +1,26 @@
import 'package:equatable/equatable.dart';
class GuestPlayerEntity extends Equatable {
final String? playerID;
final String? playerToken;
final String? username;
final bool? isGuest;
final DateTime? createdAt;
const GuestPlayerEntity({
this.playerID,
this.playerToken,
this.username,
this.isGuest,
this.createdAt,
});
@override
List<Object?> get props => [
playerID,
playerToken,
username,
isGuest,
createdAt,
];
}

14
lib/features/home/domain/entity/home_entity.dart

@ -1,14 +0,0 @@
import 'package:equatable/equatable.dart';
class HomeEntity extends Equatable {
final int? id;
const HomeEntity({
this.id,
});
@override
List<Object?> get props => [
id,
];
}

4
lib/features/home/domain/repository/home_repository.dart

@ -1,8 +1,8 @@
import 'package:shia_game_flutter/core/error_handler/my_exception.dart';
import 'package:shia_game_flutter/core/params/home_params.dart';
import 'package:shia_game_flutter/core/utils/data_state.dart';
import 'package:shia_game_flutter/features/home/domain/entity/home_entity.dart';
import 'package:shia_game_flutter/features/home/domain/entity/guest_player_entity.dart';
abstract class IHomeRepository {
Future<DataState<HomeEntity, MyException>> getData({required HomeParams params});
Future<DataState<GuestPlayerEntity, MyException>> loginGuest({required HomeParams params});
}

10
lib/features/home/domain/usecases/get_home_usecase.dart → lib/features/home/domain/usecases/login_guest_usecase.dart

@ -2,16 +2,16 @@ import 'package:shia_game_flutter/core/error_handler/my_exception.dart';
import 'package:shia_game_flutter/core/params/home_params.dart';
import 'package:shia_game_flutter/core/usecase/usecase.dart';
import 'package:shia_game_flutter/core/utils/data_state.dart';
import 'package:shia_game_flutter/features/home/domain/entity/home_entity.dart';
import 'package:shia_game_flutter/features/home/domain/entity/guest_player_entity.dart';
import 'package:shia_game_flutter/features/home/domain/repository/home_repository.dart';
class GetHomeUseCase implements UseCase<HomeEntity, HomeParams> {
class LoginGuestUseCase implements UseCase<GuestPlayerEntity, HomeParams> {
final IHomeRepository repository;
const GetHomeUseCase(this.repository);
const LoginGuestUseCase(this.repository);
@override
Future<DataState<HomeEntity, MyException>> call(HomeParams params) {
return repository.getData(params: params);
Future<DataState<GuestPlayerEntity, MyException>> call(HomeParams params) {
return repository.loginGuest(params: params);
}
}

66
lib/features/home/presentation/controller/home_controller.dart

@ -1,58 +1,76 @@
import 'package:flutter/cupertino.dart';
import 'package:get/get.dart';
import 'package:shia_game_flutter/common_ui/resources/my_colors.dart';
import 'package:shia_game_flutter/core/auth_storage/auth_storage.dart';
import 'package:shia_game_flutter/core/params/home_params.dart';
import 'package:shia_game_flutter/core/routers/my_routes.dart';
import 'package:shia_game_flutter/core/status/base_status.dart';
import 'package:shia_game_flutter/features/home/domain/entity/home_entity.dart';
import 'package:shia_game_flutter/features/home/domain/usecases/get_home_usecase.dart';
import 'package:shia_game_flutter/features/home/presentation/pages/widgets/home_username_dialog.dart';
import 'package:shia_game_flutter/features/home/domain/entity/guest_player_entity.dart';
import 'package:shia_game_flutter/features/home/domain/usecases/login_guest_usecase.dart';
class HomeController extends GetxController with StateMixin {
class HomeController extends GetxController {
/// ----- Constructor -----
HomeController(this.getHomeUseCase);
HomeController(this._loginGuestUseCase);
@override
void onInit() {
super.onInit();
change('', status: RxStatus.success());
showUsernameDialog();
}
@override
void onClose() {
textEditingController.dispose();
usernameController.dispose();
super.onClose();
}
/// ----- UseCases -----
final GetHomeUseCase getHomeUseCase;
final LoginGuestUseCase _loginGuestUseCase;
/// ----- Variables -----
final Rx<HomeParams> homeParams = Rx(HomeParams());
final Rx<HomeEntity> homeEntity = Rx(const HomeEntity());
final HomeParams homeParams = HomeParams();
final Rx<GuestPlayerEntity> guestEntity = Rx(const GuestPlayerEntity());
/// ------ Controllers ------
final TextEditingController textEditingController = TextEditingController();
final TextEditingController usernameController = TextEditingController();
/// ------ Statuses ------
final Rx<BaseStatus> getHomeStatus = Rx(const BaseInit());
final Rx<BaseStatus> loginGuestStatus = Rx(const BaseInit());
/// ------ Functions ------
void goToBattleLeaguePage() {
Get.toNamed(Routes.battleLeaguePage);
}
/// ------ Api Calls ------
Future<void> getHome() async {
change('', status: RxStatus.loading());
await getHomeUseCase(homeParams.value).then(
(value) => value.fold(
(data) {
homeEntity.value = data;
change('', status: RxStatus.success());
},
(error) {
change('', status: RxStatus.error(error.errorMessage));
},
),
Future<void> showUsernameDialog() async {
await Future.delayed(const Duration(seconds: 1));
Get.dialog(
const UsernameDialog(),
useSafeArea: false,
barrierColor: MyColors.black.withValues(alpha: 0.7),
barrierDismissible: false,
);
}
/// ------ Api Calls ------
Future<void> loginGuest() async {
if (homeParams.username?.isNotEmpty ?? false) {
loginGuestStatus.value = const BaseLoading();
await _loginGuestUseCase(homeParams).then(
(value) => value.fold(
(data) async {
guestEntity.value = data;
await AuthStorage.saveData(newTokenParams: data.playerToken ?? '');
Get.back();
loginGuestStatus.value = const BaseComplete();
},
(error) {
loginGuestStatus.value =
BaseError(errorMessage: error.errorMessage);
},
),
);
}
}
}

16
lib/features/home/presentation/pages/home_page.dart

@ -21,12 +21,10 @@ class HomePage extends GetView<HomeController> {
return MyBackground(
child: Column(
children: [
const MyImage(asset: MyAssets.shiaMindGroup),
_image(),
40.h.gapHeight,
const HomeMembership(),
HomeBattleLeague(
onTap: controller.goToBattleLeaguePage,
),
_homeBattleLeague(),
20.h.gapHeight,
_customWidgets(context),
20.h.gapHeight,
@ -36,6 +34,16 @@ class HomePage extends GetView<HomeController> {
);
}
MyImage _image() {
return const MyImage(asset: MyAssets.shiaMindGroup);
}
HomeBattleLeague _homeBattleLeague() {
return HomeBattleLeague(
onTap: controller.goToBattleLeaguePage,
);
}
Widget _customWidgets(BuildContext context) {
return Row(
spacing: 20,

80
lib/features/home/presentation/pages/widgets/home_username_dialog.dart

@ -0,0 +1,80 @@
import 'package:flutter/cupertino.dart';
import 'package:flutter/material.dart';
import 'package:get/get.dart';
import 'package:shia_game_flutter/common_ui/resources/my_text_style.dart';
import 'package:shia_game_flutter/core/status/base_status.dart';
import 'package:shia_game_flutter/core/utils/my_localization.dart';
import 'package:shia_game_flutter/core/utils/screen_size.dart';
import 'package:shia_game_flutter/core/widgets/container/my_container.dart';
import 'package:shia_game_flutter/core/widgets/input/my_input.dart';
import 'package:shia_game_flutter/core/widgets/text/gradient_text.dart';
import 'package:shia_game_flutter/features/home/presentation/controller/home_controller.dart';
class UsernameDialog extends GetView<HomeController> {
const UsernameDialog({super.key});
@override
Widget build(BuildContext context) {
return MyContainer(
padding: const EdgeInsets.only(left: 30, right: 30, bottom: 30, top: 13),
margin: EdgeInsets.symmetric(horizontal: 30.w, vertical: 290.h),
borderGradient: const LinearGradient(
begin: Alignment.topCenter,
end: Alignment.bottomCenter,
colors: [Color(0XFF6013DA), Color(0XFF4908B0)],
),
gradient: const RadialGradient(
radius: 1,
colors: [Color(0XFF4F09BF), Color(0XFF350D73)],
),
borderRadius: const BorderRadius.all(Radius.circular(40)),
child: Column(
mainAxisAlignment: MainAxisAlignment.spaceBetween,
children: [
Text(
context.translate.welcome,
style: Lexend.extraBold.copyWith(
fontSize: 18,
color: const Color(0XFFBAA3DD),
),
),
MyInput(
controller: controller.usernameController,
labelText: context.translate.username,
onFieldSubmitted: (value) {
controller.loginGuest();
},
onChanged: (value) {
controller.homeParams.username = value;
},
),
Obx(
() => MyContainer(
onTap: controller.loginGuest,
height: 41.h,
loading: controller.loginGuestStatus.value is BaseLoading,
borderRadius: const BorderRadius.all(Radius.circular(12)),
gradient: const RadialGradient(
radius: 4,
center: Alignment(-0.3, 0),
colors: [Color(0XFF6A36BF), Color(0XFF562A9E)],
),
borderGradient: LinearGradient(
begin: AlignmentDirectional.topStart,
end: AlignmentDirectional.bottomEnd,
colors: [
const Color(0XFF7F4CD4),
const Color(0XFF7F4CD4).withValues(alpha: 0),
],
),
child: GradientText(
text: context.translate.done,
color: const Color(0XFFB69CDE),
),
),
),
],
),
);
}
}

14
lib/init_bindings.dart

@ -8,7 +8,7 @@ import 'package:shia_game_flutter/features/awards/domain/usecases/get_awards_use
import 'package:shia_game_flutter/features/battle_league/first_part/data/datasource/battle_league_datasource.dart';
import 'package:shia_game_flutter/features/battle_league/first_part/data/repository_impl/battle_league_repository_impl.dart';
import 'package:shia_game_flutter/features/battle_league/first_part/domain/repository/battle_league_repository.dart';
import 'package:shia_game_flutter/features/battle_league/first_part/domain/usecases/get_battle_league_usecase.dart';
import 'package:shia_game_flutter/features/battle_league/first_part/domain/usecases/get_topics_usecase.dart';
import 'package:shia_game_flutter/features/battle_league/question_part/bl_question/data/datasource/bl_question_datasource.dart';
import 'package:shia_game_flutter/features/battle_league/question_part/bl_question/data/repository_impl/bl_question_repository_impl.dart';
import 'package:shia_game_flutter/features/battle_league/question_part/bl_question/domain/repository/bl_question_repository.dart';
@ -16,7 +16,7 @@ import 'package:shia_game_flutter/features/battle_league/question_part/bl_questi
import 'package:shia_game_flutter/features/home/data/datasource/home_datasource.dart';
import 'package:shia_game_flutter/features/home/data/repository_impl/home_repository_impl.dart';
import 'package:shia_game_flutter/features/home/domain/repository/home_repository.dart';
import 'package:shia_game_flutter/features/home/domain/usecases/get_home_usecase.dart';
import 'package:shia_game_flutter/features/home/domain/usecases/login_guest_usecase.dart';
import 'package:shia_game_flutter/features/intro/data/datasource/intro_datasource.dart';
import 'package:shia_game_flutter/features/intro/data/repository_impl/intro_repository_impl.dart';
import 'package:shia_game_flutter/features/intro/domain/repository/intro_repository.dart';
@ -53,14 +53,14 @@ void initBindings() {
Get.lazyPut<GetIntroUseCase>(() => GetIntroUseCase(Get.find()));
/// ----- Master Feature -----
Get.lazyPut<IMasterDatasource>(() => MasterDatasourceImpl(Get.find()));
Get.lazyPut<IMasterRepository>(() => MasterRepositoryImpl(Get.find()));
Get.lazyPut<GetMasterUseCase>(() => GetMasterUseCase(Get.find()));
Get.lazyPut<IMasterDatasource>(() => MasterDatasourceImpl(Get.find()), fenix: true);
Get.lazyPut<IMasterRepository>(() => MasterRepositoryImpl(Get.find()), fenix: true);
Get.lazyPut<GetMasterUseCase>(() => GetMasterUseCase(Get.find()), fenix: true);
/// ----- Home Feature -----
Get.lazyPut<IHomeDatasource>(() => HomeDatasourceImpl(Get.find()), fenix: true);
Get.lazyPut<IHomeRepository>(() => HomeRepositoryImpl(Get.find()), fenix: true);
Get.lazyPut<GetHomeUseCase>(() => GetHomeUseCase(Get.find()), fenix: true);
Get.lazyPut<LoginGuestUseCase>(() => LoginGuestUseCase(Get.find()), fenix: true);
/// ----- Shop Feature -----
Get.lazyPut<IShopDatasource>(() => ShopDatasourceImpl(Get.find()), fenix: true);
@ -80,7 +80,7 @@ void initBindings() {
/// ----- BattleLeague Feature -----
Get.lazyPut<IBattleLeagueDatasource>(() => BattleLeagueDatasourceImpl(Get.find()), fenix: true);
Get.lazyPut<IBattleLeagueRepository>(() => BattleLeagueRepositoryImpl(Get.find()), fenix: true);
Get.lazyPut<GetBattleLeagueUseCase>(() => GetBattleLeagueUseCase(Get.find()), fenix: true);
Get.lazyPut<GetTopicsUseCase>(() => GetTopicsUseCase(Get.find()), fenix: true);
/// ----- BattleLeagueQuestion Feature -----
Get.lazyPut<IBLQuestionDatasource>(() => BLQuestionDatasourceImpl(Get.find()), fenix: true);

5
lib/l10n/app_en.arb

@ -1,5 +1,6 @@
{
"@@locale": "en",
"check_internet_connection": "Please Check your internet connection.",
"loading": "Loading...",
"home": "Home",
"shop": "Shop",
@ -49,5 +50,7 @@
"quiz_league": "Quiz league",
"your_place": "Your place",
"finding_player": "Finding player ...",
"find_hint": "The fastest player to answer the question correctly gets the point."
"find_hint": "The fastest player to answer the question correctly gets the point.",
"welcome": "Welcome",
"done": "Done"
}

18
lib/l10n/app_localizations.dart

@ -94,6 +94,12 @@ abstract class AppLocalizations {
/// A list of this localizations delegate's supported locales.
static const List<Locale> supportedLocales = <Locale>[Locale('en')];
/// No description provided for @check_internet_connection.
///
/// In en, this message translates to:
/// **'Please Check your internet connection.'**
String get check_internet_connection;
/// No description provided for @loading.
///
/// In en, this message translates to:
@ -393,6 +399,18 @@ abstract class AppLocalizations {
/// In en, this message translates to:
/// **'The fastest player to answer the question correctly gets the point.'**
String get find_hint;
/// No description provided for @welcome.
///
/// In en, this message translates to:
/// **'Welcome'**
String get welcome;
/// No description provided for @done.
///
/// In en, this message translates to:
/// **'Done'**
String get done;
}
class _AppLocalizationsDelegate

10
lib/l10n/app_localizations_en.dart

@ -8,6 +8,10 @@ import 'app_localizations.dart';
class AppLocalizationsEn extends AppLocalizations {
AppLocalizationsEn([String locale = 'en']) : super(locale);
@override
String get check_internet_connection =>
'Please Check your internet connection.';
@override
String get loading => 'Loading...';
@ -158,4 +162,10 @@ class AppLocalizationsEn extends AppLocalizations {
@override
String get find_hint =>
'The fastest player to answer the question correctly gets the point.';
@override
String get welcome => 'Welcome';
@override
String get done => 'Done';
}

6
lib/main.dart

@ -5,14 +5,14 @@ import 'package:shia_game_flutter/common_ui/theme/theme_service.dart';
import 'package:shia_game_flutter/core/auth_storage/auth_storage.dart';
import 'package:shia_game_flutter/core/routers/my_routes.dart';
import 'package:get/get.dart';
import 'package:get_storage/get_storage.dart';
import 'package:shia_game_flutter/core/utils/local_storage.dart';
import 'package:shia_game_flutter/init_bindings.dart';
import 'package:shia_game_flutter/l10n/app_localizations.dart';
Future<void> main() async {
WidgetsFlutterBinding.ensureInitialized();
await Future.wait([
GetStorage.init(),
LocalStorage.init(),
]);
AuthStorage.loadData();
runApp(const MainApp());
@ -31,7 +31,7 @@ class MainApp extends StatelessWidget {
fallbackLocale: const Locale('en', 'US'),
supportedLocales: const [Locale('en', 'US')],
getPages: appPages,
initialRoute: Routes.battleLeagueQuestionPage,
initialRoute: Routes.masterPage,
localizationsDelegates: const [
AppLocalizations.delegate,
GlobalMaterialLocalizations.delegate,

159
pubspec.lock

@ -25,6 +25,14 @@ packages:
url: "https://pub.dev"
source: hosted
version: "2.1.2"
centrifuge:
dependency: "direct main"
description:
name: centrifuge
sha256: "9605036830de242cbb4b0ea1912b5b2238e588bbf639015018a5320734f97c73"
url: "https://pub.dev"
source: hosted
version: "0.17.0"
change_app_package_name:
dependency: "direct dev"
description:
@ -57,6 +65,22 @@ packages:
url: "https://pub.dev"
source: hosted
version: "1.19.1"
crypto:
dependency: transitive
description:
name: crypto
sha256: c8ea0233063ba03258fbcf2ca4d6dadfefe14f02fab57702265467a19f27fadf
url: "https://pub.dev"
source: hosted
version: "3.0.7"
curl_logger_dio_interceptor:
dependency: "direct main"
description:
name: curl_logger_dio_interceptor
sha256: "0702d32b8ff1b451ba1d9882d57b885061872ebc38384c18243b18b2a0db2a5b"
url: "https://pub.dev"
source: hosted
version: "1.0.1"
dio:
dependency: "direct main"
description:
@ -105,6 +129,22 @@ packages:
url: "https://pub.dev"
source: hosted
version: "2.1.4"
file:
dependency: transitive
description:
name: file
sha256: a3b4f84adafef897088c160faf7dfffb7696046cb13ae90b508c2cbc95d3b8d4
url: "https://pub.dev"
source: hosted
version: "7.0.1"
fixnum:
dependency: transitive
description:
name: fixnum
sha256: b6dc7065e46c974bc7c5f143080a6764ec7a4be6da1285ececdc37be96de53be
url: "https://pub.dev"
source: hosted
version: "1.1.1"
flutter:
dependency: "direct main"
description: flutter
@ -136,6 +176,11 @@ packages:
description: flutter
source: sdk
version: "0.0.0"
flutter_web_plugins:
dependency: transitive
description: flutter
source: sdk
version: "0.0.0"
get:
dependency: "direct main"
description:
@ -144,14 +189,6 @@ packages:
url: "https://pub.dev"
source: hosted
version: "4.7.2"
get_storage:
dependency: "direct main"
description:
name: get_storage
sha256: "39db1fffe779d0c22b3a744376e86febe4ade43bf65e06eab5af707dc84185a2"
url: "https://pub.dev"
source: hosted
version: "2.1.1"
http:
dependency: transitive
description:
@ -256,30 +293,6 @@ packages:
url: "https://pub.dev"
source: hosted
version: "1.1.0"
path_provider:
dependency: transitive
description:
name: path_provider
sha256: "50c5dd5b6e1aaf6fb3a78b33f6aa3afca52bf903a8a5298f53101fdaee55bbcd"
url: "https://pub.dev"
source: hosted
version: "2.1.5"
path_provider_android:
dependency: transitive
description:
name: path_provider_android
sha256: "3b4c1fc3aa55ddc9cd4aa6759984330d5c8e66aa7702a6223c61540dc6380c37"
url: "https://pub.dev"
source: hosted
version: "2.2.19"
path_provider_foundation:
dependency: transitive
description:
name: path_provider_foundation
sha256: "16eef174aacb07e09c351502740fa6254c165757638eba1e9116b0a781201bbd"
url: "https://pub.dev"
source: hosted
version: "2.4.2"
path_provider_linux:
dependency: transitive
description:
@ -336,6 +349,70 @@ packages:
url: "https://pub.dev"
source: hosted
version: "1.4.0"
protobuf:
dependency: transitive
description:
name: protobuf
sha256: "2fcc8a202ca7ec17dab7c97d6b6d91cf03aa07fe6f65f8afbb6dfa52cc5bd902"
url: "https://pub.dev"
source: hosted
version: "5.1.0"
shared_preferences:
dependency: "direct main"
description:
name: shared_preferences
sha256: "6e8bf70b7fef813df4e9a36f658ac46d107db4b4cfe1048b477d4e453a8159f5"
url: "https://pub.dev"
source: hosted
version: "2.5.3"
shared_preferences_android:
dependency: transitive
description:
name: shared_preferences_android
sha256: "46a46fd64659eff15f4638bbe19de43f9483f0e0bf024a9fb6b3582064bacc7b"
url: "https://pub.dev"
source: hosted
version: "2.4.17"
shared_preferences_foundation:
dependency: transitive
description:
name: shared_preferences_foundation
sha256: "4e7eaffc2b17ba398759f1151415869a34771ba11ebbccd1b0145472a619a64f"
url: "https://pub.dev"
source: hosted
version: "2.5.6"
shared_preferences_linux:
dependency: transitive
description:
name: shared_preferences_linux
sha256: "580abfd40f415611503cae30adf626e6656dfb2f0cee8f465ece7b6defb40f2f"
url: "https://pub.dev"
source: hosted
version: "2.4.1"
shared_preferences_platform_interface:
dependency: transitive
description:
name: shared_preferences_platform_interface
sha256: "57cbf196c486bc2cf1f02b85784932c6094376284b3ad5779d1b1c6c6a816b80"
url: "https://pub.dev"
source: hosted
version: "2.4.1"
shared_preferences_web:
dependency: transitive
description:
name: shared_preferences_web
sha256: c49bd060261c9a3f0ff445892695d6212ff603ef3115edbb448509d407600019
url: "https://pub.dev"
source: hosted
version: "2.4.3"
shared_preferences_windows:
dependency: transitive
description:
name: shared_preferences_windows
sha256: "94ef0f72b2d71bc3e700e025db3710911bd51a71cefb65cc609dd0d9a982e3c1"
url: "https://pub.dev"
source: hosted
version: "2.4.1"
sky_engine:
dependency: transitive
description: flutter
@ -445,6 +522,22 @@ packages:
url: "https://pub.dev"
source: hosted
version: "1.1.1"
web_socket:
dependency: transitive
description:
name: web_socket
sha256: "34d64019aa8e36bf9842ac014bb5d2f5586ca73df5e4d9bf5c936975cae6982c"
url: "https://pub.dev"
source: hosted
version: "1.0.1"
web_socket_channel:
dependency: transitive
description:
name: web_socket_channel
sha256: d645757fb0f4773d602444000a8131ff5d48c9e47adfe9772652dd1a4f2d45c8
url: "https://pub.dev"
source: hosted
version: "3.0.3"
xdg_directories:
dependency: transitive
description:
@ -463,4 +556,4 @@ packages:
version: "6.6.1"
sdks:
dart: ">=3.9.2 <4.0.0"
flutter: ">=3.29.0"
flutter: ">=3.35.0"

4
pubspec.yaml

@ -7,6 +7,7 @@ environment:
sdk: ^3.9.2
dependencies:
centrifuge: ^0.17.0
dio: ^5.9.0
draggable_scrollbar: ^0.1.0
equatable: ^2.0.7
@ -16,9 +17,10 @@ dependencies:
flutter_localizations:
sdk: flutter
get: ^4.7.2
get_storage: ^2.1.1
intl: ^0.20.2
pretty_dio_logger: ^1.4.0
curl_logger_dio_interceptor: ^1.0.1
shared_preferences: ^2.5.3
vector_graphics: ^1.1.19
dev_dependencies:

Loading…
Cancel
Save