FotisK FotisK - 2 months ago 16
Android Question

Screen Pinning unreliable: sometimes asks for passcode on awakening, other times skips directly to pinned app

(this question was originally posted on the android enthusiasts stub in a slightly altered form)

I've been trying to lock an android tablet in kiosk mode for a survey app I'm making; for that I've made use of the Screen Pinning lollipop feature (with passcode enabled).
I used the following code

@Override
protected void onResume() {
super.onResume();
startLockTask();
}


For the most part, this worked "reliably",
- If the application is pinned and the user lets the device screen time out (or presses the power/lock button), the device will enter sleep and next time he tries to awaken the device (via the power/lock button) the pinned app will pop into view again (without the user having to enter the passcode that he obviously doesn't know).
- On the other hand if the user attempts to unpin it, he/she is presented with the lock screen and the passcode.
So far so good.

However some times (and this is puzzling me) when the user tries to awaken the device, instead of going directly to the pinned app, the device will display the lock screen and ask the user for the passcode!

I'm not sure why the inconsistency in behavior (ie on wake, it sometimes asks for passcode, while other times goes directly to the pinned app) and couldn't find any mention anywhere of such a behavior.
Any input will be greatly appreciated!

Thanks!

Answer

Apparently every time the device wakes up, the startLockTask() is being executed. In case it was already in pinned mode this would run again, and cause issues. Eventually, I tested out my initial assumption and edited the onResume() function to perform a startLockTask() only if it is not pinned already. This seems to have solved the problems (even though I don't understand why it this behavior). Would be glad if somebody could explain this. I'm posting the answer here for anybody who bumps into this issue.

onResume()

    @Override
    protected void onResume() {
        super.onResume();
        if(Build.VERSION.SDK_INT >=Build.VERSION_CODES.LOLLIPOP) {
            if (!isAppInLockTaskMode()) {
                startLockTask();
            }
        }
    }

isAppInLockTaskMode() was taken from enter link description here and solves the issue for different API versions.

public boolean isAppInLockTaskMode() {
        ActivityManager activityManager=(ActivityManager)getSystemService(Context.ACTIVITY_SERVICE);
        if(Build.VERSION.SDK_INT >=Build.VERSION_CODES.M) { // When SDK version is 23
            int lockTaskMode=activityManager.getLockTaskModeState();
            return lockTaskMode != ActivityManager.LOCK_TASK_MODE_NONE ? true : false;
        }
        else if(Build.VERSION.SDK_INT >=Build.VERSION_CODES.LOLLIPOP &&
                Build.VERSION.SDK_INT< Build.VERSION_CODES.M) {
            //When SDK version <=21 and <23. This API is deprecated in 23.
            return activityManager.isInLockTaskMode();
        }
        else {
            return false;
        }
    }
Comments