added lang
This commit is contained in:
parent
20e4b6654e
commit
8088935aef
|
|
@ -0,0 +1,3 @@
|
|||
{
|
||||
"profile_select_lang": "Выберите язык"
|
||||
}
|
||||
|
|
@ -0,0 +1,3 @@
|
|||
{
|
||||
"profile_select_lang": "Dil saýlamak"
|
||||
}
|
||||
|
|
@ -1,2 +1,3 @@
|
|||
export 'bottom_navbar_cubit/bottom_navbar_cubit.dart';
|
||||
export 'user_bloc/user_bloc.dart';
|
||||
export 'language_bloc/language_bloc.dart';
|
||||
|
|
|
|||
|
|
@ -0,0 +1,52 @@
|
|||
import 'dart:async';
|
||||
|
||||
import 'package:easy_localization/easy_localization.dart';
|
||||
import 'package:equatable/equatable.dart';
|
||||
import 'package:flutter/material.dart';
|
||||
import 'package:flutter_bloc/flutter_bloc.dart';
|
||||
import 'package:shared_preferences/shared_preferences.dart';
|
||||
|
||||
import '../../core/core.dart';
|
||||
import '../../data/data.dart';
|
||||
|
||||
part 'language_event.dart';
|
||||
part 'language_state.dart';
|
||||
|
||||
const kDefaultLocale = Locale('ru');
|
||||
|
||||
class LanguageBloc extends Bloc<LanguageEvent, LanguageState> {
|
||||
LanguageBloc() : super(const LanguageState()) {
|
||||
on<LanguageInitial>(_onLanguageInitial);
|
||||
on<LanguageChanged>(_onLanguageChanged);
|
||||
}
|
||||
|
||||
FutureOr<void> _onLanguageChanged(LanguageChanged event, Emitter<LanguageState> emit) async {
|
||||
final ctx = event.context;
|
||||
if (!ctx.mounted) return;
|
||||
|
||||
final lang = event.lang;
|
||||
|
||||
final locale = Locale(lang.code, lang.countryCode);
|
||||
|
||||
await ctx.setLocale(locale);
|
||||
|
||||
emit(state.copyWith(locale: locale));
|
||||
|
||||
/// Keep in shared preference
|
||||
SharedPreferences prefs = await SharedPreferences.getInstance();
|
||||
prefs.setString(activeLang, lang.code);
|
||||
}
|
||||
|
||||
FutureOr<void> _onLanguageInitial(LanguageInitial event, Emitter<LanguageState> emit) async {
|
||||
SharedPreferences prefs = await SharedPreferences.getInstance();
|
||||
final langCode = prefs.getString(activeLang) ?? 'tr';
|
||||
|
||||
final lang = languages.where((l) => l.code == langCode).first;
|
||||
|
||||
emit(
|
||||
state.copyWith(
|
||||
locale: Locale(lang.code, lang.countryCode),
|
||||
),
|
||||
);
|
||||
}
|
||||
}
|
||||
|
|
@ -0,0 +1,20 @@
|
|||
part of 'language_bloc.dart';
|
||||
|
||||
sealed class LanguageEvent extends Equatable {
|
||||
const LanguageEvent();
|
||||
|
||||
@override
|
||||
List<Object> get props => [];
|
||||
}
|
||||
|
||||
final class LanguageInitial extends LanguageEvent {}
|
||||
|
||||
final class LanguageChanged extends LanguageEvent {
|
||||
final Language lang;
|
||||
final BuildContext context;
|
||||
|
||||
const LanguageChanged({required this.lang, required this.context});
|
||||
|
||||
@override
|
||||
List<Object> get props => [lang, context];
|
||||
}
|
||||
|
|
@ -0,0 +1,19 @@
|
|||
part of 'language_bloc.dart';
|
||||
|
||||
class LanguageState extends Equatable {
|
||||
final Locale locale;
|
||||
const LanguageState({
|
||||
this.locale = const Locale('tr', 'TR'),
|
||||
});
|
||||
|
||||
@override
|
||||
List<Object?> get props => [locale];
|
||||
|
||||
LanguageState copyWith({
|
||||
Locale? locale,
|
||||
}) {
|
||||
return LanguageState(
|
||||
locale: locale ?? this.locale,
|
||||
);
|
||||
}
|
||||
}
|
||||
|
|
@ -1,3 +1,4 @@
|
|||
import 'package:easy_localization/easy_localization.dart';
|
||||
import 'package:flutter/material.dart';
|
||||
import 'package:flutter_bloc/flutter_bloc.dart';
|
||||
|
||||
|
|
@ -13,6 +14,9 @@ class MyApp extends StatelessWidget {
|
|||
return MultiBlocProvider(
|
||||
providers: [
|
||||
BlocProvider(create: (context) => di.sl<NavigationCubit>()),
|
||||
BlocProvider(
|
||||
create: (context) => di.sl<LanguageBloc>()..add(LanguageInitial()),
|
||||
),
|
||||
BlocProvider(
|
||||
create: (context) => di.sl<UserBloc>(), //..add(CheckUser()),
|
||||
),
|
||||
|
|
@ -22,6 +26,9 @@ class MyApp extends StatelessWidget {
|
|||
title: appTitle,
|
||||
onGenerateRoute: AppRouter.onGenerateRoute,
|
||||
onGenerateInitialRoutes: (initialRoute) => AppRouter.generateInitialRoutes(initialRoute),
|
||||
localizationsDelegates: context.localizationDelegates,
|
||||
supportedLocales: context.supportedLocales,
|
||||
locale: context.locale,
|
||||
initialRoute: AppRouter.root,
|
||||
),
|
||||
);
|
||||
|
|
|
|||
|
|
@ -4,3 +4,6 @@ const String appTitle = 'Cargo App';
|
|||
// Storage and Databases
|
||||
const String articlesTableName = '';
|
||||
const String databaseName = '';
|
||||
|
||||
// SharedPreferences
|
||||
const String activeLang = 'activeLang';
|
||||
|
|
|
|||
|
|
@ -0,0 +1,6 @@
|
|||
import '../../data.dart';
|
||||
|
||||
List<Language> languages = [
|
||||
Language(id: 1, language: 'Türkmen dili', code: 'tr', countryCode: 'TR'),
|
||||
Language(id: 2, language: 'Русский', code: 'ru', countryCode: 'RU'),
|
||||
];
|
||||
|
|
@ -1 +1,2 @@
|
|||
export 'user_local_data_source.dart';
|
||||
export 'languages_data_source.dart';
|
||||
|
|
|
|||
|
|
@ -0,0 +1,12 @@
|
|||
class Language {
|
||||
Language({
|
||||
required this.id,
|
||||
required this.language,
|
||||
required this.code,
|
||||
required this.countryCode,
|
||||
});
|
||||
int id;
|
||||
String language;
|
||||
String code;
|
||||
String countryCode;
|
||||
}
|
||||
|
|
@ -1,2 +1,3 @@
|
|||
export 'user/user_model.dart';
|
||||
export 'language.dart';
|
||||
export 'user/authentication_response_model.dart';
|
||||
export 'user/user_model.dart';
|
||||
|
|
|
|||
|
|
@ -2,6 +2,7 @@ import 'package:get_it/get_it.dart';
|
|||
|
||||
import 'common.dart';
|
||||
import 'cubits.dart';
|
||||
import 'language.dart';
|
||||
import 'user.dart';
|
||||
|
||||
final sl = GetIt.instance;
|
||||
|
|
@ -10,6 +11,7 @@ final sl = GetIt.instance;
|
|||
Future<void> init() async {
|
||||
// Register features
|
||||
registerUserFeature();
|
||||
registerLanguageFeature();
|
||||
// registerCategoryFeature();
|
||||
// registerProductFeature();
|
||||
// registerDeliveryInfoFeature();
|
||||
|
|
|
|||
|
|
@ -0,0 +1,7 @@
|
|||
import '../application/language_bloc/language_bloc.dart';
|
||||
import 'di.dart';
|
||||
|
||||
void registerLanguageFeature() {
|
||||
// Product BLoC and Use Cases
|
||||
sl.registerFactory(() => LanguageBloc());
|
||||
}
|
||||
|
|
@ -1,3 +1,4 @@
|
|||
import 'package:easy_localization/easy_localization.dart';
|
||||
import 'package:flutter/material.dart';
|
||||
import 'package:flutter/services.dart';
|
||||
import 'package:flutter_bloc/flutter_bloc.dart';
|
||||
|
|
@ -8,6 +9,7 @@ import 'di/di.dart' as di;
|
|||
|
||||
Future<void> main() async {
|
||||
WidgetsFlutterBinding.ensureInitialized();
|
||||
await EasyLocalization.ensureInitialized();
|
||||
|
||||
// await GetStorage.init();
|
||||
|
||||
|
|
@ -25,13 +27,24 @@ Future<void> main() async {
|
|||
statusBarBrightness: Brightness.dark,
|
||||
));
|
||||
|
||||
runApp(Phoenix(child: const MyApp()));
|
||||
runApp(
|
||||
EasyLocalization(
|
||||
supportedLocales: const [
|
||||
Locale('tr', 'TR'),
|
||||
Locale('ru', 'RU'),
|
||||
],
|
||||
path: 'assets/locale',
|
||||
fallbackLocale: const Locale('tr', 'TR'),
|
||||
startLocale: const Locale('tr', 'TR'),
|
||||
child: Phoenix(child: const MyApp()),
|
||||
),
|
||||
);
|
||||
}
|
||||
|
||||
|
||||
/// ADDING PROGRESS
|
||||
// 1 create bloc
|
||||
// 2 create use_case under domain folder
|
||||
// 3 create repository
|
||||
// 4 create repository implementation
|
||||
// 5 create data source
|
||||
// 6 add di register
|
||||
// 6 add di register
|
||||
|
|
|
|||
|
|
@ -1,8 +1,8 @@
|
|||
import 'package:cargo/presentation/presentation.dart';
|
||||
import 'package:flutter/material.dart';
|
||||
|
||||
import '../../configs/configs.dart';
|
||||
import '../../core/core.dart';
|
||||
import '../widgets/widgets.dart';
|
||||
|
||||
class OrdersScreen extends StatelessWidget {
|
||||
const OrdersScreen({super.key});
|
||||
|
|
|
|||
|
|
@ -1,7 +1,6 @@
|
|||
import 'package:cargo/configs/app_typography.dart';
|
||||
import 'package:cargo/configs/space.dart';
|
||||
import 'package:cargo/presentation/presentation.dart';
|
||||
import 'package:easy_localization/easy_localization.dart';
|
||||
import 'package:flutter/material.dart';
|
||||
import 'package:flutter/widgets.dart';
|
||||
|
||||
import '../../configs/configs.dart';
|
||||
import '../../core/core.dart';
|
||||
|
|
@ -103,16 +102,19 @@ class ProfileScreen extends StatelessWidget {
|
|||
padding: const EdgeInsets.all(16.0),
|
||||
child: Column(
|
||||
children: [
|
||||
/// identity
|
||||
const RowWidget(
|
||||
text: 'Dil saýlamak (Türkmen dili)',
|
||||
leadingIcon: Icons.language_outlined,
|
||||
trailingIcon: Icons.arrow_forward_ios,
|
||||
/// language
|
||||
GestureDetector(
|
||||
onTap: () => onSelectLang(context),
|
||||
child: Container(
|
||||
color: Colors.transparent,
|
||||
child: RowWidget(
|
||||
text: 'profile_select_lang'.tr(),
|
||||
leadingIcon: Icons.language_outlined,
|
||||
trailingIcon: Icons.arrow_forward_ios,
|
||||
),
|
||||
),
|
||||
),
|
||||
|
||||
/// gap
|
||||
Space.yf(1),
|
||||
|
||||
/// name surname
|
||||
const RowWidget(
|
||||
text: 'Gizlinlik syýasaty',
|
||||
|
|
@ -120,9 +122,6 @@ class ProfileScreen extends StatelessWidget {
|
|||
trailingIcon: Icons.arrow_forward_ios,
|
||||
),
|
||||
|
||||
/// gap
|
||||
Space.yf(1),
|
||||
|
||||
/// phone
|
||||
const RowWidget(
|
||||
text: 'Ulanyş şertleri',
|
||||
|
|
@ -175,28 +174,31 @@ class RowWidget extends StatelessWidget {
|
|||
|
||||
@override
|
||||
Widget build(BuildContext context) {
|
||||
return Row(
|
||||
children: [
|
||||
Icon(
|
||||
leadingIcon,
|
||||
color: AppColors.darkGrey,
|
||||
),
|
||||
Space.x!,
|
||||
Text(
|
||||
text,
|
||||
style: AppText.b1!.copyWith(
|
||||
color: AppColors.darkGrey,
|
||||
),
|
||||
),
|
||||
if (trailingIcon != null) ...[
|
||||
const Spacer(),
|
||||
return Padding(
|
||||
padding: Space.vf(0.5),
|
||||
child: Row(
|
||||
children: [
|
||||
Icon(
|
||||
trailingIcon,
|
||||
leadingIcon,
|
||||
color: AppColors.darkGrey,
|
||||
size: AppDimensions.normalize(7),
|
||||
),
|
||||
]
|
||||
],
|
||||
Space.x!,
|
||||
Text(
|
||||
text,
|
||||
style: AppText.b1!.copyWith(
|
||||
color: AppColors.darkGrey,
|
||||
),
|
||||
),
|
||||
if (trailingIcon != null) ...[
|
||||
const Spacer(),
|
||||
Icon(
|
||||
trailingIcon,
|
||||
color: AppColors.darkGrey,
|
||||
size: AppDimensions.normalize(7),
|
||||
),
|
||||
]
|
||||
],
|
||||
),
|
||||
);
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -0,0 +1,73 @@
|
|||
import 'package:cargo/configs/configs.dart';
|
||||
import 'package:flutter/material.dart';
|
||||
import 'package:flutter_bloc/flutter_bloc.dart';
|
||||
|
||||
import '../../application/application.dart';
|
||||
import '../../data/data_sources/local/languages_data_source.dart';
|
||||
|
||||
class BottomSheetContent extends StatelessWidget {
|
||||
const BottomSheetContent({super.key});
|
||||
|
||||
@override
|
||||
Widget build(BuildContext context) {
|
||||
return SizedBox(
|
||||
height: AppDimensions.normalize(65),
|
||||
child: BlocBuilder<LanguageBloc, LanguageState>(
|
||||
builder: (context, state) {
|
||||
return Container(
|
||||
padding: Space.vf(),
|
||||
child: ListView.separated(
|
||||
itemCount: languages.length,
|
||||
separatorBuilder: (context, index) => Padding(
|
||||
padding: Space.hf(1),
|
||||
child: const Divider(),
|
||||
),
|
||||
itemBuilder: (context, index) {
|
||||
final lang = languages[index];
|
||||
return ListTile(
|
||||
title: Text(
|
||||
lang.language,
|
||||
style: AppText.b1,
|
||||
),
|
||||
trailing: state.locale.languageCode == lang.code
|
||||
? Icon(
|
||||
Icons.check,
|
||||
color: Colors.green,
|
||||
size: 26.0,
|
||||
shadows: [
|
||||
Shadow(
|
||||
offset: const Offset(0, 2),
|
||||
blurRadius: 3.0,
|
||||
color: Colors.black.withOpacity(0.3),
|
||||
),
|
||||
],
|
||||
)
|
||||
: null,
|
||||
onTap: () {
|
||||
debugPrint('lang_selection');
|
||||
context.read<LanguageBloc>().add(
|
||||
LanguageChanged(
|
||||
lang: lang,
|
||||
context: context,
|
||||
),
|
||||
);
|
||||
Navigator.of(context).pop();
|
||||
},
|
||||
);
|
||||
},
|
||||
),
|
||||
);
|
||||
},
|
||||
),
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
Future<void> onSelectLang(BuildContext context) async {
|
||||
await showModalBottomSheet(
|
||||
context: context,
|
||||
builder: (context) {
|
||||
return const BottomSheetContent();
|
||||
},
|
||||
);
|
||||
}
|
||||
|
|
@ -9,3 +9,4 @@ export 'order_header.dart';
|
|||
export 'successful_auth_dialog.dart';
|
||||
export 'vertical_line.dart';
|
||||
export 'dashed_line.dart';
|
||||
export 'lang_selection.dart';
|
||||
|
|
|
|||
21
pubspec.lock
21
pubspec.lock
|
|
@ -81,6 +81,22 @@ packages:
|
|||
url: "https://pub.dev"
|
||||
source: hosted
|
||||
version: "0.10.1"
|
||||
easy_localization:
|
||||
dependency: "direct main"
|
||||
description:
|
||||
name: easy_localization
|
||||
sha256: fa59bcdbbb911a764aa6acf96bbb6fa7a5cf8234354fc45ec1a43a0349ef0201
|
||||
url: "https://pub.dev"
|
||||
source: hosted
|
||||
version: "3.0.7"
|
||||
easy_logger:
|
||||
dependency: transitive
|
||||
description:
|
||||
name: easy_logger
|
||||
sha256: c764a6e024846f33405a2342caf91c62e357c24b02c04dbc712ef232bf30ffb7
|
||||
url: "https://pub.dev"
|
||||
source: hosted
|
||||
version: "0.0.2"
|
||||
equatable:
|
||||
dependency: "direct main"
|
||||
description:
|
||||
|
|
@ -134,6 +150,11 @@ packages:
|
|||
url: "https://pub.dev"
|
||||
source: hosted
|
||||
version: "3.0.2"
|
||||
flutter_localizations:
|
||||
dependency: transitive
|
||||
description: flutter
|
||||
source: sdk
|
||||
version: "0.0.0"
|
||||
flutter_map:
|
||||
dependency: "direct main"
|
||||
description:
|
||||
|
|
|
|||
|
|
@ -26,6 +26,7 @@ dependencies:
|
|||
flutter_map: ">=6.0.0 <7.0.0"
|
||||
latlong2: ^0.9.0
|
||||
flutter_map_marker_cluster: ^1.3.6
|
||||
easy_localization: ^3.0.7
|
||||
|
||||
dev_dependencies:
|
||||
flutter_test:
|
||||
|
|
@ -40,6 +41,7 @@ flutter:
|
|||
- assets/svg/
|
||||
- assets/svg/logo/
|
||||
- assets/images/
|
||||
- assets/locale/
|
||||
|
||||
# An image asset can refer to one or more resolution-specific "variants", see
|
||||
# https://flutter.dev/assets-and-images/#resolution-aware
|
||||
|
|
|
|||
Loading…
Reference in New Issue