- 一個進程有一個ResourcesManager類, 單例; 一個ResourcesManager類管理多個Resources;
- ResourcesManager中, 由
mActiveResources的map, 保存多個ResourcesKey和Resources的鍵值對, (不同分辨率, 語言); 由getTopLevelResources獲取對應(yīng)的Resources - ContextImpl對象, 包含一個
mResources的變量, context對象的getResources即返回此變量, 而mRseources對象由getTopLevelResources方法獲取 - Resources對象包含 AssetManager 對象
- app不走正常的初始化,沒法獲得AssetManager, 但是可以通過反射創(chuàng)建, AssetManager的私有方法
addAssetPath接受一個dex文件的路徑, 可以生成對于的AssetManager
AssetManager assetManager = AssetManager.class.newInstance();
Method addAssetPathMethod = assetManager.getClass().getMethod("addAssetPath", String.class);
addAssetPathMethod.invoke(assetManager, apkPath );
- 根據(jù)原apk的
context對象, 可以創(chuàng)建一個新的Resources對象
Resources superRes = context.getResources();
Resources apkResource = new Resources(assetManager,superRes.getDisplayMetrics(),superRes.getConfiguration());
每個資源屬性的定義, 由 packageName, TypeName, entryName 構(gòu)成, 可以由
getResourceName(resId)獲得, "package:type/entry", 也可分別獲得getResourcePackageNamegetResourceTypeNamegetResourceEntryName由
Resources.getIdentifier方法, 根據(jù) entryName, typeName, package, 可獲取對應(yīng)資源在Resources對象中唯一的id;
int resId = mResources.getIdentifier(resName, "drawable", packageName);