1.需求概述
现在需求是,比如某apk设置相应的业务需求,需要在apk启动前,根据业务需求作相应的跳转(我们以Settings apk来举例,比如在Settings apk里面,加了一把锁,用户可以锁住Settings apk ,如果用户打开锁,哪么就进不了Settings apk这一功能来详细解答)。
2.实现功能核心类
代码路径:
packages\apps\Launcher3\src\com\android\launcher3\Launcher.java
packages\apps\Launcher3\src\com\android\launcher3\touch\ItemClickHandler
3.核心代码分析
3.1 Launcher.java 代码分析
找到bindAppsAdded()方法,然后再看里面的bindItems()方法。
在bindItems()方法里面,我们看到了item.itemType的类型为ITEM_TYPE_APPLICATION时,就是我们需要的了,再继续找下去,执行createShortcut()方法。
在createShortcut()方法里面,我们看到了点击apk时,设置的点击事件onclickListener了。
在这里他是传进ItemClickHandler.INSTANCE这个类,所以我们继续跟踪此类:
在ItemClickHandler.java中我们终于找到了最终调用的onClick()方法了,我们就可以在这里修改
为我们的业务需要了。
以下为修改的代码,达到实现功能,标红的代码为修改的地方
private static void onClick(View v) {
// Make sure that rogue clicks don't get through while allapps is launching, or after the
// view has detached (it's possible for this to happen if the view is removed mid touch).
if (v.getWindowToken() == null) return;
Launcher launcher = Launcher.getLauncher(v.getContext());
if (!launcher.getWorkspace().isFinishedSwitchingState()) return;
Object tag = v.getTag();
// launcher3 桌面快捷键apk点击事件
if (tag instanceof WorkspaceItemInfo) {
String pkg = ((WorkspaceItemInfo) tag).getTargetComponent().getPackageName();
if (!SettingsLockUtils.getInstall().isLockApkPackageName("com.android.settings", pkg, v.getContext())) {
onClickAppShortcut(v, (WorkspaceItemInfo) tag, launcher);
}
// launcher3 桌面快捷键文件夹点击事件
} else if (tag instanceof FolderInfo) {
if (v instanceof FolderIcon) {
onClickFolderIcon(v);
}
// launcher3 滑出来allApk列表中的apk点击事件
} else if (tag instanceof AppInfo) {
String pkg = ((AppInfo) tag).getTargetComponent().getPackageName();
if (!SettingsLockUtils.getInstall().isLockApkPackageName("com.android.settings", pkg, v.getContext())) {
startAppShortcutOrInfoActivity(v, (AppInfo) tag, launcher);
}
} else if (tag instanceof LauncherAppWidgetInfo) {
if (v instanceof PendingAppWidgetHostView) {
onClickPendingWidget((PendingAppWidgetHostView) v, launcher);
}
} else if (tag instanceof SearchActionItemInfo) {
onClickSearchAction(launcher, (SearchActionItemInfo) tag);
}
}
以下是SettingsLockUtils.java类
package com.android.launcher3.util;
import java.util.LinkedList;
import java.util.List;
import android.content.Context;
import android.widget.Toast;
import android.provider.Settings;
import android.util.Log;
/**
* by Hogan 2023.3.17
* 功能:隐藏指定的apk列表
*/
public class SettingsLockUtils {
public static final String KEY_SETTINGS_LOCK = "key_settings_lock";
private SettingsLockUtils() {
}
private static class SettingsLockUtilsHolder {
private static final SettingsLockUtils INSTALL = new SettingsLockUtils();
}
public static SettingsLockUtils getInstall() {
return SettingsLockUtilsHolder.INSTALL;
}
public boolean isLockApkPackageName(String curPkg, String lockPkg, Context context) {
boolean isLock = false;
// 1用户不能用,0用户可以使用
int lockValue = Settings.Global.getInt(context.getContentResolver(), KEY_SETTINGS_LOCK, 0);
Log.e("Hogan", "curPkg==" + curPkg + " lockPkg==" + lockPkg + " lockValue==" + lockValue);
if (lockPkg.equals(curPkg) && (1 == lockValue)) {
isLock = true;
Toast.makeText(context, "Settings 已被禁用,请先解锁,再使用。", Toast.LENGTH_SHORT).show();
}
return isLock;
}
}