easy_localization
easy_localization copied to clipboard
setLocale() or context.locale=Locale("...") is not Updating app locale instantly
I've updated easy_localization: 3.0.0 package from easy_localization: ^2.3.3. When i was using easy_localization: ^2.3.3 it is updating my app locale instantly whenever i called
setState(() {
context.locale = Locale("en");
});
But since I've updated the package version to 3.0.0 it is not updating the locale instantly. I've to hot restart the whole app to see the changes.
Here is what im doing in version 3.0.0
onTap: () async { await homeController .setLanguage("EN") .then((value) async { await context .setLocale( const Locale( "en")); }) },
And here is what im doing in version 2.3.3 (which is working,and updating locale instantly)
onTap: () { homeController .setLanguage("EN"); setState(() { context.locale = const Locale( "en"); }); },
I have the same regression on my app too. The local has been changed, but there is now refresh. Is this a breaking change and how can I force a refresh on locale change if so ?
For me the app text direction changes based on the new language(rtl) but the new languages' keys doesn't load and UI not updating. No error messages
Same thing happening on my app
same issue here
same energy on my end
Thanks for issue, i will check
I have the same problem with easy_localization: ^3.0.0 with Arabic and English, when changing the current locale the direction changes but the actual localized titles don't.
the same issue in my app. any updates?
I found where is the isuue is. I use GetMaterialApp from Get package to initialize App.
GetMaterialApp( localizationsDelegates: context.localizationDelegates, supportedLocales: context.supportedLocales, locale: context.locale, debugShowCheckedModeBanner: false, initialRoute: '/', onGenerateRoute: RouteGenerator.generateRoute, ),
When I change it to normal one it works.
MaterialApp( localizationsDelegates: context.localizationDelegates, supportedLocales: context.supportedLocales, locale: context.locale, debugShowCheckedModeBanner: false, initialRoute: '/', onGenerateRoute: RouteGenerator.generateRoute, ),
I found where is the isuue is. I use
GetMaterialAppfromGetpackage to initialize App.GetMaterialApp( localizationsDelegates: context.localizationDelegates, supportedLocales: context.supportedLocales, locale: context.locale, debugShowCheckedModeBanner: false, initialRoute: '/', onGenerateRoute: RouteGenerator.generateRoute, ),When I change it to normal one it works.
MaterialApp( localizationsDelegates: context.localizationDelegates, supportedLocales: context.supportedLocales, locale: context.locale, debugShowCheckedModeBanner: false, initialRoute: '/', onGenerateRoute: RouteGenerator.generateRoute, ),
This issue here that simply removing GetMaterialApp will be very difficult because literally, the whole app depends on it.
I have found a possible solution.
In case you are using GetMaterialApp you should when changing the current language call Get.updateLocale() to inform GetMaterialApp about the language change
final _newLocale = Locale('ar', 'EG')
await context.setLocale(_newLocale); // change `easy_localization` locale
Get.updateLocale(_newLocale); // change `Get` locale direction
I have found a possible solution.
In case you are using
GetMaterialAppyou should when changing the current language callGet.updateLocale()to informGetMaterialAppabout the language changefinal _newLocale = Locale('ar', 'EG') await context.setLocale(_newLocale); // change `easy_localization` locale Get.updateLocale(_newLocale); // change `Get` locale direction
It worked thanks 👏
I have found a possible solution.
In case you are using
GetMaterialAppyou should when changing the current language callGet.updateLocale()to informGetMaterialAppabout the language changefinal _newLocale = Locale('ar', 'EG') await context.setLocale(_newLocale); // change `easy_localization` locale Get.updateLocale(_newLocale); // change `Get` locale direction
Okay @AhmedAbouelkher Thanks for the Solution. It's working now 👍 I'm closing the issue now..
I have found a possible solution.
In case you are using
GetMaterialAppyou should when changing the current language callGet.updateLocale()to informGetMaterialAppabout the language changefinal _newLocale = Locale('ar', 'EG') await context.setLocale(_newLocale); // change `easy_localization` locale Get.updateLocale(_newLocale); // change `Get` locale direction
What if you aren't using Get? I still have this problem!
Same issue here with 2.3.3 (can't use 3.0 due to not supporting flutter 2.0 in the current app) and not using Get. Need to actually hot reload the app for changes to actually take place, if not the font size weirdly changes but not the language.
Just posting again to say that this actually works: https://stackoverflow.com/questions/43778488/how-to-force-flutter-to-rebuild-redraw-all-widgets
@override
Widget build(BuildContext context) {
rebuildAllChildren(context);
return MaterialApp( ....
}
void rebuildAllChildren(BuildContext context) {
void rebuild(Element el) {
el.markNeedsBuild();
el.visitChildren(rebuild);
}
(context as Element).visitChildren(rebuild);
}
It was posted by the author of the i18n_extension ( https://pub.dev/packages/i18n_extension ) and even though it shouldn't be recommended it seems to be the only way to inmediately refresh the widget tree to show the new locale properly.
I had the same problem, becuase I was missing locale: context.locale, in MaterialApp
class MyApp extends StatelessWidget {
@override
Widget build(BuildContext context) {
return MaterialApp(
localizationsDelegates: context.localizationDelegates,
supportedLocales: context.supportedLocales,
locale: context.locale,
home: MyHomePage()
);
}
}
our app is not using Get, it has locale: context.locale set and still the language changes only if the whole screen is redrawn (ie. closed and opened again) - any other widget that's visible or was created before the language change doesn't change its content to match selected language.
using a DropdownButton to set locale
onChanged: (value) async {
if (value != null) {
await context.setLocale(value);
}
},
example of 2 locale changes, one after the other
I/flutter (19778): [🌎 Easy Localization] [DEBUG] Load asset from assets/translations
I/flutter (19778): [🌎 Easy Localization] [INFO] Locale de changed
I/flutter (19778): [🌎 Easy Localization] [DEBUG] Build
I/flutter (19778): [🌎 Easy Localization] [DEBUG] Init Localization Delegate
I/flutter (19778): [🌎 Easy Localization] [DEBUG] Init provider
I/flutter (19778): [🌎 Easy Localization] [DEBUG] Load Localization Delegate
I/flutter (19778): [🌎 Easy Localization] [INFO] Locale de saved
I/flutter (19778): [🌎 Easy Localization] [DEBUG] Load asset from assets/translations
I/flutter (19778): [🌎 Easy Localization] [INFO] Locale en changed
I/flutter (19778): [🌎 Easy Localization] [DEBUG] Build
I/flutter (19778): [🌎 Easy Localization] [DEBUG] Init Localization Delegate
I/flutter (19778): [🌎 Easy Localization] [DEBUG] Init provider
I/flutter (19778): [🌎 Easy Localization] [DEBUG] Load Localization Delegate
I/flutter (19778): [🌎 Easy Localization] [INFO] Locale en saved
our app is not using Get, it has
locale: context.localeset and still the language changes only if the whole screen is redrawn (ie. closed and opened again) - any other widget that's visible or was created before the language change doesn't change its content to match selected language.using a DropdownButton to set locale
onChanged: (value) async { if (value != null) { await context.setLocale(value); } },example of 2 locale changes, one after the other
I/flutter (19778): [🌎 Easy Localization] [DEBUG] Load asset from assets/translations I/flutter (19778): [🌎 Easy Localization] [INFO] Locale de changed I/flutter (19778): [🌎 Easy Localization] [DEBUG] Build I/flutter (19778): [🌎 Easy Localization] [DEBUG] Init Localization Delegate I/flutter (19778): [🌎 Easy Localization] [DEBUG] Init provider I/flutter (19778): [🌎 Easy Localization] [DEBUG] Load Localization Delegate I/flutter (19778): [🌎 Easy Localization] [INFO] Locale de saved I/flutter (19778): [🌎 Easy Localization] [DEBUG] Load asset from assets/translations I/flutter (19778): [🌎 Easy Localization] [INFO] Locale en changed I/flutter (19778): [🌎 Easy Localization] [DEBUG] Build I/flutter (19778): [🌎 Easy Localization] [DEBUG] Init Localization Delegate I/flutter (19778): [🌎 Easy Localization] [DEBUG] Init provider I/flutter (19778): [🌎 Easy Localization] [DEBUG] Load Localization Delegate I/flutter (19778): [🌎 Easy Localization] [INFO] Locale en saved
Could you share you MaterialApp widget?
I tried this solution which allows me to rebuild the whole widget tree by adding a new unique key every time the localization change.
return MaterialApp(
key: UniqueKey(),
our app is not using Get, it has
locale: context.localeset and still the language changes only if the whole screen is redrawn (ie. closed and opened again) - any other widget that's visible or was created before the language change doesn't change....Could you share you
MaterialAppwidget?
Here you go:
void main() async {
WidgetsFlutterBinding.ensureInitialized();
await EasyLocalization.ensureInitialized();
runApp(
EasyLocalization(
supportedLocales: [Locale('en'), Locale('de')],
path: 'assets/translations',
fallbackLocale: Locale('en'),
child: App(),
),
);
}
class App extends StatelessWidget {
@override
Widget build(BuildContext context) {
return MaterialApp(
localizationsDelegates: context.localizationDelegates,
supportedLocales: context.supportedLocales,
locale: context.locale,
home: MainScreen(),
);
}
}
I tried this solution which allows me to rebuild the whole widget tree by adding a new unique key every time the localization change.
return MaterialApp( key: UniqueKey(),
this really feels like too much to do to in Flutter whose performance is based on redrawing only necessary views...
I have found a possible solution. In case you are using
GetMaterialAppyou should when changing the current language callGet.updateLocale()to informGetMaterialAppabout the language changefinal _newLocale = Locale('ar', 'EG') await context.setLocale(_newLocale); // change `easy_localization` locale Get.updateLocale(_newLocale); // change `Get` locale directionOkay @AhmedAbouelkher Thanks for the Solution. It's working now 👍 I'm closing the issue now..
I have used it. But still sometime not working.
`if (newValue == LocaleKeys.arabic.tr()) { this.setState(() { dropdownValue = LocaleKeys.arabic.tr();
context.setLocale(Locale('ar'));
});`
`if (newValue == LocaleKeys.arabic.tr()) { this.setState(() { dropdownValue = LocaleKeys.arabic.tr();
context.setLocale(Locale('ar')); });`
no, that does nothing...
`if (newValue == LocaleKeys.arabic.tr()) {
this.setState(() {
dropdownValue = LocaleKeys.arabic.tr();
context.setLocale(Locale('ar'));});`no, that does nothing...
it's work with me
yeah, thank you, your comment made me think and it seems that in my case it doesn't work (doesn't rebuild the screen on which the dropdown is) because the dropdown button and setLocale are located several widgets away from the content that should change language but didn't.
I will now implement some kind of listener or move the whole setLocale logic up the tree and use setState to force a refresh.
Why is this closed?
same issue here, Why is this closed ?
Same issue, only some widgets are rebuilding, but most of the app stays in the old selected language.