Soheil
Soheil

Reputation: 1706

how to check screen on/off status in onStop()?

as mentioned here, when the screen goes off, the onStop() of current Activity will be called. I need to check the screen on/off status when the onStop() of my Activity is called. so I have registered a BroadcastReceiver for these actions(ACTION_SCREEN_ON AND ACTION_SCREEN_OFF) to record the current on/off status(and they work properly, I have logged!).
but when I turn off the screen and check the on/off status in the onStop , it says the screen is on. why? I think the receiver must receive the ACTION_SCREEN_OFF before onStop is called so what's wrong?

Upvotes: 32

Views: 31609

Answers (4)

Alexander Semenov
Alexander Semenov

Reputation: 1552

You can try to use PowerManager system service for this purpose, here is example and official documentation (note this method was added in API level 7):

PowerManager pm = (PowerManager) getSystemService(Context.POWER_SERVICE);
boolean isScreenOn = pm.isScreenOn();

EDIT:

isScreenOn() method is deprecated API level 21. You should use isInteractive instead:

Java:

PowerManager pm = (PowerManager) getSystemService(Context.POWER_SERVICE);
boolean isScreenOn = pm.isInteractive();

Kotlin:

val pm = applicationContext.getSystemService(Context.POWER_SERVICE) as PowerManager
var isScreenOn = pm.isInteractive

http://developer.android.com/reference/android/os/PowerManager.html#isInteractive()

Upvotes: 79

Atakan Yıldırım
Atakan Yıldırım

Reputation: 882

If you want to manually check the screen state instead of the broadcast receiver, you should consider some situations.

  • Screen may be active with Doze mode (Samsung's Always-on-Display feature)
  • VR mode may be active

In order to check that the screen is not turned off and the user is actively using the phone, the screen state must not be Display.STATE_OFF and not in the keyguardManager.isKeyguardLocked() state.

public static boolean isDeviceActive(
        @NonNull DisplayManager displayManager,
        @NonNull KeyguardManager keyguardManager
) {
    for (Display display : displayManager.getDisplays()) {
        if (display.getState() != Display.STATE_OFF) {
            return !keyguardManager.isKeyguardLocked();
        }
    }
    return false;
}

Upvotes: 1

Rem-D
Rem-D

Reputation: 675

As mentioned in this answer to a similar question. In API 21 and above we can use the DisplayManager to determine the state of the display. This has the advantage of supporting the querying of multiple displays:

DisplayManager dm = (DisplayManager) 
context.getSystemService(Context.DISPLAY_SERVICE);
for (Display display : dm.getDisplays()) {
    if (display.getState() != Display.STATE_OFF) {
        return true;
    }
}
return false;

Depending upon your circumstance it might be more appropriate to query the display that a particular view is being displayed on:

myView.getDisplay().getState() != Display.STATE_OFF

Upvotes: 3

Mary Seo
Mary Seo

Reputation: 9

PowerManager pm = (PowerManager) mMainActivity.getSystemService(Context.POWER_SERVICE);
boolean isScreenOn = Utils.hasLollipop() ? pm.isInteractive() : pm.isScreenOn();

Upvotes: 0

Related Questions