您的位置:首页 > 移动开发

Android 反射实战 - 更换APP皮肤<3>

2015-12-10 15:57 405 查看
前面的两节写了一下,好像和真正更新皮肤没什么特别关系,这篇提供一个demo供阅读者了解一下,根据我提供的链接,下载我的demo.

操作步骤如下:

<1> : eclipse中,先导入OneplusFactoryApp工程,如下:

<2> : 再导入OneplusSkin这个工程,如下:

这个工程只是在values文件夹下把替换对应的资源更新到values各个文件里面,比如如果更新文字内容,那么对应colors.xml,可以将上面两个工程的资源进行对比,基本上就明白了.

这个工程build好了以后,我是生成的apk放在手机sdcard/路径下的,当然很多时候,很多人会把OneplusSkin.apk改成OneplusSkin.skin或者OneplusSkin.theme的形式,然后再放入手机里面做测试.

<3> 主工程大致的思路是这样的:

/**
* @author zhibao.liu
* @date 2015-12-2
* @company : oneplus.Inc
*/
public class OneplusFactory implements Factory {

/**
* Store the view item that need skin changing in the activity
* 保存所有子view的视窗和对应的属性
*/
private List<OneplusSkinItem> mSkinItems = new ArrayList<OneplusSkinItem>();

@Override
public View onCreateView(String name, Context context, AttributeSet attrs) {
// TODO Auto-generated method stub

View view = createView(context, name, attrs);

if (view == null) {
return null;
}

parseSkinAttr(context, attrs, view);

return view;
}
... ...


先通过上面收集和获取所有view的种类和属性,并且保存到数据结构体中.

有了上面的数据和信息.

<4> : 下面获取皮肤包里面的资源:

File file = new File(skinPkgPath);
if(file == null || !file.exists()){
return null;
}

PackageManager mPm = context.getPackageManager();
PackageInfo mInfo = mPm.getPackageArchiveInfo(skinPkgPath, PackageManager.GET_ACTIVITIES);
skinPackageName = mInfo.packageName;

AssetManager assetManager = AssetManager.class.newInstance();
Method addAssetPath = assetManager.getClass().getMethod("addAssetPath", String.class);
addAssetPath.invoke(assetManager, skinPkgPath);

Resources superRes = context.getResources();
Resources skinResource = new Resources(assetManager,superRes.getDisplayMetrics(),superRes.getConfiguration());
... ...
这个在前面说过了,获取皮肤包[OneplusSkin.apk] , 获取以后将其加载到系统资源路径下,这样就可以让第三方调用了.
<5> : 有View所有信息,又有了所有替换资源信息,接下来就是用从皮肤包里面获取的资源替换当前的资源

@Override
public void onThemeUpdate() {
// TODO Auto-generated method stub
if(!isResponseOnSkinChanging){
return;
}
mFactory.applySkin();
}
... ...


<6> : 具体的替换如下:
tv.setTextColor(OneplusSkinManager.getInstance().convertToColorStateList(attrValueRefId));
由于工程里面有十多个java文件,具体还是阅读源代码,更加快捷.

如果有疑惑可以给我留言,第一时间回复.
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: