Skip to content

Commit

Permalink
优化: 使资源钩子支持color类型
Browse files Browse the repository at this point in the history
  • Loading branch information
HChenX committed Mar 31, 2024
1 parent 0212beb commit 8c30b50
Show file tree
Hide file tree
Showing 7 changed files with 130 additions and 119 deletions.
9 changes: 1 addition & 8 deletions app/src/main/java/com/sevtinge/hyperceiler/XposedInit.java
Original file line number Diff line number Diff line change
Expand Up @@ -31,7 +31,6 @@
import com.sevtinge.hyperceiler.module.hook.systemframework.CleanShareMenu;
import com.sevtinge.hyperceiler.module.hook.systemframework.ScreenRotation;
import com.sevtinge.hyperceiler.module.hook.systemsettings.VolumeSeparateControlForSettings;
import com.sevtinge.hyperceiler.module.hook.systemui.navigation.HandleLineCustom;
import com.sevtinge.hyperceiler.module.hook.tsmclient.AutoNfc;

import de.robv.android.xposed.IXposedHookInitPackageResources;
Expand Down Expand Up @@ -67,7 +66,7 @@ public void initZygote(IXposedHookZygoteInit.StartupParam startupParam) throws T
@Override
public void handleLoadPackage(XC_LoadPackage.LoadPackageParam lpparam) throws Throwable {
if ("com.miui.contentcatcher".equals(lpparam.packageName) ||
"com.miui.catcherpatch".equals(lpparam.packageName)) {
"com.miui.catcherpatch".equals(lpparam.packageName)) {
return;
}
init(lpparam);
Expand Down Expand Up @@ -97,12 +96,6 @@ public void handleInitPackageResources(XC_InitPackageResources.InitPackageResour
SidebarLineCustom.INSTANCE.initResource(resparam);
}
break;

case "com.android.systemui":
if (mPrefsMap.getBoolean("system_ui_navigation_handle_custom")) {
HandleLineCustom.INSTANCE.initResource(resparam);
}
break;
}
}
}
Original file line number Diff line number Diff line change
@@ -1,13 +1,14 @@
package com.sevtinge.hyperceiler.module.app;

import com.sevtinge.hyperceiler.module.base.BaseModule;
import com.sevtinge.hyperceiler.module.hook.demo.CrashDemo;
import com.sevtinge.hyperceiler.module.hook.demo.ColorTest;
import com.sevtinge.hyperceiler.module.hook.demo.ToastTest;

