Is there an alternative for getRunningTask API
Asked Answered
F

2

6

I was using getRunningTask API in one of my application to find the Foreground application. This API has been deprecated since Lollipop. After this deprecation, I preferred getRunningAppProcess API along with Importance_Foreground. I also ruled out REASON_SERVICE and REASON_PROVIDER from this list. I filtered out the system applications based on a logic, which worked perfectly. The problem is that, If Application A is on foreground, I get Application B as a spike. So, this approach is currently questionable. Is there any other alternative to the getRunningTask API?? Or am I missing any simple thing in the current approach. Please help guys.

Fructificative answered 3/11, 2014 at 12:24 Comment(3)
This would really depend on your purpose for the information. If it's a legitimate one there are probably alternatives, but they would depend on what exactly you are trying to accomplish.Cerecloth
Possible duplicate of Android: How can I get the current foreground activity (from a service)?Anabel
I'm voting to close this since there are way too many questions about this on StackOverflow, and the original question already covers the techniques in this question.Anabel
K
30

Based on the answer to this question

String getTopPackage(){
    long ts = System.currentTimeMillis();
    UsageStatsManager mUsageStatsManager = (UsageStatsManager)getSystemService("usagestats");
    List<UsageStats> usageStats = mUsageStatsManager.queryUsageStats(UsageStatsManager.INTERVAL_BEST, ts-1000, ts);
    if (usageStats == null || usageStats.size() == 0) {
        return NONE_PKG;
    }
    Collections.sort(usageStats, mRecentComp);
    return usageStats.get(0).getPackageName();
}

This is the mRecentComp:

static class RecentUseComparator implements Comparator<UsageStats> {

    @Override
    public int compare(UsageStats lhs, UsageStats rhs) {
        return (lhs.getLastTimeUsed() > rhs.getLastTimeUsed()) ? -1 : (lhs.getLastTimeUsed() == rhs.getLastTimeUsed()) ? 0 : 1;
    }
}

This permission is needed:

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

And you will need user authorization to request the stats, use this to direct the user to the settings page:

Intent intent = new Intent(Settings.ACTION_USAGE_ACCESS_SETTINGS);
startActivity(intent);

And you can check if you already have permission like this:

public static boolean needPermissionForBlocking(Context context) {
    try {
        PackageManager packageManager = context.getPackageManager();
        ApplicationInfo applicationInfo = packageManager.getApplicationInfo(context.getPackageName(), 0);
        AppOpsManager appOpsManager = (AppOpsManager) context.getSystemService(Context.APP_OPS_SERVICE);
        int mode = appOpsManager.checkOpNoThrow(AppOpsManager.OPSTR_GET_USAGE_STATS, applicationInfo.uid, applicationInfo.packageName);
        return  (mode != AppOpsManager.MODE_ALLOWED);
    } catch (PackageManager.NameNotFoundException e) {
        return true;
    }
}
Kindly answered 4/12, 2014 at 21:21 Comment(9)
Thanks. All of the things mentioned works like a charm. But one more thing, can I use any kind of Content Observer on this to know when the user turns it off or on? I'll accept the answer soon after I get response for this.Fructificative
I guess you could try this #6897246.Kindly
If that doesn't work you could use the needPermission function in my answer to check if it's on.Kindly
i tried the way u mentioned @gaston but the list always is empty. The permission in manifest, setting enabled from user , its all done but the list is still empty. Device used is Nexus 7 and android version is 5.0.1Darksome
on changing "ts-1000" to "ts-4000" the list started to fill upDarksome
It's documented that there may not be a system activity to handle the Settings.ACTION_USAGE_ACCESS_SETTINGS intent. Samsung and LG are among the manufacturers who have removed this activity from their Lollipop builds, so this solution will never work on their devices.Lunula
It's working on samsung for sure, I haven't tested it on an LG device.Kindly
thanks for 'tools:ignore="ProtectedPermissions"'. otherwise 'Permission is only granted to system apps' compile error occur.Avalos
You need an interval of at least a day to get the lists. Use following code to get the list List<UsageStats> usageStats = mUsageStatsManager.queryUsageStats(UsageStatsManager.INTERVAL_BEST, ts - 86400000, ts); 86400000 = (60*60*24*1000)Corporal
T
3

Get the list of RunningAppProcessInfo by ActivityManager.getRunningAppProcesses(). Choose the RuningAppProcessInfo with whose importance == RunningAppProcessInfo.IMPORTANCE_FOREGROUND and whose processState == ActivityManager.START_TASK_TO_FRONT. (The former is easy, the latter is difficult because the reflection is necessary)

See my answer for this question getRunningTasks doesn't work in Android L

Tomkins answered 2/2, 2015 at 12:22 Comment(2)
Doesn't work in Android M pre-release, unfortunately.Anabel
Yes, it is. We should find new approach.Tomkins

© 2022 - 2024 — McMap. All rights reserved.