1 /* 2 * Copyright (C) 2022 The Android Open Source Project 3 * 4 * Licensed under the Apache License, Version 2.0 (the "License"); 5 * you may not use this file except in compliance with the License. 6 * You may obtain a copy of the License at 7 * 8 * http://www.apache.org/licenses/LICENSE-2.0 9 * 10 * Unless required by applicable law or agreed to in writing, software 11 * distributed under the License is distributed on an "AS IS" BASIS, 12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 * See the License for the specific language governing permissions and 14 * limitations under the License. 15 */ 16 17 package com.android.systemui.shade 18 19 import com.android.systemui.common.buffer.RingBuffer 20 import com.android.systemui.dump.DumpsysTableLogger 21 import com.android.systemui.dump.Row 22 import com.android.systemui.shade.NotificationShadeWindowState.Buffer 23 import com.android.systemui.statusbar.StatusBarState 24 25 /** 26 * Represents state of shade window, used by [NotificationShadeWindowControllerImpl]. Contains 27 * nested class [Buffer] for pretty table logging in bug reports. 28 */ 29 class NotificationShadeWindowState( 30 @JvmField var keyguardShowing: Boolean = false, 31 @JvmField var keyguardOccluded: Boolean = false, 32 @JvmField var keyguardNeedsInput: Boolean = false, 33 @JvmField var panelVisible: Boolean = false, 34 /** shade panel is expanded (expansion fraction > 0) */ 35 @JvmField var panelExpanded: Boolean = false, 36 @JvmField var notificationShadeFocusable: Boolean = false, 37 @JvmField var bouncerShowing: Boolean = false, 38 @JvmField var keyguardFadingAway: Boolean = false, 39 @JvmField var keyguardGoingAway: Boolean = false, 40 @JvmField var qsExpanded: Boolean = false, 41 @JvmField var headsUpNotificationShowing: Boolean = false, 42 @JvmField var lightRevealScrimOpaque: Boolean = false, 43 @JvmField var forceWindowCollapsed: Boolean = false, 44 @JvmField var forceDozeBrightness: Boolean = false, 45 // TODO: forceUserActivity seems to be unused, delete? 46 @JvmField var forceUserActivity: Boolean = false, 47 @JvmField var launchingActivityFromNotification: Boolean = false, 48 @JvmField var mediaBackdropShowing: Boolean = false, 49 @JvmField var windowNotTouchable: Boolean = false, 50 @JvmField var componentsForcingTopUi: MutableSet<String> = mutableSetOf(), 51 @JvmField var forceOpenTokens: MutableSet<Any> = mutableSetOf(), 52 /** one of [StatusBarState] */ 53 @JvmField var statusBarState: Int = 0, 54 @JvmField var remoteInputActive: Boolean = false, 55 @JvmField var forcePluginOpen: Boolean = false, 56 @JvmField var dozing: Boolean = false, 57 @JvmField var dreaming: Boolean = false, 58 @JvmField var scrimsVisibility: Int = 0, 59 @JvmField var backgroundBlurRadius: Int = 0, 60 ) { 61 62 fun isKeyguardShowingAndNotOccluded(): Boolean { 63 return keyguardShowing && !keyguardOccluded 64 } 65 66 /** List of [String] to be used as a [Row] with [DumpsysTableLogger]. */ 67 val asStringList: List<String> by lazy { 68 listOf( 69 keyguardShowing.toString(), 70 keyguardOccluded.toString(), 71 keyguardNeedsInput.toString(), 72 panelVisible.toString(), 73 panelExpanded.toString(), 74 notificationShadeFocusable.toString(), 75 bouncerShowing.toString(), 76 keyguardFadingAway.toString(), 77 keyguardGoingAway.toString(), 78 qsExpanded.toString(), 79 headsUpNotificationShowing.toString(), 80 lightRevealScrimOpaque.toString(), 81 forceWindowCollapsed.toString(), 82 forceDozeBrightness.toString(), 83 forceUserActivity.toString(), 84 launchingActivityFromNotification.toString(), 85 mediaBackdropShowing.toString(), 86 windowNotTouchable.toString(), 87 componentsForcingTopUi.toString(), 88 forceOpenTokens.toString(), 89 StatusBarState.toString(statusBarState), 90 remoteInputActive.toString(), 91 forcePluginOpen.toString(), 92 dozing.toString(), 93 scrimsVisibility.toString(), 94 backgroundBlurRadius.toString() 95 ) 96 } 97 98 /** 99 * [RingBuffer] to store [NotificationShadeWindowState]. After the buffer is full, it will 100 * recycle old events. 101 */ 102 class Buffer(capacity: Int) { 103 104 private val buffer = RingBuffer(capacity) { NotificationShadeWindowState() } 105 106 /** Insert a new element in the buffer. */ 107 fun insert( 108 keyguardShowing: Boolean, 109 keyguardOccluded: Boolean, 110 keyguardNeedsInput: Boolean, 111 panelVisible: Boolean, 112 panelExpanded: Boolean, 113 notificationShadeFocusable: Boolean, 114 bouncerShowing: Boolean, 115 keyguardFadingAway: Boolean, 116 keyguardGoingAway: Boolean, 117 qsExpanded: Boolean, 118 headsUpShowing: Boolean, 119 lightRevealScrimOpaque: Boolean, 120 forceCollapsed: Boolean, 121 forceDozeBrightness: Boolean, 122 forceUserActivity: Boolean, 123 launchingActivity: Boolean, 124 backdropShowing: Boolean, 125 notTouchable: Boolean, 126 componentsForcingTopUi: MutableSet<String>, 127 forceOpenTokens: MutableSet<Any>, 128 statusBarState: Int, 129 remoteInputActive: Boolean, 130 forcePluginOpen: Boolean, 131 dozing: Boolean, 132 scrimsVisibility: Int, 133 backgroundBlurRadius: Int, 134 ) { 135 buffer.advance().apply { 136 this.keyguardShowing = keyguardShowing 137 this.keyguardOccluded = keyguardOccluded 138 this.keyguardNeedsInput = keyguardNeedsInput 139 this.panelVisible = panelVisible 140 this.panelExpanded = panelExpanded 141 this.notificationShadeFocusable = notificationShadeFocusable 142 this.bouncerShowing = bouncerShowing 143 this.keyguardFadingAway = keyguardFadingAway 144 this.keyguardGoingAway = keyguardGoingAway 145 this.qsExpanded = qsExpanded 146 this.headsUpNotificationShowing = headsUpShowing 147 this.lightRevealScrimOpaque = lightRevealScrimOpaque 148 this.forceWindowCollapsed = forceCollapsed 149 this.forceDozeBrightness = forceDozeBrightness 150 this.forceUserActivity = forceUserActivity 151 this.launchingActivityFromNotification = launchingActivity 152 this.mediaBackdropShowing = backdropShowing 153 this.windowNotTouchable = notTouchable 154 this.componentsForcingTopUi.clear() 155 this.componentsForcingTopUi.addAll(componentsForcingTopUi) 156 this.forceOpenTokens.clear() 157 this.forceOpenTokens.addAll(forceOpenTokens) 158 this.statusBarState = statusBarState 159 this.remoteInputActive = remoteInputActive 160 this.forcePluginOpen = forcePluginOpen 161 this.dozing = dozing 162 this.scrimsVisibility = scrimsVisibility 163 this.backgroundBlurRadius = backgroundBlurRadius 164 } 165 } 166 167 /** 168 * Returns the content of the buffer (sorted from latest to newest). 169 * 170 * @see [NotificationShadeWindowState.asStringList] 171 */ 172 fun toList(): List<Row> { 173 return buffer.map { it.asStringList } 174 } 175 } 176 177 companion object { 178 /** Headers for dumping a table using [DumpsysTableLogger]. */ 179 @JvmField 180 val TABLE_HEADERS = 181 listOf( 182 "keyguardShowing", 183 "keyguardOccluded", 184 "keyguardNeedsInput", 185 "panelVisible", 186 "panelExpanded", 187 "notificationShadeFocusable", 188 "bouncerShowing", 189 "keyguardFadingAway", 190 "keyguardGoingAway", 191 "qsExpanded", 192 "headsUpShowing", 193 "lightRevealScrimOpaque", 194 "forceCollapsed", 195 "forceDozeBrightness", 196 "forceUserActivity", 197 "launchingActivity", 198 "backdropShowing", 199 "notTouchable", 200 "componentsForcingTopUi", 201 "forceOpenTokens", 202 "statusBarState", 203 "remoteInputActive", 204 "forcePluginOpen", 205 "dozing", 206 "scrimsVisibility", 207 "backgroundBlurRadius" 208 ) 209 } 210 } 211