背景之前开发者总是反映我的应用切换了语言,但是工具类获取的字符串没有变化。其实这个问题很简单。你切换语言的Context只作用于你的Activity,不会对你的Application做同样的操作。知道了这一点,解决问题就很简单了。为了省事,告诉你LanguageUtils是封装好的,一行代码就可以完成多国语言的切换。分分钟完成类似微信的语言切换。使用Gradle:implementation'com.blankj:utilcode:latest_version'APIslanguage-related->LanguageUtils.java->DemoapplySystemLanguage:应用系统语言applyLanguage:应用语言原理如果我们的应用没有设置android:configChanges="locale|layoutDirection",然后应用随着系统语言设置的改变而改变。比如你的应用适配了英文(values-en-rUS)和简体中文(values-zh-rCN),那么如果你在设置中切换为英文,你会回到你的应用中,你的Activity会再次重新创建,将Activity#Resource#Configuration#Locale设置为当前系统语言,这样可以跟随系统语言设置的变化,但是Application并没有重启,所以这就导致了一个Open的问题提及。解决跟随系统变化的问题,只需要在Activity#onCreate的生命周期中设置Application#Resource#Configuration#Locale为系统的locale,那么如何读取系统的locale,知道上一屏适配方案熟悉这个方法的人应该也能想到这个方法:Resources.getSystem().getConfiguration().locale,这样我们的Application也会切换到系统语言。注意Locale的更新需要兼容低版本。具体调用代码可以参考如下:),locale.getLanguage())&&equals(contextLocale.getCountry(),locale.getCountry())){return;}DisplayMetricsdm=resources.getDisplayMetrics();if(Build.VERSION.SDK_INT>=Build.VERSION_CODES.JELLY_BEAN_MR1){config.setLocale(locale);context.createConfigurationContext(config);}else{config.locale=locale;}resources.updateConfiguration(config,dm);}那么在应用内切换语言呢?我们可以像系统切换语言一样关闭自己所有的Activity,然后启动首页的Activity。在打开的Activity#onCreate中,放入Activity和Application的Locale可以设置成我们设置的语言。当然,这个设置需要保存。根据自己的需要决定是保存在服务器上还是本地。那么如何关闭所有的活动呢?我们可以增加Intent的标志是Intent.FLAG_ACTIVITY_CLEAR_TOP|Intent.FLAG_ACTIVITY_CLEAR_TASK,相关代码如下:privatestaticvoidapplyLanguage(@NonNullfinalLocalelocale,finalStringactivityClassName,finalbooleanisFollowSystem){if(isFollowSystem){//如果是跟随系统,则sp不会保存任何东西SPUtils.get().put(KEY_LOCALE,"");}else{//否则保存设置的语言并在onCreate中应用"+localCountry);}updateLanguage(Utils.getApp(),locale);//更新ApplicationIntent的语言intent=newIntent();StringrealActivityClassName//如果传入的activityClassName为空,则启动launcherActivity。=TextUtils.isEmpty(activityClassName)?getLauncherActivity():activityClassName;intent.setComponent(newComponentName(Utils.getApp(),realActivityClassName));intent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK|Intent.FLAG_ACTIVITY_CLEAR_TOP|Intent.FLAG_LEARTIVITY.ls)().startActivity(intent);//关闭其他Activity,启动realActivityClassName的Activity}//工具类在ActivityLifecycleCallbacks中调用该函数#onActivityCreatedstaticvoidapplyLanguage(@NonNullfinalActivityactivity){finalStringspLocale=SPUtils.getInstance().getString(KEY_LOCALE);//获取保存的语言if(TextUtils.isEmpty(spLocale)){//如果为空表示跟随系统,则更新系统语言。LocalesysLocale=Resources.getSystem().getConfiguration().locale;updateLanguage(Utils.getApp(),sysLocale);updateLanguage(activity,sysLocale);return;}//读取sp保存的语言并应用语言String[]language_country=spLocale.split("\\$");if(language_country.length!=2){Log.e("LanguageUtils","Thestringof"+spLocale+"isnotinthecorrectformat.");return;}LocalesettingLocale=newLocale(language_country[0],language_country[1]);updateLanguage(Utils.getApp(),settingLocale);updateLanguage(activity,settingLocale);}根据以上分析:如果应用根据系统设置切换language,那么就靠我的工具类,它会自动给你更新Application的语言。如果需要在应用中切换语言,调用LanguageUtils.applyLanguage(Locale.你要设置的语言,"com.blankj.launcher.pkg.MainActivity/*切换语言后你想跳转的页面即可。如果为空,则启动应用程序的启动器Activity*/")。如果需要在应用中切换语言跟随系统设置语言,则调用LanguageUtils.applySystemLanguage(""/*切换语言后要跳转到的页面,如果为空,则启动应用的启动器Activity*/);就是这样。epilogue功能其实很简单,但是总是缺少能够分析透彻并完美分享的人。希望我这次的分享能够让大家看到这一点,从而提高你们以后的技能。
