Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit d57efdf2 authored by Chris Göllner's avatar Chris Göllner
Browse files

DisplayRepository: tweak to implementation of displayAdditionEvent

- Change it so that it only emits after `displays` has emitted. This
  guarantees that calls to `getDisplay` with the newly added display id
  will always be non-null.
- This also allows us to reuse an existing `Display` instance, without
  having to do another call to `DisplayManager`

Test: DisplayRepositoryTest
Bug: 367592591
Flag: EXEMPT small implementation tweak covered with tests
Change-Id: Ic5d6f877d8ab77f13e239632f6dee1deecdf97eb
parent 92be35f8
Loading
Loading
Loading
Loading
+22 −0
Original line number Diff line number Diff line
@@ -439,6 +439,28 @@ class DisplayRepositoryTest : SysuiTestCase() {
            assertThat(display!!.type).isEqualTo(TYPE_EXTERNAL)
        }

    @Test
    fun displayAdditionEvent_emptyByDefault() =
        testScope.runTest {
            setDisplays(1, 2, 3)

            val lastAddedDisplay by lastDisplayAdditionEvent()

            assertThat(lastAddedDisplay).isNull()
        }

    @Test
    fun displayAdditionEvent_displaysAdded_doesNotReplayEventsToNewSubscribers() =
        testScope.runTest {
            val priorDisplayAdded by lastDisplayAdditionEvent()
            setDisplays(1)
            sendOnDisplayAdded(1)
            assertThat(priorDisplayAdded?.displayId).isEqualTo(1)

            val lastAddedDisplay by collectLastValue(displayRepository.displayAdditionEvent)
            assertThat(lastAddedDisplay).isNull()
        }

    @Test
    fun defaultDisplayOff_changes() =
        testScope.runTest {
+14 −6
Original line number Diff line number Diff line
@@ -33,6 +33,7 @@ import com.android.systemui.dagger.SysUISingleton
import com.android.systemui.dagger.qualifiers.Background
import com.android.systemui.display.data.DisplayEvent
import com.android.systemui.util.Compile
import com.android.systemui.util.kotlin.pairwiseBy
import javax.inject.Inject
import kotlinx.coroutines.CoroutineDispatcher
import kotlinx.coroutines.CoroutineScope
@@ -41,11 +42,12 @@ import kotlinx.coroutines.flow.Flow
import kotlinx.coroutines.flow.MutableStateFlow
import kotlinx.coroutines.flow.SharingStarted
import kotlinx.coroutines.flow.StateFlow
import kotlinx.coroutines.flow.asFlow
import kotlinx.coroutines.flow.combine
import kotlinx.coroutines.flow.distinctUntilChanged
import kotlinx.coroutines.flow.filter
import kotlinx.coroutines.flow.filterIsInstance
import kotlinx.coroutines.flow.first
import kotlinx.coroutines.flow.flatMapLatest
import kotlinx.coroutines.flow.flowOn
import kotlinx.coroutines.flow.map
import kotlinx.coroutines.flow.onEach
@@ -146,11 +148,6 @@ constructor(
    override val displayChangeEvent: Flow<Int> =
        allDisplayEvents.filterIsInstance<DisplayEvent.Changed>().map { event -> event.displayId }

    override val displayAdditionEvent: Flow<Display?> =
        allDisplayEvents.filterIsInstance<DisplayEvent.Added>().map {
            getDisplayFromDisplayManager(it.displayId)
        }

    override val displayRemovalEvent: Flow<Int> =
        allDisplayEvents.filterIsInstance<DisplayEvent.Removed>().map { it.displayId }

@@ -212,6 +209,17 @@ constructor(
     */
    override val displays: StateFlow<Set<Display>> = enabledDisplays

    /**
     * Implementation that maps from [displays], instead of [allDisplayEvents] for 2 reasons:
     * 1. Guarantee that it emits __after__ [displays] emitted. This way it is guaranteed that
     *    calling [getDisplay] for the newly added display will be non-null.
     * 2. Reuse the existing instance of [Display] without a new call to [DisplayManager].
     */
    override val displayAdditionEvent: Flow<Display?> =
        displays
            .pairwiseBy { previousDisplays, currentDisplays -> currentDisplays - previousDisplays }
            .flatMapLatest { it.asFlow() }

    val _ignoredDisplayIds = MutableStateFlow<Set<Int>>(emptySet())
    private val ignoredDisplayIds: Flow<Set<Int>> = _ignoredDisplayIds.debugLog("ignoredDisplayIds")