Keep screen on during voice message recording (#1684)

This commit is contained in:
jonnyandrew 2023-10-30 12:37:10 +00:00 committed by GitHub
parent b1fffdc9e9
commit 6f49d689f4
5 changed files with 32 additions and 0 deletions

View file

@ -93,6 +93,7 @@ import io.element.android.libraries.designsystem.theme.components.Scaffold
import io.element.android.libraries.designsystem.theme.components.Text import io.element.android.libraries.designsystem.theme.components.Text
import io.element.android.libraries.designsystem.theme.components.TopAppBar import io.element.android.libraries.designsystem.theme.components.TopAppBar
import io.element.android.libraries.designsystem.utils.CommonDrawables import io.element.android.libraries.designsystem.utils.CommonDrawables
import io.element.android.libraries.designsystem.utils.KeepScreenOn
import io.element.android.libraries.designsystem.utils.LogCompositions import io.element.android.libraries.designsystem.utils.LogCompositions
import io.element.android.libraries.designsystem.utils.OnLifecycleEvent import io.element.android.libraries.designsystem.utils.OnLifecycleEvent
import io.element.android.libraries.designsystem.utils.snackbar.SnackbarHost import io.element.android.libraries.designsystem.utils.snackbar.SnackbarHost
@ -124,6 +125,8 @@ fun MessagesView(
state.voiceMessageComposerState.eventSink(VoiceMessageComposerEvents.LifecycleEvent(event)) state.voiceMessageComposerState.eventSink(VoiceMessageComposerEvents.LifecycleEvent(event))
} }
KeepScreenOn(state.voiceMessageComposerState.keepScreenOn)
AttachmentStateView( AttachmentStateView(
state = state.composerState.attachmentsState, state = state.composerState.attachmentsState,
onPreviewAttachments = onPreviewAttachments, onPreviewAttachments = onPreviewAttachments,

View file

@ -64,6 +64,7 @@ class VoiceMessageComposerPresenter @Inject constructor(
override fun present(): VoiceMessageComposerState { override fun present(): VoiceMessageComposerState {
val localCoroutineScope = rememberCoroutineScope() val localCoroutineScope = rememberCoroutineScope()
val recorderState by voiceRecorder.state.collectAsState(initial = VoiceRecorderState.Idle) val recorderState by voiceRecorder.state.collectAsState(initial = VoiceRecorderState.Idle)
val keepScreenOn by remember { derivedStateOf { recorderState is VoiceRecorderState.Recording } }
val permissionState = permissionsPresenter.present() val permissionState = permissionsPresenter.present()
var isSending by remember { mutableStateOf(false) } var isSending by remember { mutableStateOf(false) }
@ -191,6 +192,7 @@ class VoiceMessageComposerPresenter @Inject constructor(
else -> VoiceMessageState.Idle else -> VoiceMessageState.Idle
}, },
showPermissionRationaleDialog = permissionState.showDialog, showPermissionRationaleDialog = permissionState.showDialog,
keepScreenOn = keepScreenOn,
eventSink = handleEvents, eventSink = handleEvents,
) )
} }

View file

@ -23,6 +23,7 @@ import io.element.android.libraries.textcomposer.model.VoiceMessageState
data class VoiceMessageComposerState( data class VoiceMessageComposerState(
val voiceMessageState: VoiceMessageState, val voiceMessageState: VoiceMessageState,
val showPermissionRationaleDialog: Boolean, val showPermissionRationaleDialog: Boolean,
val keepScreenOn: Boolean,
val eventSink: (VoiceMessageComposerEvents) -> Unit, val eventSink: (VoiceMessageComposerEvents) -> Unit,
) )

View file

@ -30,10 +30,12 @@ internal open class VoiceMessageComposerStateProvider : PreviewParameterProvider
internal fun aVoiceMessageComposerState( internal fun aVoiceMessageComposerState(
voiceMessageState: VoiceMessageState = VoiceMessageState.Idle, voiceMessageState: VoiceMessageState = VoiceMessageState.Idle,
keepScreenOn: Boolean = false,
showPermissionRationaleDialog: Boolean = false, showPermissionRationaleDialog: Boolean = false,
) = VoiceMessageComposerState( ) = VoiceMessageComposerState(
voiceMessageState = voiceMessageState, voiceMessageState = voiceMessageState,
showPermissionRationaleDialog = showPermissionRationaleDialog, showPermissionRationaleDialog = showPermissionRationaleDialog,
keepScreenOn = keepScreenOn,
eventSink = {}, eventSink = {},
) )

View file

@ -101,6 +101,30 @@ class VoiceMessageComposerPresenterTest {
} }
} }
@Test
fun `present - recording keeps screen on`() = runTest {
val presenter = createVoiceMessageComposerPresenter()
moleculeFlow(RecompositionMode.Immediate) {
presenter.present()
}.test {
awaitItem().apply {
eventSink(VoiceMessageComposerEvents.RecordButtonEvent(PressEvent.PressStart))
assertThat(keepScreenOn).isFalse()
}
awaitItem().apply {
assertThat(keepScreenOn).isTrue()
eventSink(VoiceMessageComposerEvents.RecordButtonEvent(PressEvent.LongPressEnd))
}
val finalState = awaitItem().apply {
assertThat(keepScreenOn).isFalse()
}
testPauseAndDestroy(finalState)
}
}
@Test @Test
fun `present - abort recording`() = runTest { fun `present - abort recording`() = runTest {
val presenter = createVoiceMessageComposerPresenter() val presenter = createVoiceMessageComposerPresenter()