微信中可以动态设置,apk的语言版本,最近尝试实现了这个功能。
我们知道,android本身就支持多国语言版本的。
不过这个语言的切换 依赖于系统的的语言设置,见图
也依赖apk本身values多国语言的资源配置,en代表英文,zh代表中文
通常来说,在android系统上实现功能,最好的借助系统提供的api,如果没有明确的api,则想办法曲线救国。
实际上本博客内提供的实现方法,就是一个曲线救国的方式,下面就介绍下他的核心思路。
1.在values中配置相应的 语言资源
2.更改当前系统Configuration的配置信息
3.指定的控件重新加载 语言资源
第一步,大家都会,不多做介绍
第二步,直接上代码
// 刷新显示配置-
public void refreshTheLanguage() {
// 得到SharedPreferences中存储的 语言配置信息
String str = getLanguage();
Resources localResources = this.context.getResources();
// 判断 系统配置设置的 国家语言 是否和 SharedPreferences中存储的 一致
if (!localResources.getConfiguration().locale.getLanguage().equals(str)) {
// 得到系统配置信息类
Configuration localConfiguration = context.getResources()
.getConfiguration();
// 创建Locale类(简单理解为 所在地区 类)
Locale localLocale = new Locale(str);
// 设置默认地区信息
Locale.setDefault(localLocale);
// 将系统配置中的 地区信息 重新赋值为 自行设置的
localConfiguration.locale = localLocale;
DisplayMetrics localDisplayMetrics = localResources
.getDisplayMetrics();
// 更新系统的配置信息
localResources.updateConfiguration(localConfiguration,
localDisplayMetrics);
}
}第三步,view重新加载values资源即可
language.setText(R.string.language);
以微信为例子,设置语言的activity 肯定是 5级界面,到这来就涉及到 activity 和 activity之间 通信的问题。
方案有2种,1.广播, 2.使用观察者模式
我个人比较喜欢第二种,觉得观察者模式更轻一些。
1.创建一个被观察者
import java.util.Observable;
public class SwitchLanguageObservable extends Observable {
@Override
public void notifyObservers() {
setChanged();
super.notifyObservers();
}
@Override
public void notifyObservers(Object data) {
setChanged();
super.notifyObservers(data);
}
}
2.创建一个观察者,并提供回调方法
import java.util.Observable;
import java.util.Observer;
public class SwitchLanguageObserver implements Observer {
private ObserverChange mObserverChange;
public SwitchLanguageObserver(Observable simpleObservable) {
simpleObservable.addObserver(this);
}
@Override
public void update(Observable observable, Object data) {
if (mObserverChange != null) mObserverChange.observerChange();
}
public void setOnObserverChange(ObserverChange observerChange) {
this.mObserverChange = observerChange;
}
public interface ObserverChange {
public void observerChange();
}
3.将被观察 设置为全局对象,方便其他的activity调用
import com.example.demo.utils.LanguageSettingUtil;
import com.example.demo.utils.SwitchLanguageObservable;
import android.app.Application;
public class TestApplication extends Application {
/**
* 语言设置工具类
* */
private LanguageSettingUtil languageSetting;
/**
* 语言设置 被观察对象
* */
private SwitchLanguageObservable switchLangObs;
@Override
public void onCreate() {
super.onCreate();
// 注册 切换语言 工具类
LanguageSettingUtil.init(this);// 初始化
languageSetting = LanguageSettingUtil.get();// 检查是否已经初始化
switchLangObs = new SwitchLanguageObservable();
}
public LanguageSettingUtil getLanguageSetting() {
return languageSetting;
}
public SwitchLanguageObservable getSwitchLangObs() {
return switchLangObs;
}
}
4.能够切换语言的view,进行注册
language = (TextView) findViewById(R.id.language);
TestApplication app = (TestApplication) getApplication();
obs = app.getSwitchLangObs();
obser = new SwitchLanguageObserver(obs);
obser.setOnObserverChange(new ObserverChange() {
@Override
public void observerChange() {
language.setText(R.string.language);
}
});
5.被观察的对象,进行注册
import com.example.demo.utils.LanguageSettingUtil;
import com.example.demo.utils.SwitchLanguageObservable;
import android.app.Activity;
import android.os.Bundle;
import android.view.View;
import android.view.View.OnClickListener;
import android.widget.TextView;
public class SwitchLanguageActivity extends Activity implements OnClickListener {
private LanguageSettingUtil languageSetting;
private TextView switchCh, switchEn;
private SwitchLanguageObservable obs;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_switch_language);
TestApplication app = (TestApplication) getApplication();
switchCh = (TextView) findViewById(R.id.switch_ch);
switchEn = (TextView) findViewById(R.id.switch_en);
switchCh.setOnClickListener(this);
switchEn.setOnClickListener(this);
languageSetting = app.getLanguageSetting();// 检查是否已经初始化
obs = app.getSwitchLangObs();
}
@Override
protected void onDestroy() {
super.onDestroy();
}
@Override
public void onClick(View view) {
switch (view.getId()) {
case R.id.switch_ch:
languageSetting.saveLanguage("zh");
LanguageSettingUtil.get().refreshLanguage();// 刷新
obs.notifyObservers();
finish();
break;
case R.id.switch_en:
languageSetting.saveLanguage("en");
LanguageSettingUtil.get().refreshLanguage();// 刷新
obs.notifyObservers();
finish();
break;
default:
break;
}
}上面的例子可以 看出代码步骤。
设置语言信息
languageSetting.saveLanguage("zh");刷新系统配置信息
LanguageSettingUtil.get().refreshLanguage();
被观察者发生变化
obs.notifyObservers();
观察者回调接口的实现方法,实现方法中重新设置了string信息
obser.setOnObserverChange(new ObserverChange() {
@Override
public void observerChange() {
language.setText(R.string.language);
}
});
然后app内 动态切换语言,就实现了。
源码链接/detail/tianya19871987/8600969