2014-10-09 77 views
1

我需要知道何時Android設備閒置了一段時間,當我的應用程序當前處於後臺時(並且如果它閒置,請將我的應用程序前面)。只有兩個辦法我能想到的要做到這一點是:Android服務:當設備空閒X分鐘時檢測

  1. 不知怎的,檢測用戶交互的應用程序之外,如果還沒有幾分鐘的X個任意輸入,帶給我的應用程序前。

    或:

  2. 當設備進入睡眠模式,帶給我的應用程序的前面。

我不知道如何這些,但2似乎是對我來說最可行的選擇。這是什麼代碼?

+0

在我看到過類似的討論之前,這裏:http://stackoverflow.com/questions/4075180/application-idle-time – Scalarr 2014-10-09 21:26:17

+0

@Scalar這是檢測空閒時間_inside_應用程序。 – uyuyuy99 2014-10-09 21:48:02

+0

當設備進入睡眠模式時,*無*(至少以普通軟件的方式)正在運行。 – 2014-10-09 21:54:40

回答

0

我是能夠通過使用被放置在所有視圖頂部「透明的」視圖,它檢查用戶完成1.觸摸

步驟用於實現所需要的效果:

1)創建一個服務這在其onCreate方法創建透明視圖,其附加到觀點堆棧
2)onStartCommand調用initTimer()方法
3)上的服務
4實施View.OnTouchListener)覆蓋onTouch方法
5) onTouch甚至t)收到 - 呼叫initTimer()
6)onDestroy的服務 - 從視圖堆棧中刪除透明視圖
7)當你的主要活動的onPause被調用時啓動服務
8)當應用程序停止服務打開

下面是代碼:

private Handler mHandler; 
private Runnable mRunnable; 
private final int mTimerDelay = 60000;//inactivity delay in milliseconds 
private LinearLayout mTouchLayout;//the transparent view 

@Override 
public IBinder onBind(Intent intent) { 
    return null; 
} 

@Override 
public void onCreate() { 
    super.onCreate(); 

    mTouchLayout = new LinearLayout(this); 

    LinearLayout.LayoutParams lp = new LinearLayout.LayoutParams(LinearLayout.LayoutParams.MATCH_PARENT, 
      LinearLayout.LayoutParams.MATCH_PARENT); 
    mTouchLayout.setLayoutParams(lp); 

    // set on touch listener 
    mTouchLayout.setOnTouchListener(this); 

    // fetch window manager object 
    WindowManager windowManager = (WindowManager) getSystemService(WINDOW_SERVICE); 
    // set layout parameter of window manager 

    WindowManager.LayoutParams mParams = new WindowManager.LayoutParams(
      WindowManager.LayoutParams.WRAP_CONTENT, 
      WindowManager.LayoutParams.WRAP_CONTENT, 
      WindowManager.LayoutParams.TYPE_SYSTEM_ERROR, 
      WindowManager.LayoutParams.FLAG_NOT_TOUCHABLE | 
        WindowManager.LayoutParams.FLAG_WATCH_OUTSIDE_TOUCH | 
        WindowManager.LayoutParams.FLAG_NOT_FOCUSABLE, PixelFormat.TRANSLUCENT 
    ); 

    mParams.gravity = Gravity.LEFT | Gravity.TOP; 
    windowManager.addView(mTouchLayout, mParams); 
} 

@Override 
public int onStartCommand(Intent intent, int flags, int startId) { 
    initTimer(); 

    return START_NOT_STICKY; 
} 

@Override 
public boolean onTouch(View view, MotionEvent motionEvent) { 
    Log.d("IdleDetectorService", "Touch detected. Resetting timer"); 
    initTimer(); 
    return false; 
} 

@Override 
public void onDestroy() { 
    super.onDestroy(); 
    mHandler.removeCallbacks(mRunnable); 
    WindowManager windowManager = (WindowManager) getSystemService(WINDOW_SERVICE); 
    if (windowManager != null && mTouchLayout != null) { 
     windowManager.removeView(mTouchLayout); 
    } 
} 

/** 
* (Re)sets the timer to send the inactivity broadcast 
*/ 
private void initTimer() { 
    // Start timer and timer task 
    if (mRunnable == null) { 

     mRunnable = new Runnable() { 
      @Override 
      public void run() { 
       Log.d("IdleDetectorService", "Inactivity detected. Sending broadcast to start the app"); 

       try { 
        boolean isInForeground = new ForegroundCheckTask().execute(getApplicationContext()).get(); 

        if (!isInForeground) { 
         Intent launchIntent = getApplication() 
           .getPackageManager() 
           .getLaunchIntentForPackage("<your-package-name>"); 
         if (launchIntent != null) { 
          LogUtil.d("IdleDetectorService", "App started"); 
          getApplication().startActivity(launchIntent); 
         } 
        } 

        stopSelf(); 
       } catch (Exception e) { 
       } 
      } 
     }; 
    } 

    if (mHandler == null) { 
     mHandler = new Handler(); 
    } 

    mHandler.removeCallbacks(mRunnable); 
    mHandler.postDelayed(mRunnable, mTimerDelay); 
} 

private class ForegroundCheckTask extends AsyncTask<Context, Void, Boolean> { 

    @Override 
    protected Boolean doInBackground(Context... params) { 
     final Context context = params[0]; 
     return isAppOnForeground(context); 
    } 

    private boolean isAppOnForeground(Context context) { 
     ActivityManager activityManager = (ActivityManager) context.getSystemService(Context.ACTIVITY_SERVICE); 
     List<ActivityManager.RunningAppProcessInfo> appProcesses = null; 

     if (Build.VERSION.SDK_INT <= Build.VERSION_CODES.KITKAT) { 
      appProcesses = activityManager.getRunningAppProcesses(); 
     } else { 
      //for devices with Android 5+ use alternative methods 
      appProcesses = AndroidProcesses.getRunningAppProcessInfo(getApplication()); 
     } 

     if (appProcesses == null) { 
      return false; 
     } 

     final String packageName = context.getPackageName(); 

     for (ActivityManager.RunningAppProcessInfo appProcess : appProcesses) { 
      if (appProcess.importance == ActivityManager.RunningAppProcessInfo.IMPORTANCE_FOREGROUND && 
        appProcess.processName.equals(packageName)) { 
       return true; 
      } 
     } 

     return false; 
    } 
} 

請注意,你應該在你的AndroidManifest.xml文件中添加額外的權限: 機器人:名字= 「android.permission.SYSTEM_ALERT_WINDOW」