Turn Activity when screen locked

도입

최근 알람앱을 개발하고 있는데, 알람 시간이 되면 Notification 가 울리는 것이 아닌 액티비티가 표시되는 것이 조건이었다.

원래의 해결 방법이라면, 해당 Activity 의 onCreate(Bundle) 메서드에서 setContentView 메서드가 실행되기 전 아래의 코드를 삽입하는 것으로 마무리 된다.

 window.addFlags(
            WindowManager.LayoutParams.FLAG_DISMISS_KEYGUARD or
            WindowManager.LayoutParams.FLAG_SHOW_WHEN_LOCKED or
            WindowManager.LayoutParams.FLAG_TURN_SCREEN_ON)

하지만 위 방법의 경우 Oreo 8.0 ~ 8.1 에서 deprecated 되었고, 이에 따라 분기처리 할 필요성이 있었다.

Oreo 8.1 에서 바뀐 부분

window.addFlags(WindowManager.LayoutParams.FLAG_SHOW_WHEN_LOCKED)
window.addFlags(WindowManager.LayoutParams.FLAG_TURN_SCREEN_ON)

위 두 개 코드가 Deprecated 되었는데, 의도하지 않은 두 번의 라이프 사이클 이벤트를 방지하기 위해서 라고 한다. 이 코드 대신 사용할 수 있는 코드는 다음과 같다.

setShowWhenLocked(true)
setTurnScreenOn(true)

둘 다 Activity 에 있는 메서드이며, 각각 FLAG_SHOW_WHEN_LOCKEDFLAG_TURN_SCREEN_ON 과 같은 효과를 낸다.

Oreo 8.0 에서 바뀐 부분

window.addFlags(WindowManager.LayoutParams.FLAG_DISMISS_KEYGUARD)

위 코드가 Deprecated 되었는데, 이 이유로는 해당 플래그가 있는 액티비티가 포커스 되었을 때 Keyguard가 해제되므로 의도하지 않은 터치를 막을 수 없기 때문이라고 한다.

대신, KeyguardManager 를 통하여 keyguard 를 dismiss 하는 요청을 해야 한다.

val keyguardManager = getSystemService(Context.KEYGUARD_SERVICE) as? KeyguardManager?
keyguardManager?.requestDismissKeyguard(this, null)

전체 코드

위 사항을 전부 고려하면 아래와 같은 코드가 나온다.

fun Activity.setTurnScreenOnLock() {
    val keyguardManager = getSystemService(Context.KEYGUARD_SERVICE) as? KeyguardManager?
    when {
        android.os.Build.VERSION.SDK_INT >= 27 -> {
            setShowWhenLocked(true)
            setTurnScreenOn(true)
            keyguardManager?.requestDismissKeyguard(this, null)
        }
        android.os.Build.VERSION.SDK_INT == 26 -> {
            window.addFlags(WindowManager.LayoutParams.FLAG_SHOW_WHEN_LOCKED)
            window.addFlags(WindowManager.LayoutParams.FLAG_TURN_SCREEN_ON)
            keyguardManager?.requestDismissKeyguard(this, null)
        }
        else -> {
            window.addFlags(WindowManager.LayoutParams.FLAG_SHOW_WHEN_LOCKED)
            window.addFlags(WindowManager.LayoutParams.FLAG_TURN_SCREEN_ON)
            window.addFlags(WindowManager.LayoutParams.FLAG_DISMISS_KEYGUARD)
        }
    }

    window.addFlags(WindowManager.LayoutParams.FLAG_KEEP_SCREEN_ON)
}