web-dev-qa-db-ja.com

Android Lollipop 5.0のみでフォアグラウンドアクティビティ名を取得できません

次のコードを使用して、変数foregroundTaskPackageNameでフォアグラウンドアプリのアクティビティ名を取得します。 4.1から4.4までのすべてのOSバージョンで動作しますが、Android 5.0 Lollipopでは動作しません。

5.0 Lollipopの変更点についてだれでも支援できますか? Lollipopでは、foregroundTaskPackageNameで取得するテキストは「Launcher3」です。 Genymotion Emulatorを使用しています。

ActivityManager am = (ActivityManager) getSystemService(ACTIVITY_SERVICE);
RunningTaskInfo foregroundTaskInfo = am.getRunningTasks(1).get(0); // get
                                                                        // list
                                                                        // of
                                                                        // running
                                                                        // tasks
String foregroundTaskAppName = null;
String foregroundTaskPackageName = foregroundTaskInfo.topActivity
                .getPackageName();
21
user1406716

起動されたアクティビティの履歴を取得するには、新しいUsageStatsManagerを使用し、そのqueryUsageStatsメソッドを呼び出す必要があります。ユーザーは、[セキュリティ]-> [使用権限のあるアプリ]でデバイス設定の使用統計にアクセスする必要があります。

リンク:

UsageStatsManager documentation

queryUsageStatsメソッドのドキュメント

9
Muzikant

これは私のためにLollipopで動作します(21):

    ActivityManager manager = (ActivityManager)mContext.getSystemService(Context.ACTIVITY_SERVICE);

    List<ActivityManager.RunningAppProcessInfo> tasks = manager.getRunningAppProcesses();

    Log.i("current_app",tasks.get(0).processName);
29
Mert

以下のコードを使用して、現在のフォアグラウンドアクティビティパッケージ名を取得できます。

 if (Android.os.Build.VERSION.SDK_INT >= Android.os.Build.VERSION_CODES.Lollipop) {
        // intentionally using string value as Context.USAGE_STATS_SERVICE was
        // strangely only added in API 22 (Lollipop_MR1)
        @SuppressWarnings("WrongConstant")
        UsageStatsManager usm = (UsageStatsManager) getSystemService("usagestats");
        long time = System.currentTimeMillis();
        List<UsageStats> appList = usm.queryUsageStats(UsageStatsManager.INTERVAL_DAILY,
                        time - 1000 * 1000, time);
                if (appList != null && appList.size() > 0) {
                    SortedMap<Long, UsageStats> mySortedMap = new TreeMap<Long, UsageStats>();
                    for (UsageStats usageStats : appList) {
                        mySortedMap.put(usageStats.getLastTimeUsed(),
                                usageStats);
                    }
                    if (mySortedMap != null && !mySortedMap.isEmpty()) {
                        currentApp = mySortedMap.get(
                                mySortedMap.lastKey()).getPackageName();
                    }
                }
    } else {
        ActivityManager am = (ActivityManager) getSystemService(Context.ACTIVITY_SERVICE);
        List<ActivityManager.RunningAppProcessInfo> tasks = am
                        .getRunningAppProcesses();
                currentApp = tasks.get(0).processName;
    }

これらのアクセス許可をマニフェストファイルに追加します(最初のアクセス許可は<API 21、2番目のアクセス許可は> = API 21)。

<uses-permission Android:name="Android.permission.GET_TASKS" />
<uses-permission Android:name="Android.permission.PACKAGE_USAGE_STATS" tools:ignore="ProtectedPermissions" />
7
Vishal Butani

getRunningTasks() docs:

このメソッドはAPIレベル21で非推奨になりました。Lollipopの時点で、このメソッドはサードパーティのアプリケーションでは使用できなくなりました:ドキュメント中心の最近の手段の導入発信者に個人情報が漏洩する可能性があります。後方互換性のために、それはまだそのデータの小さなサブセットを返します:少なくとも呼び出し側の自身のタスク、そしておそらくは重要ではないことが知られている家のような他のいくつかのタスク。

4
Marcin Orlowski

利用可能ですが、最良ではない方法は、アクセシビリティを使用することです。

AndroidManifest xmlファイルでアクセシビリティサービスを宣言する

<service
            Android:name=".MyAccessibilityService"
            Android:label="@string/accessibility_service_label"
            Android:permission="Android.permission.BIND_ACCESSIBILITY_SERVICE" >
            <intent-filter>
                <action Android:name="Android.accessibilityservice.AccessibilityService" />
            </intent-filter>

            <meta-data
                Android:name="Android.accessibilityservice"
                Android:resource="@xml/accessibility_service_config" />
        </service>

accessibility_service_config.xmlファイル

<accessibility-service xmlns:Android="http://schemas.Android.com/apk/res/Android"
    Android:description="@string/accessibility_service_desc"
    Android:accessibilityEventTypes="typeAllMask"
    Android:accessibilityFlags="flagDefault|flagIncludeNotImportantViews"
    Android:accessibilityFeedbackType="feedbackSpoken"
    Android:notificationTimeout="100"
    Android:canRetrieveWindowContent="true"
/>

ウィンドウの状態が変化したときにアクティビティ名を保存する

public class MyAccessibilityService extends AccessibilityService{
    public static String sActivityName;
    @Override
    public void onAccessibilityEvent(AccessibilityEvent event) {
        // TODO Auto-generated method stub
        if(event.getEventType() == AccessibilityEvent.TYPE_WINDOW_STATE_CHANGED){
            Log.d("activitytest", "onAccessibilityEvent with window state changed");
            sActivityName = event.getClassName().toString();
        }
    }

    @Override
    public void onInterrupt() {
        // TODO Auto-generated method stub

    }

}

欠点は、ユーザーが設定でアクセシビリティサービスを有効にできるようにする必要があることです。

2
gonglong

/system/bin/toolboxコマンドを使用してプロセスを識別し、次に可視アプリケーションを識別するクラスを作成しました。追加の必要性は、UIおよびAndroidランチャーのないシステムアプリを識別します。

ProcessManager.Java

2
Rukmal Dias

これを試して

public static boolean isForeground(Context context) {
    ActivityManager manager = (ActivityManager)context.getSystemService(Context.ACTIVITY_SERVICE);
    List<ActivityManager.RunningAppProcessInfo> tasks = manager.getRunningAppProcesses();
    if(tasks.isEmpty())
        return false;

    for (ActivityManager.RunningAppProcessInfo task : tasks) {
        if(context.getPackageName().equalsIgnoreCase(task.processName)){
            return task.importance == ActivityManager.RunningAppProcessInfo.IMPORTANCE_FOREGROUND;
        }
    }
    return false;
}
0
Beom Soo Joung