1

タイマーをオンに設定してAccountActivity.class、ユーザーがログアウトするためのカウントダウンを開始したり、ユーザーが画面をロックしたりした場合に、ユーザーがホームボタンを押さないようにします。

しかし今、私はそのonPause方法のために問題に直面しています。ユーザーがメソッドを呼び出すボタンをクリックすると、ユーザーが にgetaccounttask()リダイレクトされAccountInformationActivity.classonPauseメソッドもアクティブになり、タイマーがカウントダウンを開始します。

onPauseメソッドがカウントダウンしたり、タイマーがキャンセルされたりするのを防ぐ解決策はありますAccountInformationActivity.classか?

インテントが開始する前にタイマーをキャンセルしようとしましたが、まだ機能しません。

ハンドラーも使用してみましたが、同じ問題が発生しました.Androidがどのように完全に機能するかをまだ把握しようとしているので、あなたの助けや解決策に深く感謝します.

public class AccountActivity extends AppCompatActivity {

    private Timer timer;

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_account);
    }

    private class getaccounttask extends AsyncTask<String, Void, String>
    {
      @Override
      protected String doInBackground(String... urlaccount)
      {
        StringBuilder result = new StringBuilder();
        try
        {
            //My Codes
        }
        catch (Exception e)
        {
            e.printStackTrace();
        }
        return result.toString();
      }

      @Override
      protected void onPostExecute(String result)
      {
        Intent intent = new Intent();
        intent.setClass(getApplicationContext(), AccountInformationActivity.class);
        startActivity(intent);
      }
     }

    @Override
    protected void onPause() {
        super.onPause();

        timer = new Timer();
        Log.i("Main", "Invoking logout timer");
        LogOutTimerTask logoutTimeTask = new LogOutTimerTask();
        timer.schedule(logoutTimeTask, 300000); //auto logout in 5 minutes
    }

    @Override
    protected void onResume() {
        super.onResume();
        if (timer != null) {
            timer.cancel();
            Log.i("Main", "cancel timer");
            timer = null;
        }
    }

    private class LogOutTimerTask extends TimerTask {

        @Override
        public void run() {

            //redirect user to login screen
            Intent i = new Intent(AccountActivity.this, MainActivity.class);
            i.addFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP);
            startActivity(i);
            finish();
        }
    }
}
4

3 に答える 3

0

でいくつかの変更をonPause()行い、この権限を追加します

<uses-permission android:name="android.permission.GET_TASKS" />

    @Override
    protected void onPause() {
        if (isApplicationSentToBackground(this)) {
            // Do what you want to do on detecting Home Key being Pressed
            timer = new Timer();
            Log.i("Main", "Invoking logout timer");
            LogOutTimerTask logoutTimeTask = new LogOutTimerTask();
            timer.schedule(logoutTimeTask, 300000); //auto logout in 5 minutes
            Log.i("Main", "Invoking Home Key pressed");
        }
        super.onPause();

    }

    public boolean isApplicationSentToBackground(final Context context) {
        ActivityManager am = (ActivityManager) context.getSystemService(Context.ACTIVITY_SERVICE);
        List<ActivityManager.RunningTaskInfo> tasks = am.getRunningTasks(1);
        if (!tasks.isEmpty()) {
            ComponentName topActivity = tasks.get(0).topActivity;
            if (!topActivity.getPackageName().equals(context.getPackageName())) {
                return true;
            }
        }
        return false;
    }
于 2016-08-24T04:47:33.533 に答える
0

選択した実装アーキテクチャは改善される可能性があります。それについては後で説明します。まず、このクイック フィックスを適用してアーキテクチャを修正します。

明らかに、ホーム画面Timerを使用していないときに開始する必要があります。ただし、ユーザーはを使用して に切り替えることで、Activity外出することもできます。これで追跡できます。したがって、ブール値のフラグを のように保ちます。最初は である必要があります。の場合は に設定する必要がありますが、行く場合はに設定する必要があります。で、 経由で外出する場合は になります。である場合はタイマーをキャンセルし、それ以外の場合は を開始します。ActivityIntentAccountActivityshouldNavigatefalseonResumefalsegetcounttaskonPostExecutetrueonPausegetcounttaskshouldNavigatetruetrueTimer

コード:

public class AccountActivity extends AppCompatActivity {

    private Timer timer;
    private volatile boolean shouldNavigate = false;

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_account);
    }

    private class getaccounttask extends AsyncTask<String, Void, String>
    {
      @Override
      protected String doInBackground(String... urlaccount)
      {
        StringBuilder result = new StringBuilder();
        try
        {
            //My Codes
        }
        catch (Exception e)
        {
            e.printStackTrace();
        }
        return result.toString();
      }

      @Override
      protected void onPostExecute(String result)
      {
        shouldNavigate = true;
        Intent intent = new Intent();
        intent.setClass(getApplicationContext(), AccountInformationActivity.class);
        startActivity(intent);
      }
     }

    @Override
    protected void onPause() {
        super.onPause();
        if (!shouldNavigate){
            timer = new Timer();
            Log.i("Main", "Invoking logout timer");
            LogOutTimerTask logoutTimeTask = new LogOutTimerTask();
            timer.schedule(logoutTimeTask, 300000); 
        }else{
            if (timer != null){
                  timer.cancel();
                  timer = null;
            }
        }
    }

    @Override
    protected void onResume() {
        super.onResume();
        shouldNavigate = false;
        if (timer != null) {
            timer.cancel();
            Log.i("Main", "cancel timer");
            timer = null;
        }
    }

    private class LogOutTimerTask extends TimerTask {

        @Override
        public void run() {

            //redirect user to login screen
            shouldNavigate = false;
            Intent i = new Intent(AccountActivity.this, MainActivity.class);
            i.addFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP);
            startActivity(i);
            finish();
        }
    }
}

より良いアプローチはServiceSingletonクラスを保持することです。シングルトンクラスは

public Singleton{
    private static Singleton instance = null;
    private Singleton(){
        activityMap = new HashMap<String, Activity>();
    }

    public static Singleton getInstance(){
         if (instance == null) instance = new Singeton();
         return instance;
    }

    public HashMap<String, Activity> activityMap;

}

これで、各アクティビティにはタグ (名前など) が付けられるため、再開時の各アクティビティは

Singleton.getInstance().activityMap.put(tag, this);

そしていつ行くonPause

Singleton.getInstance().activityMap.remove(tag, this);

そのため、サイズSingleton.getInstance().activityMapがゼロであることをサービスが検出すると、明らかにフォアグラウンドでのアクティビティがないため、タイマーが開始されます。タイマーが切れたら、カウントがまだゼロかどうかを再度確認し、ゼロの場合はログアウトを実行します。

于 2016-08-24T04:40:32.130 に答える