发布Oreo 8.0+ Action_User_Present解决方法?

时间:2019-04-21 22:17:04

标签: c# android

我希望设备每次解锁时都可以打开我的应用程序。实际上,我需要一致地替换ACTION_USER_PRESENT。


(注意,这是一项跨学科,经过同行评审的学术研究,将很快开始,对研究的成功至关重要)

在Oero 8.0更新之前,ACTION_USER_PRESENT是每次设备解锁时启动android应用的理想方法。

不幸的是,我一直试图使用的变通方法只是没有削减它。实际上,我已经分配了一个myBroadastReceiver来尝试运行该应用程序和PowerManager来查看设备是否打开。取决于是否使用设备会影响myBroadcastReceiver中的代码是否会初始化Intent。

问题1)只能将广播接收机分配为至少每15分钟运行一次。每当设备解锁时,我都需要运行它。

问题2)有时广播接收器甚至一次都不会尝试运行几个小时……似乎分配的15分钟检查只是一个宽松的建议,而不是明确的命令。

某些代码:

公共类classMyBroadcastReceiver扩展了BroadcastReceiver {

@Override
public void onReceive(Context contextOfReceive, Intent intentOfReceive) {

    ////////////////////////////////////////////////////////////////////////////////////////////
    //This loads up the user selected settings choosen at the homepage of the application.
    final SharedPreferences internalAppInformation = contextOfReceive.getSharedPreferences("userPreferences", Context.MODE_PRIVATE);
    final SharedPreferences.Editor editor = internalAppInformation.edit();
    ////////////////////////////////////////////////////////////////////////////////////////////

    ////////////////////////////////////////////////////////////////////////////////////////////
    //Code used to determine 2 things
    // 1) if the Device being used or inactive
    // 2) if the activity has already been prompted earlier and therefore should be in the foreground of the device
    PowerManager pm = (PowerManager) contextOfReceive.getSystemService(Context.POWER_SERVICE);
    boolean booleanIsScreenOn = pm.isInteractive();
    boolean booleanIsActivityUp = internalAppInformation.getBoolean("booleanIsActivityUp", false);
    ////////////////////////////////////////////////////////////////////////////////////////////

    ////////////////////////////////////////////////////////////////////////////////////////////
    //If Screen is Off (i.e. the device is NOT BEING USED AT THE MOMENT)
    //then this code should allow the Activity to Start
    if ( (!booleanIsActivityUp)&&(!booleanIsScreenOn) ) {
        //Initiates and Starts up the Intent PromptAndClose.class

        editor.putBoolean("booleanIsActivityUp", true);
        editor.commit();
        editor.apply();

        //THE REST OF THE CODE BELOW IS JUST CHOOSING AND
        // INITIATING THE PROGRAM AND IS NOT PROBLEMATIC.

    }

}

如果有帮助,可以提供更详细的代码。我担心更多的代码会对读者造成混乱。

启动myBroadcastReceiver时要描述的附加代码。

公共类设置扩展了AppCompatActivity {

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

    ////////////////////////////////////////////////////////////////////////////////////////////
    //Sets up and starts the calendar (with the setAlarm method for re-occuring attempts to 
    //prompt the app to move to the foreground if the right conditions are met.
    Calendar calendar = Calendar.getInstance();
    //if(Build.VERSION.SDK_INT >= 23) {

    Log.i("Calendar", "Set Calendar >=23");
    calendar.set(
            calendar.get(Calendar.YEAR),
            calendar.get(Calendar.MONTH),
            calendar.get(Calendar.DAY_OF_MONTH),
            calendar.get(Calendar.HOUR),
            calendar.get(Calendar.MINUTE),
            30
    );


    setAlarm(calendar.getTimeInMillis());
    int time = (int) calendar.getTimeInMillis();
    String timeString = String.valueOf(time);
    Log.i("TIME", "time: " + timeString);

}

private void setAlarm(long timeInMillis) {
    AlarmManager alarmManager = (AlarmManager) getSystemService(Context.ALARM_SERVICE);
    Intent intent = new Intent(this, classMyBroadcastReceiver.class);

    PendingIntent pendingIntent = PendingIntent.getBroadcast(this, 0, intent, 0);

    assert alarmManager != null;

    //RTC-Fires the pending intent at the specified time but does not wake up the device.
    //The shortest interval is INTERVAL_FIFTEEN_MINUTES.
    alarmManager.setInexactRepeating(AlarmManager.RTC, timeInMillis,
            AlarmManager.INTERVAL_FIFTEEN_MINUTES, pendingIntent);

}

}

此代码出现在应用程序的主要活动中。其概念是,首次安装和运行该应用程序时,它将运行此代码,并在不使用该设备的情况下启动并连续循环检查并显示该应用程序到设备的前台。一旦用户与该意图进行了交互并关闭了该循环,循环将再次启动。

1 个答案:

答案 0 :(得分:2)

那是行不通的。打ze模式和应用待机状态会使您尝试做的事情变得非常不可靠。

尝试以下操作:创建前台服务。当您需要开始接收此广播时,请启动该前台服务。在该服务的onCreate()中,调用registerReceiver()ACTION_USER_PRESENT注册一个接收者。只要您的服务正在运行,您就会像以前一样收到ACTION_USER_PRESENT广播。