From ff0417b7e7545a97fe6e4e800dc9f16c98a73a5a Mon Sep 17 00:00:00 2001 From: Damontecres Date: Mon, 2 Mar 2026 16:53:27 -0500 Subject: [PATCH] Move buttons to new composable --- .../ui/detail/music/NowPlayingButtons.kt | 108 ++++++++++++++++++ .../ui/detail/music/NowPlayingOverlay.kt | 71 +----------- .../wholphin/ui/playback/PlaybackControls.kt | 2 +- 3 files changed, 115 insertions(+), 66 deletions(-) create mode 100644 app/src/main/java/com/github/damontecres/wholphin/ui/detail/music/NowPlayingButtons.kt diff --git a/app/src/main/java/com/github/damontecres/wholphin/ui/detail/music/NowPlayingButtons.kt b/app/src/main/java/com/github/damontecres/wholphin/ui/detail/music/NowPlayingButtons.kt new file mode 100644 index 00000000..41880198 --- /dev/null +++ b/app/src/main/java/com/github/damontecres/wholphin/ui/detail/music/NowPlayingButtons.kt @@ -0,0 +1,108 @@ +package com.github.damontecres.wholphin.ui.detail.music + +import androidx.annotation.OptIn +import androidx.compose.foundation.layout.Arrangement +import androidx.compose.foundation.layout.Box +import androidx.compose.foundation.layout.Row +import androidx.compose.runtime.Composable +import androidx.compose.ui.Alignment +import androidx.compose.ui.Modifier +import androidx.compose.ui.focus.FocusRequester +import androidx.compose.ui.graphics.Color +import androidx.media3.common.Player +import androidx.media3.common.util.UnstableApi +import androidx.media3.ui.compose.state.rememberNextButtonState +import androidx.media3.ui.compose.state.rememberPlayPauseButtonState +import androidx.media3.ui.compose.state.rememberPreviousButtonState +import androidx.media3.ui.compose.state.rememberRepeatButtonState +import androidx.media3.ui.compose.state.rememberShuffleButtonState +import androidx.tv.material3.MaterialTheme +import com.github.damontecres.wholphin.R +import com.github.damontecres.wholphin.ui.playback.ControllerViewState +import com.github.damontecres.wholphin.ui.playback.PlaybackAction +import com.github.damontecres.wholphin.ui.playback.PlaybackButtons +import com.github.damontecres.wholphin.ui.playback.PlaybackFaButton +import com.github.damontecres.wholphin.ui.playback.buttonSpacing +import kotlin.time.Duration.Companion.seconds + +@OptIn(UnstableApi::class) +@Composable +fun NowPlayingButtons( + player: Player, + controllerViewState: ControllerViewState, + initialFocusRequester: FocusRequester, + modifier: Modifier = Modifier, +) { + val playPauseState = rememberPlayPauseButtonState(player) + val previousState = rememberPreviousButtonState(player) + val nextState = rememberNextButtonState(player) + val shuffleState = rememberShuffleButtonState(player) + val repeatState = rememberRepeatButtonState(player) + Box( + modifier = modifier, + ) { + PlaybackButtons( + player = player, + initialFocusRequester = initialFocusRequester, + onControllerInteraction = { controllerViewState.pulseControls() }, + onPlaybackActionClick = { + when (it) { + PlaybackAction.Next -> { + nextState.onClick() + } + + PlaybackAction.Previous -> { + previousState.onClick() + } + + is PlaybackAction.ToggleCaptions -> { + TODO() + } + + else -> {} + } + }, + showPlay = playPauseState.showPlay, + previousEnabled = previousState.isEnabled, + nextEnabled = nextState.isEnabled, + seekBack = 10.seconds, + skipBackOnResume = null, + seekForward = 30.seconds, // TODO + modifier = Modifier.align(Alignment.Center), + ) + Row( + horizontalArrangement = Arrangement.spacedBy(buttonSpacing), + modifier = Modifier.align(Alignment.CenterEnd), + ) { + PlaybackFaButton( + iconRes = R.string.fa_shuffle, + onClick = { + shuffleState.onClick() + }, + onControllerInteraction = { controllerViewState.pulseControls() }, + textColor = + if (shuffleState.shuffleOn) { + MaterialTheme.colorScheme.secondary + } else { + Color.Unspecified + }, + ) + PlaybackFaButton( + iconRes = R.string.fa_repeat, + onClick = { + repeatState.onClick() + }, + onControllerInteraction = { controllerViewState.pulseControls() }, + textColor = + when (repeatState.repeatModeState) { + Player.REPEAT_MODE_ALL -> MaterialTheme.colorScheme.secondary + + // TODO + Player.REPEAT_MODE_ONE -> MaterialTheme.colorScheme.tertiary + + else -> Color.Unspecified + }, + ) + } + } +} diff --git a/app/src/main/java/com/github/damontecres/wholphin/ui/detail/music/NowPlayingOverlay.kt b/app/src/main/java/com/github/damontecres/wholphin/ui/detail/music/NowPlayingOverlay.kt index 35a9a37d..59de5279 100644 --- a/app/src/main/java/com/github/damontecres/wholphin/ui/detail/music/NowPlayingOverlay.kt +++ b/app/src/main/java/com/github/damontecres/wholphin/ui/detail/music/NowPlayingOverlay.kt @@ -33,7 +33,6 @@ import androidx.compose.ui.Modifier import androidx.compose.ui.focus.FocusRequester import androidx.compose.ui.focus.focusRequester import androidx.compose.ui.focus.onFocusChanged -import androidx.compose.ui.graphics.Color import androidx.compose.ui.res.stringResource import androidx.compose.ui.unit.dp import androidx.media3.common.Player @@ -50,16 +49,12 @@ import com.github.damontecres.wholphin.data.model.AudioItem import com.github.damontecres.wholphin.ui.ifElse import com.github.damontecres.wholphin.ui.main.settings.MoveDirection import com.github.damontecres.wholphin.ui.playback.ControllerViewState -import com.github.damontecres.wholphin.ui.playback.PlaybackAction -import com.github.damontecres.wholphin.ui.playback.PlaybackButtons -import com.github.damontecres.wholphin.ui.playback.PlaybackFaButton import com.github.damontecres.wholphin.ui.playback.SeekBar import com.github.damontecres.wholphin.ui.preferences.MoveButton import com.github.damontecres.wholphin.ui.roundSeconds import com.github.damontecres.wholphin.ui.tryRequestFocus import kotlinx.coroutines.launch import kotlin.time.Duration -import kotlin.time.Duration.Companion.seconds @OptIn(UnstableApi::class) @Composable @@ -133,69 +128,15 @@ fun NowPlayingOverlay( Modifier .align(Alignment.CenterHorizontally), ) { - Row( + NowPlayingButtons( + player = player, + controllerViewState = controllerViewState, + initialFocusRequester = focusRequester, modifier = Modifier + .fillMaxWidth() .align(Alignment.CenterHorizontally), - ) { - PlaybackButtons( - player = player, - initialFocusRequester = focusRequester, - onControllerInteraction = { controllerViewState.pulseControls() }, - onPlaybackActionClick = { - when (it) { - PlaybackAction.Next -> { - nextState.onClick() - } - - PlaybackAction.Previous -> { - previousState.onClick() - } - - is PlaybackAction.ToggleCaptions -> { - TODO() - } - - else -> {} - } - }, - showPlay = playPauseState.showPlay, - previousEnabled = previousState.isEnabled, - nextEnabled = nextState.isEnabled, - seekBack = 10.seconds, - skipBackOnResume = null, - seekForward = 30.seconds, // TODO - ) - PlaybackFaButton( - iconRes = R.string.fa_shuffle, - onClick = { - shuffleState.onClick() - }, - onControllerInteraction = { controllerViewState.pulseControls() }, - textColor = - if (shuffleState.shuffleOn) { - MaterialTheme.colorScheme.secondary - } else { - Color.Unspecified - }, - ) - PlaybackFaButton( - iconRes = R.string.fa_repeat, - onClick = { - repeatState.onClick() - }, - onControllerInteraction = { controllerViewState.pulseControls() }, - textColor = - when (repeatState.repeatModeState) { - Player.REPEAT_MODE_ALL -> MaterialTheme.colorScheme.secondary - - // TODO - Player.REPEAT_MODE_ONE -> MaterialTheme.colorScheme.tertiary - - else -> Color.Unspecified - }, - ) - } + ) } if (queue.isEmpty()) { Text("No items") diff --git a/app/src/main/java/com/github/damontecres/wholphin/ui/playback/PlaybackControls.kt b/app/src/main/java/com/github/damontecres/wholphin/ui/playback/PlaybackControls.kt index 417702e1..d9fd9640 100644 --- a/app/src/main/java/com/github/damontecres/wholphin/ui/playback/PlaybackControls.kt +++ b/app/src/main/java/com/github/damontecres/wholphin/ui/playback/PlaybackControls.kt @@ -290,7 +290,7 @@ fun SeekBar( } } -private val buttonSpacing = 12.dp +val buttonSpacing = 12.dp @Composable fun LeftPlaybackButtons(