public class Demo extends BaseModule {
@Override
public void handleLoadPackage() {
initHook(new ToastTest(), true);
initHook(new CrashDemo(), true);
// initHook(new CrashDemo(), true);
initHook(new ColorTest(), true);
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -264,7 +264,7 @@ public void handleLoadPackage() {
initHook(new StatusBarIconPositionAdjust(), isStatusBarIconAtRightEnable);

// 导航栏
initHook(HandleLineCustom.INSTANCE, mPrefsMap.getBoolean("system_ui_navigation_handle_custom"));
initHook(new HandleLineCustom(), mPrefsMap.getBoolean("system_ui_navigation_handle_custom"));
initHook(new NavigationCustom(), mPrefsMap.getBoolean("system_ui_navigation_custom"));
initHook(new HideNavigationBar(), mPrefsMap.getBoolean("system_ui_hide_navigation_bar"));
initHook(new RotationButton(), mPrefsMap.getStringAsInt("system_framework_other_rotation_button_int", 0) != 0);
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -29,12 +29,14 @@
import android.content.res.AssetManager;
import android.content.res.Configuration;
import android.content.res.Resources;
import android.content.res.TypedArray;
import android.content.res.loader.ResourcesLoader;
import android.content.res.loader.ResourcesProvider;
import android.os.Build;
import android.os.Handler;
import android.os.ParcelFileDescriptor;
import android.util.Pair;
import android.util.TypedValue;

import com.sevtinge.hyperceiler.XposedInit;
import com.sevtinge.hyperceiler.utils.ContextUtils;
Expand Down Expand Up @@ -208,33 +210,52 @@ private void applyHooks() {
switch (method.getName()) {
case "getInteger", "getLayout", "getBoolean",
"getDimension", "getDimensionPixelOffset",
"getDimensionPixelSize", "getText",
"getDimensionPixelSize", "getText", "getFloat",
"getIntArray", "getStringArray",
"getTextArray", "getAnimation" -> {
if (method.getParameterTypes().length == 1
&& method.getParameterTypes()[0].equals(int.class)) {
hookResMethod(method.getName(), int.class, hookBefore);
hookResMethod(method.getName(), int.class, hookResBefore);
}
}
case "getColor" -> {
if (method.getParameterTypes().length == 2) {
hookResMethod(method.getName(), int.class, Resources.Theme.class, hookResBefore);
}
}
case "getFraction" -> {
if (method.getParameterTypes().length == 3) {
hookResMethod(method.getName(), int.class, int.class, int.class, hookBefore);
hookResMethod(method.getName(), int.class, int.class, int.class, hookResBefore);
}
}
case "getDrawableForDensity" -> {
if (method.getParameterTypes().length == 3) {
hookResMethod(method.getName(), int.class, int.class, Resources.Theme.class, hookBefore);
hookResMethod(method.getName(), int.class, int.class, Resources.Theme.class, hookResBefore);
}
}
}
}

Method[] typedMethod = TypedArray.class.getDeclaredMethods();
for (Method method : typedMethod) {
switch (method.getName()) {
case "getColor" -> {
hookTypedMethod(method.getName(), int.class, int.class, hookTypedBefore);
}
}
}
}

private void hookResMethod(String name, Object... args) {
XC_MethodHook.Unhook unhook = HookTool.findAndHookMethod(Resources.class, name, args);
unhooks.add(unhook);
}

private void hookTypedMethod(String name, Object... args) {
XC_MethodHook.Unhook unhook = HookTool.findAndHookMethod(TypedArray.class, name, args);
unhooks.add(unhook);
}

public void unHookRes() {
if (unhooks.isEmpty()) {
isInit = false;
Expand All @@ -247,7 +268,27 @@ public void unHookRes() {
isInit = false;
}

private final HookTool.MethodHook hookBefore = new HookTool.MethodHook() {
private final HookTool.MethodHook hookTypedBefore = new HookTool.MethodHook() {
@Override
protected void before(MethodHookParam param) {
Resources mResources = (Resources) XposedHelpers.getObjectField(param.thisObject, "mResources");
int index = (int) param.args[0];
int[] mData = (int[]) XposedHelpers.getObjectField(param.thisObject, "mData");
int type = mData[index + 0];
if (type == TypedValue.TYPE_NULL) {
return;
}
int id = mData[index + 3];
if (id != 0) {
Object value = getTypedArrayReplacement(mResources, id);
if (value != null) {
param.setResult(value);
}
}
}
};

private final HookTool.MethodHook hookResBefore = new HookTool.MethodHook() {
@Override
protected void before(MethodHookParam param) {
Context context;
Expand Down Expand Up @@ -397,4 +438,41 @@ else if ("getDrawableForDensity".equals(method) || "getFraction".equals(method))
}
return null;
}

private Object getTypedArrayReplacement(Resources resources, int id) {
if (id != 0) {
String pkgName = null;
String resType = null;
String resName = null;
try {
pkgName = resources.getResourcePackageName(id);
resType = resources.getResourceTypeName(id);
resName = resources.getResourceEntryName(id);
} catch (Throwable ignore) {
}
if (pkgName == null || resType == null || resName == null) return null;

try {
String resFullName = pkgName + ":" + resType + "/" + resName;
String resAnyPkgName = "*:" + resType + "/" + resName;

Pair<ReplacementType, Object> replacement = null;
if (replacements.containsKey(resFullName)) {
replacement = replacements.get(resFullName);
} else if (replacements.containsKey(resAnyPkgName)) {
replacement = replacements.get(resAnyPkgName);
}
if (replacement != null) {
switch (replacement.first) {
case OBJECT -> {
return replacement.second;
}
}
}
} catch (Throwable e) {
XposedLogUtils.logE("getTypedArrayReplacement", e);
}
}
return null;
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,19 @@
package com.sevtinge.hyperceiler.module.hook.demo;

import android.graphics.Color;

import com.sevtinge.hyperceiler.module.base.BaseHook;

public class ColorTest extends BaseHook {
@Override
public void init() throws NoSuchMethodException {
findAndHookMethod("com.hchen.demo.MainActivity", "setColor",
new MethodHook() {
@Override
protected void before(MethodHookParam param) {
mResHook.setObjectReplacement("com.hchen.demo", "color", "my_test_color", Color.RED);
}
}
);
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,23 @@
package com.sevtinge.hyperceiler.module.hook.systemui.navigation;

import com.sevtinge.hyperceiler.module.base.BaseHook;

public class HandleLineCustom extends BaseHook {
@Override
public void init() throws NoSuchMethodException {
float mNavigationHandleRadius = (float) mPrefsMap.getInt("system_ui_navigation_handle_custom_thickness", 185) / 100;
try {
mResHook.setDensityReplacement("com.android.systemui", "dimen", "navigation_handle_radius", mNavigationHandleRadius);
} catch (Exception e) {
logE(TAG, e.toString());
}
int mNavigationHandleLightColor =
mPrefsMap.getInt("system_ui_navigation_handle_custom_color", -872415232);
int mNavigationHandleDarkColor =
mPrefsMap.getInt("system_ui_navigation_handle_custom_color_dark", -1);
mResHook.setObjectReplacement("com.android.systemui", "color",
"navigation_bar_home_handle_dark_color", mNavigationHandleDarkColor);
mResHook.setObjectReplacement("com.android.systemui", "color",
"navigation_bar_home_handle_light_color", mNavigationHandleLightColor);
}
}

This file was deleted.

0 comments on commit 8c30b50

Please sign in to comment.