1 /*
<lambda>null2  * Copyright (C) 2023 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 android.tools.flicker.subject.events
18 
19 import android.tools.Timestamps
20 import android.tools.flicker.assertions.Fact
21 import android.tools.flicker.subject.FlickerSubject
22 import android.tools.flicker.subject.exceptions.ExceptionMessageBuilder
23 import android.tools.flicker.subject.exceptions.IncorrectFocusException
24 import android.tools.io.Reader
25 import android.tools.traces.events.EventLog
26 import android.tools.traces.events.FocusEvent
27 
28 /** Truth subject for [FocusEvent] objects. */
29 class EventLogSubject(val eventLog: EventLog, override val reader: Reader) : FlickerSubject() {
30     override val timestamp = eventLog.entries.firstOrNull()?.timestamp ?: Timestamps.empty()
31 
32     private val _focusChanges by lazy {
33         val focusList = mutableListOf<FocusEvent>()
34         eventLog.focusEvents.firstOrNull { !it.hasFocus() }?.let { focusList.add(it) }
35         focusList + eventLog.focusEvents.filter { it.hasFocus() }
36     }
37 
38     private val exceptionMessageBuilder
39         get() = ExceptionMessageBuilder().forSubject(this)
40 
41     fun focusChanges(vararg windows: String) = apply {
42         if (windows.isNotEmpty()) {
43             val focusChanges =
44                 _focusChanges.dropWhile { !it.window.contains(windows.first()) }.take(windows.size)
45 
46             val builder =
47                 exceptionMessageBuilder
48                     .setExpected(windows.joinToString(", "))
49                     .setActual(focusChanges)
50 
51             if (focusChanges.isEmpty()) {
52                 val errorMsgBuilder = builder.setMessage("Focus did not change")
53                 throw IncorrectFocusException(errorMsgBuilder)
54             }
55 
56             val actual = focusChanges.map { Fact("Focus change", it) }
57             builder.setActual(actual)
58 
59             val success =
60                 windows.size <= focusChanges.size &&
61                     focusChanges.zip(windows).all { (focus, search) ->
62                         focus.window.contains(search)
63                     }
64 
65             if (!success) {
66                 val errorMsgBuilder = builder.setMessage("Incorrect focus change")
67                 throw IncorrectFocusException(errorMsgBuilder)
68             }
69         }
70     }
71 
72     fun focusDoesNotChange() = apply {
73         if (_focusChanges.isNotEmpty()) {
74             val actual = _focusChanges.map { Fact("Focus change", it) }
75             val errorMsgBuilder =
76                 exceptionMessageBuilder
77                     .setMessage("Focus changes")
78                     .setExpected("")
79                     .setActual(actual)
80             throw IncorrectFocusException(errorMsgBuilder)
81         }
82     }
83 }
84