From ebc2ed7dc90061f7f7a0f018ce57494d552df8ea Mon Sep 17 00:00:00 2001 From: Eugene Date: Tue, 23 Jun 2026 19:05:35 +0300 Subject: [PATCH] automatically hide player buttons on android tv --- .../videoplayer/ui/DefaultControls.kt | 8 ++++++-- .../videoplayer/ui/VideoPlayer.kt | 19 +++++++++++++++---- 2 files changed, 21 insertions(+), 6 deletions(-) diff --git a/libs/video-player/src/commonMain/kotlin/ru/shadowsparky/videoplayer/ui/DefaultControls.kt b/libs/video-player/src/commonMain/kotlin/ru/shadowsparky/videoplayer/ui/DefaultControls.kt index b511190..c5ec294 100644 --- a/libs/video-player/src/commonMain/kotlin/ru/shadowsparky/videoplayer/ui/DefaultControls.kt +++ b/libs/video-player/src/commonMain/kotlin/ru/shadowsparky/videoplayer/ui/DefaultControls.kt @@ -68,7 +68,7 @@ import ru.shadowsparky.videoplayer.PlayerState private const val DEF_SEEK_TIME = 10L @Composable -fun DefaultControls( +fun DefaultControls( state: PlayerState, controlsState: ControlsState, controller: PlayerController, @@ -382,6 +382,11 @@ private fun BoxScope.CenterControls( style = MaterialTheme.typography.bodyMedium ) } + LaunchedEffect(null) { + delay(1_000) + val result = focusContainer.play.requestFocus() + println("DefaultControls focus changed? $result") + } } } } @@ -421,7 +426,6 @@ private fun formatDuration(millis: Long): String { private class FocusContainer( val audioTrack: FocusRequester = FocusRequester(), - val audioTrackContainer: FocusRequester = FocusRequester(), val lock: FocusRequester = FocusRequester(), val prev: FocusRequester = FocusRequester(), val play: FocusRequester = FocusRequester(), diff --git a/libs/video-player/src/commonMain/kotlin/ru/shadowsparky/videoplayer/ui/VideoPlayer.kt b/libs/video-player/src/commonMain/kotlin/ru/shadowsparky/videoplayer/ui/VideoPlayer.kt index 610a0e4..4acf0a9 100644 --- a/libs/video-player/src/commonMain/kotlin/ru/shadowsparky/videoplayer/ui/VideoPlayer.kt +++ b/libs/video-player/src/commonMain/kotlin/ru/shadowsparky/videoplayer/ui/VideoPlayer.kt @@ -9,6 +9,7 @@ import androidx.compose.animation.fadeIn import androidx.compose.animation.fadeOut import androidx.compose.foundation.background import androidx.compose.foundation.clickable +import androidx.compose.foundation.focusable import androidx.compose.foundation.layout.Arrangement import androidx.compose.foundation.layout.Box import androidx.compose.foundation.layout.Column @@ -30,6 +31,9 @@ import androidx.compose.runtime.setValue import androidx.compose.ui.Alignment import androidx.compose.ui.Modifier import androidx.compose.ui.graphics.Color +import androidx.compose.ui.input.key.KeyEventType +import androidx.compose.ui.input.key.onKeyEvent +import androidx.compose.ui.input.key.type import androidx.compose.ui.unit.dp import kotlinx.coroutines.CoroutineScope import kotlinx.coroutines.delay @@ -58,6 +62,7 @@ fun VideoPlayer( } var areControlsVisible by remember { mutableStateOf(true) } var lastErrorMessage by remember { mutableStateOf(null) } + var interactionCount by remember { mutableStateOf(0) } LaunchedEffect(controller) { controller.events.collect { event -> @@ -79,15 +84,21 @@ fun VideoPlayer( } } - LaunchedEffect(areControlsVisible, state.isPlaying, lastErrorMessage) { - if (areControlsVisible && state.isPlaying && lastErrorMessage == null && !isTv) { - delay(3000) + LaunchedEffect(areControlsVisible, state.isPlaying, lastErrorMessage, interactionCount) { + if (areControlsVisible && state.isPlaying && lastErrorMessage == null) { + delay(5000) areControlsVisible = false } } val rootModifier = if (isTv) { - modifier + modifier.focusable(enabled = !areControlsVisible).onKeyEvent { + if (it.type == KeyEventType.KeyUp) { + areControlsVisible = true + interactionCount++ + } + false + } } else { modifier.clickable { areControlsVisible = !areControlsVisible