You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Android中如何检测目标应用是否在后台运行?原有方法失效求助

解决Android检测其他应用后台运行状态的问题

你的问题核心是Android系统权限限制导致旧方法失效:从Android 10(API 29)开始,系统收紧了隐私权限,ActivityManager.getRunningAppProcesses()只能返回当前应用的进程信息,无法再获取其他应用的进程状态,所以原来的代码只能检测自身进程。

针对你的使用场景(避免重复登录,根据目标应用状态选择启动方式),提供两种可行方案:

方案一:使用UsageStatsManager获取应用运行状态(需特殊权限)

这个方法可以准确获取其他应用的使用状态,但需要用户授权PACKAGE_USAGE_STATS权限。

步骤1:添加权限声明

在AndroidManifest.xml中添加:

<uses-permission android:name="android.permission.PACKAGE_USAGE_STATS"
    tools:ignore="ProtectedPermissions" />

步骤2:权限检查与申请

// 检查是否已获取使用统计权限
fun hasUsageStatsPermission(context: Context): Boolean {
    val appOps = context.getSystemService(Context.APP_OPS_SERVICE) as AppOpsManager
    val mode = appOps.checkOpNoThrow(
        AppOpsManager.OPSTR_GET_USAGE_STATS,
        android.os.Process.myUid(),
        context.packageName
    )
    return mode == AppOpsManager.MODE_ALLOWED
}

// 引导用户开启权限
fun requestUsageStatsPermission(context: Context) {
    val intent = Intent(Settings.ACTION_USAGE_ACCESS_SETTINGS)
    intent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK)
    context.startActivity(intent)
}

步骤3:检测应用是否在后台运行

fun isTargetAppRunning(context: Context, targetPackage: String): Boolean {
    val usageStatsManager = context.getSystemService(Context.USAGE_STATS_SERVICE) as UsageStatsManager
    val currentTime = System.currentTimeMillis()
    // 查询最近5分钟的应用使用统计(可根据需求调整时间范围)
    val stats = usageStatsManager.queryUsageStats(
        UsageStatsManager.INTERVAL_BEST,
        currentTime - 5 * 60 * 1000,
        currentTime
    )

    stats?.forEach { usageStat ->
        if (usageStat.packageName == targetPackage && usageStat.lastTimeUsed > currentTime - 1000) {
            // 目标应用在最近1秒内有活跃记录,判定为后台运行
            return true
        }
    }
    return false
}

方案二:绕过状态检测,在目标应用内处理登录逻辑(更推荐)

如果你的目标应用是可控的(自己开发的),可以直接在目标应用的启动页处理登录判断,无需在源应用中检测状态,这种方式不需要额外权限,更稳定。

在目标应用的启动Activity中添加逻辑:

override fun onCreate(savedInstanceState: Bundle?) {
    super.onCreate(savedInstanceState)
    
    // 先判断用户是否已登录
    if (isUserLoggedIn()) {
        // 已登录直接跳转到主页面,跳过登录流程
        startActivity(Intent(this, MainActivity::class.java))
        finish()
        return
    }

    // 未登录时,处理源应用传递的登录参数
    val needLogin = intent.getBooleanExtra("need_login", false)
    if (needLogin) {
        // 执行登录流程
        startLoginFlow()
    }
}

// 模拟判断用户登录状态的方法
private fun isUserLoggedIn(): Boolean {
    return SharedPreferences.getDefaultSharedPreferences(this)
        .getBoolean("is_logged_in", false)
}

此时,源应用只需统一携带登录Intent启动目标应用即可:

fun launchTargetApp(context: Context, targetPackage: String) {
    val launchIntent = context.packageManager.getLaunchIntentForPackage(targetPackage) ?: return
    launchIntent.putExtra("need_login", true)
    launchIntent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK)
    context.startActivity(launchIntent)
}

目标应用会自动判断是否需要执行登录,完全避免重复登录的问题。

内容的提问来源于stack exchange,提问作者Wesley DaBes

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.01 12:56:03