diff options
15 files changed, 228 insertions, 32 deletions
diff --git a/packages/SystemUI/multivalentTests/src/com/android/systemui/volume/CsdWarningDialogTest.java b/packages/SystemUI/multivalentTests/src/com/android/systemui/volume/CsdWarningDialogTest.java index bebf1cfa86e7..ac4ef06cd53a 100644 --- a/packages/SystemUI/multivalentTests/src/com/android/systemui/volume/CsdWarningDialogTest.java +++ b/packages/SystemUI/multivalentTests/src/com/android/systemui/volume/CsdWarningDialogTest.java @@ -18,16 +18,13 @@ package com.android.systemui.volume; import static android.media.AudioManager.CSD_WARNING_DOSE_REACHED_1X; import static android.media.AudioManager.CSD_WARNING_DOSE_REPEATED_5X; - import static com.google.common.truth.Truth.assertThat; - import static org.mockito.Mockito.any; import static org.mockito.Mockito.eq; import static org.mockito.Mockito.mock; import static org.mockito.Mockito.verify; import static org.mockito.Mockito.when; - import android.app.Notification; import android.app.NotificationManager; import android.content.Intent; @@ -48,13 +45,12 @@ import com.android.systemui.plugins.VolumeDialog; import com.android.systemui.util.concurrency.FakeExecutor; import com.android.systemui.util.time.FakeSystemClock; -import com.google.common.collect.ImmutableList; - import org.junit.After; import org.junit.Before; import org.junit.Test; import org.junit.runner.RunWith; +import java.util.Collections; import java.util.List; import java.util.Optional; @@ -69,8 +65,8 @@ public class CsdWarningDialogTest extends SysuiTestCase { private CsdWarningDialog mDialog; private static final String DISMISS_CSD_NOTIFICATION = "com.android.systemui.volume.DISMISS_CSD_NOTIFICATION"; - private final Optional<ImmutableList<CsdWarningAction>> mEmptyActions = - Optional.of(ImmutableList.of()); + private final Optional<List<CsdWarningAction>> mEmptyActions = + Optional.of(Collections.emptyList()); @Before public void setup() { @@ -84,7 +80,7 @@ public class CsdWarningDialogTest extends SysuiTestCase { @Test public void create1XCsdDialogAndWait_sendsNotification() { - FakeExecutor executor = new FakeExecutor(new FakeSystemClock()); + FakeExecutor executor = new FakeExecutor(new FakeSystemClock()); // instantiate directly instead of via factory; we don't want executor to be @Background mDialog = new CsdWarningDialog(CSD_WARNING_DOSE_REACHED_1X, mContext, mAudioManager, mNotificationManager, executor, null, @@ -102,7 +98,7 @@ public class CsdWarningDialogTest extends SysuiTestCase { @Test public void create5XCsdDialogAndWait_willSendNotification() { - FakeExecutor executor = new FakeExecutor(new FakeSystemClock()); + FakeExecutor executor = new FakeExecutor(new FakeSystemClock()); mDialog = new CsdWarningDialog(CSD_WARNING_DOSE_REPEATED_5X, mContext, mAudioManager, mNotificationManager, executor, null, mEmptyActions, @@ -122,7 +118,7 @@ public class CsdWarningDialogTest extends SysuiTestCase { .setPackage(mContext.getPackageName()); mDialog = new CsdWarningDialog(CSD_WARNING_DOSE_REPEATED_5X, mContext, mAudioManager, mNotificationManager, executor, null, - Optional.of(ImmutableList.of(new CsdWarningAction("Undo", undoIntent, false))), + Optional.of(List.of(new CsdWarningAction("Undo", undoIntent, false))), mFakeBroadcastDispatcher); when(mAudioManager.getStreamVolume(AudioManager.STREAM_MUSIC)).thenReturn(25); @@ -149,7 +145,7 @@ public class CsdWarningDialogTest extends SysuiTestCase { .setPackage(mContext.getPackageName()); mDialog = new CsdWarningDialog(CSD_WARNING_DOSE_REPEATED_5X, mContext, mAudioManager, mNotificationManager, executor, null, - Optional.of(ImmutableList.of(new CsdWarningAction("Undo", undoIntent, false))), + Optional.of(List.of(new CsdWarningAction("Undo", undoIntent, false))), mFakeBroadcastDispatcher); Intent dismissIntent = new Intent(DISMISS_CSD_NOTIFICATION) .setPackage(mContext.getPackageName()); diff --git a/packages/SystemUI/src/com/android/systemui/volume/CsdWarningDialog.java b/packages/SystemUI/src/com/android/systemui/volume/CsdWarningDialog.java index a63660ba2804..5c439262b02c 100644 --- a/packages/SystemUI/src/com/android/systemui/volume/CsdWarningDialog.java +++ b/packages/SystemUI/src/com/android/systemui/volume/CsdWarningDialog.java @@ -46,14 +46,13 @@ import com.android.systemui.statusbar.phone.SystemUIDialog; import com.android.systemui.util.NotificationChannels; import com.android.systemui.util.concurrency.DelayableExecutor; -import com.google.common.collect.ImmutableList; +import java.util.List; +import java.util.Optional; import dagger.assisted.Assisted; import dagger.assisted.AssistedFactory; import dagger.assisted.AssistedInject; -import java.util.Optional; - /** * A class that implements the three Computed Sound Dose-related warnings defined in * {@link AudioManager}: @@ -108,7 +107,7 @@ public class CsdWarningDialog extends SystemUIDialog private long mShowTime; @VisibleForTesting public int mCachedMediaStreamVolume; - private Optional<ImmutableList<CsdWarningAction>> mActionIntents; + private Optional<List<CsdWarningAction>> mActionIntents; private final BroadcastDispatcher mBroadcastDispatcher; /** @@ -120,7 +119,7 @@ public class CsdWarningDialog extends SystemUIDialog CsdWarningDialog create( int csdWarning, Runnable onCleanup, - Optional<ImmutableList<CsdWarningAction>> actionIntents); + Optional<List<CsdWarningAction>> actionIntents); } @AssistedInject @@ -131,7 +130,7 @@ public class CsdWarningDialog extends SystemUIDialog NotificationManager notificationManager, @Background DelayableExecutor delayableExecutor, @Assisted Runnable onCleanup, - @Assisted Optional<ImmutableList<CsdWarningAction>> actionIntents, + @Assisted Optional<List<CsdWarningAction>> actionIntents, BroadcastDispatcher broadcastDispatcher) { super(context); mCsdWarning = csdWarning; @@ -350,7 +349,7 @@ public class CsdWarningDialog extends SystemUIDialog if (Flags.sounddoseCustomization() && mActionIntents.isPresent() && !mActionIntents.get().isEmpty()) { - ImmutableList<CsdWarningAction> actionIntentsList = mActionIntents.get(); + List<CsdWarningAction> actionIntentsList = mActionIntents.get(); for (CsdWarningAction action : actionIntentsList) { if (action.getLabel() == null || action.getIntent() == null) { Log.w(TAG, "Null action intent received. Skipping addition to notification"); diff --git a/packages/SystemUI/src/com/android/systemui/volume/VolumeDialogImpl.java b/packages/SystemUI/src/com/android/systemui/volume/VolumeDialogImpl.java index a4e46f667329..ae063b416dca 100644 --- a/packages/SystemUI/src/com/android/systemui/volume/VolumeDialogImpl.java +++ b/packages/SystemUI/src/com/android/systemui/volume/VolumeDialogImpl.java @@ -31,7 +31,6 @@ import static android.view.View.INVISIBLE; import static android.view.View.LAYOUT_DIRECTION_RTL; import static android.view.View.VISIBLE; import static android.view.ViewGroup.LayoutParams.WRAP_CONTENT; - import static com.android.internal.jank.InteractionJankMonitor.CUJ_VOLUME_CONTROL; import static com.android.internal.jank.InteractionJankMonitor.Configuration.Builder; import static com.android.settingslib.flags.Flags.audioSharingDeveloperOption; @@ -144,18 +143,17 @@ import com.android.systemui.volume.domain.interactor.VolumeDialogInteractor; import com.android.systemui.volume.domain.interactor.VolumePanelNavigationInteractor; import com.android.systemui.volume.panel.shared.flag.VolumePanelFlag; import com.android.systemui.volume.ui.navigation.VolumeNavigator; - import com.google.android.msdl.domain.MSDLPlayer; -import com.google.common.collect.ImmutableList; - -import dagger.Lazy; import java.io.PrintWriter; import java.util.ArrayList; +import java.util.Collections; import java.util.List; import java.util.Optional; import java.util.function.Consumer; +import dagger.Lazy; + /** * Visual presentation of the volume dialog. * @@ -326,8 +324,8 @@ public class VolumeDialogImpl implements VolumeDialog, Dumpable, private final VolumePanelFlag mVolumePanelFlag; private final VolumeDialogInteractor mInteractor; // Optional actions for soundDose - private Optional<ImmutableList<CsdWarningAction>> - mCsdWarningNotificationActions = Optional.of(ImmutableList.of()); + private Optional<List<CsdWarningAction>> + mCsdWarningNotificationActions = Optional.of(Collections.emptyList()); public VolumeDialogImpl( Context context, @@ -2237,7 +2235,7 @@ public class VolumeDialogImpl implements VolumeDialog, Dumpable, } public void setCsdWarningNotificationActionIntents( - ImmutableList<CsdWarningAction> actionIntent) { + List<CsdWarningAction> actionIntent) { mCsdWarningNotificationActions = Optional.of(actionIntent); } diff --git a/packages/SystemUI/src/com/android/systemui/volume/dagger/VolumeModule.java b/packages/SystemUI/src/com/android/systemui/volume/dagger/VolumeModule.java index 2009143859d3..94964bbafbd6 100644 --- a/packages/SystemUI/src/com/android/systemui/volume/dagger/VolumeModule.java +++ b/packages/SystemUI/src/com/android/systemui/volume/dagger/VolumeModule.java @@ -43,13 +43,13 @@ import com.android.systemui.volume.VolumePanelDialogReceiver; import com.android.systemui.volume.VolumeUI; import com.android.systemui.volume.dialog.VolumeDialogPlugin; import com.android.systemui.volume.dialog.dagger.VolumeDialogPluginComponent; +import com.android.systemui.volume.dialog.dagger.factory.VolumeDialogPluginComponentFactory; import com.android.systemui.volume.domain.interactor.VolumeDialogInteractor; import com.android.systemui.volume.domain.interactor.VolumePanelNavigationInteractor; import com.android.systemui.volume.panel.dagger.VolumePanelComponent; import com.android.systemui.volume.panel.dagger.factory.VolumePanelComponentFactory; import com.android.systemui.volume.panel.shared.flag.VolumePanelFlag; import com.android.systemui.volume.ui.navigation.VolumeNavigator; - import com.google.android.msdl.domain.MSDLPlayer; import dagger.Binds; @@ -104,6 +104,10 @@ public interface VolumeModule { @Binds VolumePanelComponentFactory bindVolumePanelComponentFactory(VolumePanelComponent.Factory impl); + @Binds + VolumeDialogPluginComponentFactory bindVolumeDialogPluginComponentFactory( + VolumeDialogPluginComponent.Factory impl); + /** */ @Provides static VolumeDialog provideVolumeDialog( diff --git a/packages/SystemUI/src/com/android/systemui/volume/dialog/VolumeDialogPlugin.kt b/packages/SystemUI/src/com/android/systemui/volume/dialog/VolumeDialogPlugin.kt index 5a69be5486a0..938e313771ad 100644 --- a/packages/SystemUI/src/com/android/systemui/volume/dialog/VolumeDialogPlugin.kt +++ b/packages/SystemUI/src/com/android/systemui/volume/dialog/VolumeDialogPlugin.kt @@ -22,9 +22,13 @@ import com.android.app.tracing.coroutines.coroutineScopeTraced import com.android.app.tracing.coroutines.launchTraced as launch import com.android.systemui.dagger.qualifiers.Application import com.android.systemui.plugins.VolumeDialog +import com.android.systemui.volume.CsdWarningAction +import com.android.systemui.volume.CsdWarningDialog import com.android.systemui.volume.SafetyWarningDialog import com.android.systemui.volume.dialog.dagger.VolumeDialogPluginComponent +import com.android.systemui.volume.dialog.dagger.factory.VolumeDialogPluginComponentFactory import com.android.systemui.volume.dialog.ui.viewmodel.VolumeDialogPluginViewModel +import java.util.Optional import javax.inject.Inject import kotlin.coroutines.resume import kotlinx.coroutines.CoroutineScope @@ -39,7 +43,8 @@ constructor( @Application private val applicationCoroutineScope: CoroutineScope, private val context: Context, private val audioManager: AudioManager, - private val volumeDialogPluginComponentFactory: VolumeDialogPluginComponent.Factory, + private val volumeDialogPluginComponentFactory: VolumeDialogPluginComponentFactory, + private val csdWarningDialogFactory: CsdWarningDialog.Factory, ) : VolumeDialog { private var job: Job? = null @@ -67,6 +72,16 @@ constructor( } } .launchIn(this) + + viewModel.csdWarning + .mapLatest { csdWarning -> + if (csdWarning != null) { + showCsdWarningDialog(csdWarning, viewModel.csdWarningConfigModel.actions) { + viewModel.onCsdWarningDismissed() + } + } + } + .launchIn(this) } override fun destroy() { @@ -86,4 +101,23 @@ constructor( dialog.show() continuation.invokeOnCancellation { dialog.dismiss() } } + + private suspend fun showCsdWarningDialog( + warning: Int, + actions: List<CsdWarningAction>, + onDismissed: () -> Unit, + ) = suspendCancellableCoroutine { continuation -> + val dialog = + csdWarningDialogFactory.create( + warning, + { + onDismissed() + continuation.resume(Unit) + }, + Optional.of(actions), + ) + + dialog.show() + continuation.invokeOnCancellation { dialog.dismiss() } + } } diff --git a/packages/SystemUI/src/com/android/systemui/volume/dialog/dagger/VolumeDialogPluginComponent.kt b/packages/SystemUI/src/com/android/systemui/volume/dialog/dagger/VolumeDialogPluginComponent.kt index 4e0098ccdf99..f0fe4a3b7ffd 100644 --- a/packages/SystemUI/src/com/android/systemui/volume/dialog/dagger/VolumeDialogPluginComponent.kt +++ b/packages/SystemUI/src/com/android/systemui/volume/dialog/dagger/VolumeDialogPluginComponent.kt @@ -16,6 +16,7 @@ package com.android.systemui.volume.dialog.dagger +import com.android.systemui.volume.dialog.dagger.factory.VolumeDialogPluginComponentFactory import com.android.systemui.volume.dialog.dagger.module.VolumeDialogPluginModule import com.android.systemui.volume.dialog.dagger.scope.VolumeDialogPlugin import com.android.systemui.volume.dialog.dagger.scope.VolumeDialogPluginScope @@ -35,9 +36,9 @@ interface VolumeDialogPluginComponent { fun viewModel(): VolumeDialogPluginViewModel @Subcomponent.Factory - interface Factory { + interface Factory : VolumeDialogPluginComponentFactory { - fun create( + override fun create( @BindsInstance @VolumeDialogPlugin scope: CoroutineScope ): VolumeDialogPluginComponent } diff --git a/packages/SystemUI/src/com/android/systemui/volume/dialog/dagger/factory/VolumeDialogPluginComponentFactory.kt b/packages/SystemUI/src/com/android/systemui/volume/dialog/dagger/factory/VolumeDialogPluginComponentFactory.kt new file mode 100644 index 000000000000..8edccd525f68 --- /dev/null +++ b/packages/SystemUI/src/com/android/systemui/volume/dialog/dagger/factory/VolumeDialogPluginComponentFactory.kt @@ -0,0 +1,26 @@ +/* + * Copyright (C) 2025 The Android Open Source Project + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +package com.android.systemui.volume.dialog.dagger.factory + +import com.android.systemui.volume.dialog.dagger.VolumeDialogPluginComponent +import kotlinx.coroutines.CoroutineScope + +/** Common interface for all dagger Subcomponent.Factory providing [VolumeDialogPluginComponent]. */ +interface VolumeDialogPluginComponentFactory { + + fun create(scope: CoroutineScope): VolumeDialogPluginComponent +} diff --git a/packages/SystemUI/src/com/android/systemui/volume/dialog/dagger/module/VolumeDialogPluginModule.kt b/packages/SystemUI/src/com/android/systemui/volume/dialog/dagger/module/VolumeDialogPluginModule.kt index cd8cdc8573bd..547c51d1cefd 100644 --- a/packages/SystemUI/src/com/android/systemui/volume/dialog/dagger/module/VolumeDialogPluginModule.kt +++ b/packages/SystemUI/src/com/android/systemui/volume/dialog/dagger/module/VolumeDialogPluginModule.kt @@ -17,13 +17,22 @@ package com.android.systemui.volume.dialog.dagger.module import com.android.systemui.volume.dialog.dagger.VolumeDialogComponent +import com.android.systemui.volume.dialog.shared.model.CsdWarningConfigModel import com.android.systemui.volume.dialog.utils.VolumeTracer import com.android.systemui.volume.dialog.utils.VolumeTracerImpl import dagger.Binds import dagger.Module +import dagger.Provides @Module(subcomponents = [VolumeDialogComponent::class]) interface VolumeDialogPluginModule { @Binds fun bindVolumeTracer(volumeTracer: VolumeTracerImpl): VolumeTracer + + companion object { + + @Provides + fun provideCsdWarningConfigModel(): CsdWarningConfigModel = + CsdWarningConfigModel(emptyList()) + } } diff --git a/packages/SystemUI/src/com/android/systemui/volume/dialog/domain/interactor/VolumeDialogCsdWarningInteractor.kt b/packages/SystemUI/src/com/android/systemui/volume/dialog/domain/interactor/VolumeDialogCsdWarningInteractor.kt new file mode 100644 index 000000000000..ef9def328d15 --- /dev/null +++ b/packages/SystemUI/src/com/android/systemui/volume/dialog/domain/interactor/VolumeDialogCsdWarningInteractor.kt @@ -0,0 +1,55 @@ +/* + * Copyright (C) 2025 The Android Open Source Project + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +package com.android.systemui.volume.dialog.domain.interactor + +import com.android.systemui.volume.dialog.dagger.scope.VolumeDialogPluginScope +import com.android.systemui.volume.dialog.shared.model.VolumeDialogCsdWarningModel +import javax.inject.Inject +import kotlinx.coroutines.ExperimentalCoroutinesApi +import kotlinx.coroutines.delay +import kotlinx.coroutines.flow.Flow +import kotlinx.coroutines.flow.flatMapLatest +import kotlinx.coroutines.flow.flow +import kotlinx.coroutines.flow.flowOf +import kotlinx.coroutines.flow.map + +@OptIn(ExperimentalCoroutinesApi::class) +@VolumeDialogPluginScope +class VolumeDialogCsdWarningInteractor +@Inject +constructor(private val stateInteractor: VolumeDialogStateInteractor) { + + /** Emits warning when the warning should be visible and null when it shouldn't */ + val csdWarning: Flow<Int?> = + stateInteractor.volumeDialogState + .map { it.isShowingCsdWarning } + .flatMapLatest { model -> + when (model) { + is VolumeDialogCsdWarningModel.Visible -> + flow { + emit(model.warning) + delay(model.duration) + emit(null) + } + is VolumeDialogCsdWarningModel.Invisible -> flowOf(null) + } + } + + fun onCsdWarningDismissed() { + stateInteractor.setCsdWarning(VolumeDialogCsdWarningModel.Invisible) + } +} diff --git a/packages/SystemUI/src/com/android/systemui/volume/dialog/domain/interactor/VolumeDialogStateInteractor.kt b/packages/SystemUI/src/com/android/systemui/volume/dialog/domain/interactor/VolumeDialogStateInteractor.kt index 26d2414acec1..b3c92f8cdbb9 100644 --- a/packages/SystemUI/src/com/android/systemui/volume/dialog/domain/interactor/VolumeDialogStateInteractor.kt +++ b/packages/SystemUI/src/com/android/systemui/volume/dialog/domain/interactor/VolumeDialogStateInteractor.kt @@ -23,10 +23,12 @@ import com.android.systemui.volume.dialog.dagger.scope.VolumeDialogPlugin import com.android.systemui.volume.dialog.dagger.scope.VolumeDialogPluginScope import com.android.systemui.volume.dialog.data.repository.VolumeDialogStateRepository import com.android.systemui.volume.dialog.domain.model.VolumeDialogEventModel +import com.android.systemui.volume.dialog.shared.model.VolumeDialogCsdWarningModel import com.android.systemui.volume.dialog.shared.model.VolumeDialogSafetyWarningModel import com.android.systemui.volume.dialog.shared.model.VolumeDialogStateModel import com.android.systemui.volume.dialog.shared.model.VolumeDialogStreamModel import javax.inject.Inject +import kotlin.time.Duration.Companion.milliseconds import kotlinx.coroutines.CoroutineScope import kotlinx.coroutines.flow.Flow import kotlinx.coroutines.flow.launchIn @@ -64,6 +66,14 @@ constructor( is VolumeDialogEventModel.ShowSafetyWarning -> { setSafetyWarning(VolumeDialogSafetyWarningModel.Visible(event.flags)) } + is VolumeDialogEventModel.ShowCsdWarning -> { + setCsdWarning( + VolumeDialogCsdWarningModel.Visible( + warning = event.csdWarning, + duration = event.durationMs.milliseconds, + ) + ) + } is VolumeDialogEventModel.SubscribedToEvents -> { volumeDialogController.getState() } @@ -81,6 +91,10 @@ constructor( volumeDialogStateRepository.updateState { it.copy(isShowingSafetyWarning = model) } } + fun setCsdWarning(model: VolumeDialogCsdWarningModel) { + volumeDialogStateRepository.updateState { it.copy(isShowingCsdWarning = model) } + } + /** Returns a copy of [model] filled with the values from [VolumeDialogController.State]. */ private fun VolumeDialogController.State.copyIntoModel( model: VolumeDialogStateModel diff --git a/packages/SystemUI/src/com/android/systemui/volume/dialog/shared/model/CsdWarningConfigModel.kt b/packages/SystemUI/src/com/android/systemui/volume/dialog/shared/model/CsdWarningConfigModel.kt new file mode 100644 index 000000000000..e6741bae6c26 --- /dev/null +++ b/packages/SystemUI/src/com/android/systemui/volume/dialog/shared/model/CsdWarningConfigModel.kt @@ -0,0 +1,21 @@ +/* + * Copyright (C) 2025 The Android Open Source Project + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +package com.android.systemui.volume.dialog.shared.model + +import com.android.systemui.volume.CsdWarningAction + +data class CsdWarningConfigModel(val actions: List<CsdWarningAction>) diff --git a/packages/SystemUI/src/com/android/systemui/volume/dialog/shared/model/VolumeDialogCsdWarningModel.kt b/packages/SystemUI/src/com/android/systemui/volume/dialog/shared/model/VolumeDialogCsdWarningModel.kt new file mode 100644 index 000000000000..219af7165534 --- /dev/null +++ b/packages/SystemUI/src/com/android/systemui/volume/dialog/shared/model/VolumeDialogCsdWarningModel.kt @@ -0,0 +1,29 @@ +/* + * Copyright (C) 2024 The Android Open Source Project + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +package com.android.systemui.volume.dialog.shared.model + +import kotlin.time.Duration + +/** Models current CSD dialog state. */ +sealed interface VolumeDialogCsdWarningModel { + + /** CSD dialog is visible and has been shown with the [warning] for the [duration]. */ + data class Visible(val warning: Int, val duration: Duration) : VolumeDialogCsdWarningModel + + /** CSD dialog is invisible. */ + data object Invisible : VolumeDialogCsdWarningModel +} diff --git a/packages/SystemUI/src/com/android/systemui/volume/dialog/shared/model/VolumeDialogStateModel.kt b/packages/SystemUI/src/com/android/systemui/volume/dialog/shared/model/VolumeDialogStateModel.kt index 838006d0adb2..89456fe2ac75 100644 --- a/packages/SystemUI/src/com/android/systemui/volume/dialog/shared/model/VolumeDialogStateModel.kt +++ b/packages/SystemUI/src/com/android/systemui/volume/dialog/shared/model/VolumeDialogStateModel.kt @@ -23,6 +23,7 @@ data class VolumeDialogStateModel( val shouldShowA11ySlider: Boolean = false, val isShowingSafetyWarning: VolumeDialogSafetyWarningModel = VolumeDialogSafetyWarningModel.Invisible, + val isShowingCsdWarning: VolumeDialogCsdWarningModel = VolumeDialogCsdWarningModel.Invisible, val streamModels: Map<Int, VolumeDialogStreamModel> = mapOf(), val ringerModeInternal: Int = 0, val ringerModeExternal: Int = 0, diff --git a/packages/SystemUI/src/com/android/systemui/volume/dialog/ui/viewmodel/VolumeDialogPluginViewModel.kt b/packages/SystemUI/src/com/android/systemui/volume/dialog/ui/viewmodel/VolumeDialogPluginViewModel.kt index e7a2cf4eff08..1765f0111e08 100644 --- a/packages/SystemUI/src/com/android/systemui/volume/dialog/ui/viewmodel/VolumeDialogPluginViewModel.kt +++ b/packages/SystemUI/src/com/android/systemui/volume/dialog/ui/viewmodel/VolumeDialogPluginViewModel.kt @@ -20,9 +20,11 @@ import com.android.systemui.volume.Events import com.android.systemui.volume.dialog.VolumeDialog import com.android.systemui.volume.dialog.dagger.scope.VolumeDialogPlugin import com.android.systemui.volume.dialog.dagger.scope.VolumeDialogPluginScope +import com.android.systemui.volume.dialog.domain.interactor.VolumeDialogCsdWarningInteractor import com.android.systemui.volume.dialog.domain.interactor.VolumeDialogSafetyWarningInteractor import com.android.systemui.volume.dialog.domain.interactor.VolumeDialogVisibilityInteractor import com.android.systemui.volume.dialog.shared.VolumeDialogLogger +import com.android.systemui.volume.dialog.shared.model.CsdWarningConfigModel import com.android.systemui.volume.dialog.shared.model.VolumeDialogVisibilityModel import javax.inject.Inject import javax.inject.Provider @@ -38,8 +40,10 @@ constructor( @VolumeDialogPlugin private val coroutineScope: CoroutineScope, private val dialogVisibilityInteractor: VolumeDialogVisibilityInteractor, private val dialogSafetyWarningInteractor: VolumeDialogSafetyWarningInteractor, + private val dialogCsdWarningInteractor: VolumeDialogCsdWarningInteractor, private val volumeDialogProvider: Provider<VolumeDialog>, private val logger: VolumeDialogLogger, + val csdWarningConfigModel: CsdWarningConfigModel, ) { fun launchVolumeDialog() { @@ -61,11 +65,16 @@ constructor( } val isShowingSafetyWarning: Flow<Boolean> = dialogSafetyWarningInteractor.isShowingSafetyWarning + val csdWarning: Flow<Int?> = dialogCsdWarningInteractor.csdWarning fun onSafetyWarningDismissed() { dialogSafetyWarningInteractor.onSafetyWarningDismissed() } + fun onCsdWarningDismissed() { + dialogCsdWarningInteractor.onCsdWarningDismissed() + } + private fun showDialog() { volumeDialogProvider .get() diff --git a/packages/SystemUI/tests/src/com/android/systemui/volume/VolumeDialogImplTest.java b/packages/SystemUI/tests/src/com/android/systemui/volume/VolumeDialogImplTest.java index 3007eabba0b8..8d05ea16cfa6 100644 --- a/packages/SystemUI/tests/src/com/android/systemui/volume/VolumeDialogImplTest.java +++ b/packages/SystemUI/tests/src/com/android/systemui/volume/VolumeDialogImplTest.java @@ -16,6 +16,7 @@ package com.android.systemui.volume; +import java.util.List; import static android.media.AudioManager.RINGER_MODE_NORMAL; import static android.media.AudioManager.RINGER_MODE_SILENT; import static android.media.AudioManager.RINGER_MODE_VIBRATE; @@ -93,7 +94,6 @@ import com.android.systemui.volume.panel.shared.flag.VolumePanelFlag; import com.android.systemui.volume.ui.navigation.VolumeNavigator; import com.google.android.msdl.domain.MSDLPlayer; -import com.google.common.collect.ImmutableList; import dagger.Lazy; @@ -163,7 +163,7 @@ public class VolumeDialogImplTest extends SysuiTestCase { new CsdWarningDialog.Factory() { @Override public CsdWarningDialog create(int warningType, Runnable onCleanup, - Optional<ImmutableList<CsdWarningAction>> actionIntents) { + Optional<List<CsdWarningAction>> actionIntents) { return mCsdWarningDialog; } }; |