Skip to content

Commit

Permalink
Support Android 9.0, API 28
Browse files Browse the repository at this point in the history
  • Loading branch information
galenlin committed Jul 6, 2018
1 parent d83e9d1 commit 664994f
Show file tree
Hide file tree
Showing 2 changed files with 78 additions and 10 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -163,6 +163,11 @@ public boolean handleMessage(Message msg) {
}

private void redirectActivityForP(Message msg) {
if (Build.VERSION.SDK_INT >= 28) {
// Following APIs cannot be called again since android 9.0.
return;
}

Object/*android.app.servertransaction.ClientTransaction*/ t = msg.obj;
List callbacks = ReflectAccelerator.getLaunchActivityItems(t);
if (callbacks == null) return;
Expand All @@ -189,7 +194,7 @@ public void replace(ActivityInfo targetInfo) {
});
}

private void tryReplaceActivityInfo(Intent intent, ActivityInfoReplacer replacer) {
static void tryReplaceActivityInfo(Intent intent, ActivityInfoReplacer replacer) {
if (intent == null) return;

String targetClass = unwrapIntent(intent);
Expand Down Expand Up @@ -338,6 +343,20 @@ public ActivityResult execStartActivity(
who, contextThread, token, target, intent, requestCode);
}

@Override
public Activity newActivity(ClassLoader cl, final String className, Intent intent) throws InstantiationException, IllegalAccessException, ClassNotFoundException {
final String[] targetClassName = {className};
if (Build.VERSION.SDK_INT >= 28) {
ActivityThreadHandlerCallback.tryReplaceActivityInfo(intent, new ActivityThreadHandlerCallback.ActivityInfoReplacer() {
@Override
public void replace(ActivityInfo info) {
targetClassName[0] = info.targetActivity; // Redirect to the plugin activity
}
});
}
return mBase.newActivity(cl, targetClassName[0], intent);
}

@Override
/** Prepare resources for REAL */
public void callActivityOnCreate(Activity activity, android.os.Bundle icicle) {
Expand Down Expand Up @@ -1046,6 +1065,11 @@ public <T> T createObject(Bundle bundle, Context context, String type) {
* @param ai
*/
private static void applyActivityInfo(Activity activity, ActivityInfo ai) {
// Apply theme (9.0 only)
if (Build.VERSION.SDK_INT >= 28) {
ReflectAccelerator.resetResourcesAndTheme(activity, ai.getThemeResource());
}

// Apply window attributes
Window window = activity.getWindow();
window.setSoftInputMode(ai.softInputMode);
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -30,6 +30,7 @@
import android.os.Bundle;
import android.os.IBinder;
import android.util.ArrayMap;
import android.view.ContextThemeWrapper;

import java.io.File;
import java.io.IOException;
Expand Down Expand Up @@ -187,7 +188,7 @@ private static Object makeDexElement(File pkg, boolean isDirectory, DexFile dexF
}
if (sDexElementConstructor == null) {
if (Build.VERSION.SDK_INT >= 26) {
sDexElementConstructor = sDexElementClass.getConstructors()[1]; // (DexFile, File)
sDexElementConstructor = sDexElementClass.getConstructor(new Class[]{DexFile.class, File.class});
} else {
sDexElementConstructor = sDexElementClass.getConstructors()[0];
}
Expand Down Expand Up @@ -465,12 +466,23 @@ public static int addAssetPath(AssetManager assets, String path) {
}

public static int[] addAssetPaths(AssetManager assets, String[] paths) {
if (sAssetManager_addAssetPaths_method == null) {
sAssetManager_addAssetPaths_method = getMethod(AssetManager.class,
"addAssetPaths", new Class[]{String[].class});
if (Build.VERSION.SDK_INT < 28) {
if (sAssetManager_addAssetPaths_method == null) {
sAssetManager_addAssetPaths_method = getMethod(AssetManager.class,
"addAssetPaths", new Class[]{String[].class});
}
if (sAssetManager_addAssetPaths_method == null) return null;
return invoke(sAssetManager_addAssetPaths_method, assets, new Object[]{paths});
} else {
// `AssetManager#addAssetPaths` becomes unavailable since android 9.0,
// use recursively `addAssetPath` instead.
int N = paths.length;
int[] ids = new int[N];
for (int i = 0; i < N; i++) {
ids[i] = addAssetPath(assets, paths[i]);
}
return ids;
}
if (sAssetManager_addAssetPaths_method == null) return null;
return invoke(sAssetManager_addAssetPaths_method, assets, new Object[]{paths});
}

public static void mergeResources(Application app, Object activityThread, String[] assetPaths) {
Expand All @@ -484,9 +496,13 @@ public static void mergeResources(Application app, Object activityThread, String
addAssetPaths(newAssetManager, assetPaths);

try {
Method mEnsureStringBlocks = AssetManager.class.getDeclaredMethod("ensureStringBlocks", new Class[0]);
mEnsureStringBlocks.setAccessible(true);
mEnsureStringBlocks.invoke(newAssetManager, new Object[0]);
if (Build.VERSION.SDK_INT < 28) {
Method mEnsureStringBlocks = AssetManager.class.getDeclaredMethod("ensureStringBlocks", new Class[0]);
mEnsureStringBlocks.setAccessible(true);
mEnsureStringBlocks.invoke(newAssetManager, new Object[0]);
} else {
// `AssetManager#ensureStringBlocks` becomes unavailable since android 9.0
}

Collection<WeakReference<Resources>> references;

Expand Down Expand Up @@ -737,6 +753,34 @@ public static Intent getIntentOfLaunchActivityItem(Object item) {
return getValue(f, item);
}

public static void resetResourcesAndTheme(Activity activity, int themeId) {
AssetManager newAssetManager = activity.getApplication().getAssets();
Resources resources = activity.getResources();

// Set the activity resources assets to the application one
try {
Field mResourcesImpl = Resources.class.getDeclaredField("mResourcesImpl");
mResourcesImpl.setAccessible(true);
Object resourceImpl = mResourcesImpl.get(resources);
Field implAssets = resourceImpl.getClass().getDeclaredField("mAssets");
implAssets.setAccessible(true);
implAssets.set(resourceImpl, newAssetManager);
} catch (Throwable e) {
android.util.Log.e("Small", "Failed to update resources for activity " + activity, e);
}

// Reset the theme
try {
Field mt = ContextThemeWrapper.class.getDeclaredField("mTheme");
mt.setAccessible(true);
mt.set(activity, null);
} catch (Throwable e) {
android.util.Log.e("Small", "Failed to update existing theme for activity " + activity, e);
}

activity.setTheme(themeId);
}

//______________________________________________________________________________________________
// Private

Expand Down

0 comments on commit 664994f

Please sign in to comment.