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 shadeOrQsExpanded: Boolean = false,
36     @JvmField var notificationShadeFocusable: Boolean = false,
37     @JvmField var bouncerShowing: Boolean = false,
38     @JvmField var glanceableHubShowing: Boolean = false,
39     @JvmField var keyguardFadingAway: Boolean = false,
40     @JvmField var keyguardGoingAway: Boolean = false,
41     @JvmField var qsExpanded: Boolean = false,
42     @JvmField var headsUpNotificationShowing: Boolean = false,
43     @JvmField var lightRevealScrimOpaque: Boolean = false,
44     @JvmField var isSwitchingUsers: Boolean = false,
45     @JvmField var forceWindowCollapsed: Boolean = false,
46     @JvmField var forceDozeBrightness: Boolean = false,
47     // TODO: forceUserActivity seems to be unused, delete?
48     @JvmField var forceUserActivity: Boolean = false,
49     @JvmField var launchingActivityFromNotification: Boolean = false,
50     @JvmField var mediaBackdropShowing: Boolean = false,
51     @JvmField var windowNotTouchable: Boolean = false,
52     @JvmField var componentsForcingTopUi: MutableSet<String> = mutableSetOf(),
53     @JvmField var forceOpenTokens: MutableSet<Any> = mutableSetOf(),
54     /** one of [StatusBarState] */
55     @JvmField var statusBarState: Int = 0,
56     @JvmField var remoteInputActive: Boolean = false,
57     @JvmField var forcePluginOpen: Boolean = false,
58     @JvmField var dozing: Boolean = false,
59     @JvmField var dreaming: Boolean = false,
60     @JvmField var scrimsVisibility: Int = 0,
61     @JvmField var backgroundBlurRadius: Int = 0,
62     @JvmField var communalVisible: Boolean = false,
63 ) {
64 
isKeyguardShowingAndNotOccludednull65     fun isKeyguardShowingAndNotOccluded(): Boolean {
66         return keyguardShowing && !keyguardOccluded
67     }
68 
isCommunalVisibleAndNotOccludednull69     fun isCommunalVisibleAndNotOccluded(): Boolean {
70         return communalVisible && !keyguardOccluded
71     }
72 
73     /** List of [String] to be used as a [Row] with [DumpsysTableLogger]. */
<lambda>null74     val asStringList: List<String> by lazy {
75         listOf(
76             keyguardShowing.toString(),
77             keyguardOccluded.toString(),
78             keyguardNeedsInput.toString(),
79             panelVisible.toString(),
80             shadeOrQsExpanded.toString(),
81             notificationShadeFocusable.toString(),
82             bouncerShowing.toString(),
83             glanceableHubShowing.toString(),
84             keyguardFadingAway.toString(),
85             keyguardGoingAway.toString(),
86             qsExpanded.toString(),
87             headsUpNotificationShowing.toString(),
88             lightRevealScrimOpaque.toString(),
89             isSwitchingUsers.toString(),
90             forceWindowCollapsed.toString(),
91             forceDozeBrightness.toString(),
92             forceUserActivity.toString(),
93             launchingActivityFromNotification.toString(),
94             mediaBackdropShowing.toString(),
95             windowNotTouchable.toString(),
96             componentsForcingTopUi.toString(),
97             forceOpenTokens.toString(),
98             StatusBarState.toString(statusBarState),
99             remoteInputActive.toString(),
100             forcePluginOpen.toString(),
101             dozing.toString(),
102             scrimsVisibility.toString(),
103             backgroundBlurRadius.toString(),
104             communalVisible.toString(),
105         )
106     }
107 
108     /**
109      * [RingBuffer] to store [NotificationShadeWindowState]. After the buffer is full, it will
110      * recycle old events.
111      */
112     class Buffer(capacity: Int) {
113 
<lambda>null114         private val buffer = RingBuffer(capacity) { NotificationShadeWindowState() }
115 
116         /** Insert a new element in the buffer. */
insertnull117         fun insert(
118             keyguardShowing: Boolean,
119             keyguardOccluded: Boolean,
120             keyguardNeedsInput: Boolean,
121             panelVisible: Boolean,
122             panelExpanded: Boolean,
123             notificationShadeFocusable: Boolean,
124             glanceableHubShowing: Boolean,
125             bouncerShowing: Boolean,
126             keyguardFadingAway: Boolean,
127             keyguardGoingAway: Boolean,
128             qsExpanded: Boolean,
129             headsUpShowing: Boolean,
130             lightRevealScrimOpaque: Boolean,
131             isSwitchingUsers: Boolean,
132             forceCollapsed: Boolean,
133             forceDozeBrightness: Boolean,
134             forceUserActivity: Boolean,
135             launchingActivity: Boolean,
136             backdropShowing: Boolean,
137             notTouchable: Boolean,
138             componentsForcingTopUi: MutableSet<String>,
139             forceOpenTokens: MutableSet<Any>,
140             statusBarState: Int,
141             remoteInputActive: Boolean,
142             forcePluginOpen: Boolean,
143             dozing: Boolean,
144             scrimsVisibility: Int,
145             backgroundBlurRadius: Int,
146             communalVisible: Boolean,
147         ) {
148             buffer.advance().apply {
149                 this.keyguardShowing = keyguardShowing
150                 this.keyguardOccluded = keyguardOccluded
151                 this.keyguardNeedsInput = keyguardNeedsInput
152                 this.panelVisible = panelVisible
153                 this.shadeOrQsExpanded = panelExpanded
154                 this.notificationShadeFocusable = notificationShadeFocusable
155                 this.glanceableHubShowing = glanceableHubShowing
156                 this.bouncerShowing = bouncerShowing
157                 this.keyguardFadingAway = keyguardFadingAway
158                 this.keyguardGoingAway = keyguardGoingAway
159                 this.qsExpanded = qsExpanded
160                 this.headsUpNotificationShowing = headsUpShowing
161                 this.lightRevealScrimOpaque = lightRevealScrimOpaque
162                 this.isSwitchingUsers = isSwitchingUsers
163                 this.forceWindowCollapsed = forceCollapsed
164                 this.forceDozeBrightness = forceDozeBrightness
165                 this.forceUserActivity = forceUserActivity
166                 this.launchingActivityFromNotification = launchingActivity
167                 this.mediaBackdropShowing = backdropShowing
168                 this.windowNotTouchable = notTouchable
169                 this.componentsForcingTopUi.clear()
170                 this.componentsForcingTopUi.addAll(componentsForcingTopUi)
171                 this.forceOpenTokens.clear()
172                 this.forceOpenTokens.addAll(forceOpenTokens)
173                 this.statusBarState = statusBarState
174                 this.remoteInputActive = remoteInputActive
175                 this.forcePluginOpen = forcePluginOpen
176                 this.dozing = dozing
177                 this.scrimsVisibility = scrimsVisibility
178                 this.backgroundBlurRadius = backgroundBlurRadius
179                 this.communalVisible = communalVisible
180             }
181         }
182 
183         /**
184          * Returns the content of the buffer (sorted from latest to newest).
185          *
186          * @see [NotificationShadeWindowState.asStringList]
187          */
toListnull188         fun toList(): List<Row> {
189             return buffer.map { it.asStringList }
190         }
191     }
192 
193     companion object {
194         /** Headers for dumping a table using [DumpsysTableLogger]. */
195         @JvmField
196         val TABLE_HEADERS =
197             listOf(
198                 "keyguardShowing",
199                 "keyguardOccluded",
200                 "keyguardNeedsInput",
201                 "panelVisible",
202                 "panelExpanded",
203                 "notificationShadeFocusable",
204                 "glanceableHubShowing",
205                 "bouncerShowing",
206                 "keyguardFadingAway",
207                 "keyguardGoingAway",
208                 "qsExpanded",
209                 "headsUpShowing",
210                 "lightRevealScrimOpaque",
211                 "isSwitchingUsers",
212                 "forceCollapsed",
213                 "forceDozeBrightness",
214                 "forceUserActivity",
215                 "launchingActivity",
216                 "backdropShowing",
217                 "notTouchable",
218                 "componentsForcingTopUi",
219                 "forceOpenTokens",
220                 "statusBarState",
221                 "remoteInputActive",
222                 "forcePluginOpen",
223                 "dozing",
224                 "scrimsVisibility",
225                 "backgroundBlurRadius",
226                 "communalVisible"
227             )
228     }
229 }
230