Merge pull request #6821 from Bnyro/master

feat: reuse existing player when selecting other video while playing
This commit is contained in:
Bnyro 2024-11-24 14:28:48 +01:00 committed by GitHub
commit 386f45044c
No known key found for this signature in database
GPG Key ID: B5690EEEBB952194
8 changed files with 65 additions and 24 deletions

View File

@ -6,11 +6,13 @@ import android.content.Intent
import android.os.Handler import android.os.Handler
import android.os.Looper import android.os.Looper
import android.os.Process import android.os.Process
import androidx.annotation.OptIn
import androidx.core.content.getSystemService import androidx.core.content.getSystemService
import androidx.core.os.bundleOf import androidx.core.os.bundleOf
import androidx.core.os.postDelayed import androidx.core.os.postDelayed
import androidx.fragment.app.commitNow import androidx.fragment.app.commitNow
import androidx.fragment.app.replace import androidx.fragment.app.replace
import androidx.media3.common.util.UnstableApi
import com.github.libretube.NavDirections import com.github.libretube.NavDirections
import com.github.libretube.R import com.github.libretube.R
import com.github.libretube.constants.IntentData import com.github.libretube.constants.IntentData
@ -61,30 +63,56 @@ object NavigationHelper {
if (videoUrlOrId == null) return if (videoUrlOrId == null) return
if (PreferenceHelper.getBoolean(PreferenceKeys.AUDIO_ONLY_MODE, false) && !forceVideo) { if (PreferenceHelper.getBoolean(PreferenceKeys.AUDIO_ONLY_MODE, false) && !forceVideo) {
BackgroundHelper.playOnBackground( navigateAudio(context, videoUrlOrId.toID(), playlistId, channelId, keepQueue, timestamp)
context,
videoUrlOrId.toID(),
timestamp,
playlistId,
channelId,
keepQueue
)
handler.postDelayed(500) {
startAudioPlayer(context)
}
return return
} }
val activity = ContextHelper.unwrapActivity<MainActivity>(context)
val attachedToRunningPlayer = activity.runOnPlayerFragment {
this.playNextVideo(videoUrlOrId.toID())
true
}
if (attachedToRunningPlayer) return
val playerData = val playerData =
PlayerData(videoUrlOrId.toID(), playlistId, channelId, keepQueue, timestamp) PlayerData(videoUrlOrId.toID(), playlistId, channelId, keepQueue, timestamp)
val bundle = bundleOf(IntentData.playerData to playerData) val bundle = bundleOf(IntentData.playerData to playerData)
val activity = ContextHelper.unwrapActivity<MainActivity>(context)
activity.supportFragmentManager.commitNow { activity.supportFragmentManager.commitNow {
replace<PlayerFragment>(R.id.container, args = bundle) replace<PlayerFragment>(R.id.container, args = bundle)
} }
} }
@OptIn(UnstableApi::class)
fun navigateAudio(
context: Context,
videoId: String,
playlistId: String? = null,
channelId: String? = null,
keepQueue: Boolean = false,
timestamp: Long = 0,
minimizeByDefault: Boolean = false
) {
val activity = ContextHelper.unwrapActivity<MainActivity>(context)
val attachedToRunningPlayer = activity.runOnAudioPlayerFragment {
this.playNextVideo(videoId)
true
}
if (attachedToRunningPlayer) return
BackgroundHelper.playOnBackground(
context,
videoId,
timestamp,
playlistId,
channelId,
keepQueue
)
handler.postDelayed(500) {
openAudioPlayerFragment(context, minimizeByDefault = minimizeByDefault)
}
}
fun navigatePlaylist(context: Context, playlistUrlOrId: String?, playlistType: PlaylistType) { fun navigatePlaylist(context: Context, playlistUrlOrId: String?, playlistType: PlaylistType) {
if (playlistUrlOrId == null) return if (playlistUrlOrId == null) return
@ -97,7 +125,11 @@ object NavigationHelper {
/** /**
* Start the audio player fragment * Start the audio player fragment
*/ */
fun startAudioPlayer(context: Context, offlinePlayer: Boolean = false, minimizeByDefault: Boolean = false) { fun openAudioPlayerFragment(
context: Context,
offlinePlayer: Boolean = false,
minimizeByDefault: Boolean = false
) {
val activity = ContextHelper.unwrapActivity<BaseActivity>(context) val activity = ContextHelper.unwrapActivity<BaseActivity>(context)
activity.supportFragmentManager.commitNow { activity.supportFragmentManager.commitNow {
val args = bundleOf( val args = bundleOf(

View File

@ -468,7 +468,7 @@ class MainActivity : BaseActivity() {
if (intent?.getBooleanExtra(IntentData.openAudioPlayer, false) == true) { if (intent?.getBooleanExtra(IntentData.openAudioPlayer, false) == true) {
val offlinePlayer = intent!!.getBooleanExtra(IntentData.offlinePlayer, false) val offlinePlayer = intent!!.getBooleanExtra(IntentData.offlinePlayer, false)
NavigationHelper.startAudioPlayer(this, offlinePlayer = offlinePlayer) NavigationHelper.openAudioPlayerFragment(this, offlinePlayer = offlinePlayer)
return return
} }
@ -639,10 +639,17 @@ class MainActivity : BaseActivity() {
* Attempt to run code on the player fragment if running * Attempt to run code on the player fragment if running
* Returns true if a running player fragment was found and the action got consumed, else false * Returns true if a running player fragment was found and the action got consumed, else false
*/ */
private fun runOnPlayerFragment(action: PlayerFragment.() -> Boolean): Boolean { fun runOnPlayerFragment(action: PlayerFragment.() -> Boolean): Boolean {
return supportFragmentManager.fragments.filterIsInstance<PlayerFragment>() return supportFragmentManager.fragments.filterIsInstance<PlayerFragment>()
.firstOrNull() .firstOrNull()
?.let(action) ?.let(action)
?: false ?: false
} }
fun runOnAudioPlayerFragment(action: AudioPlayerFragment.() -> Boolean): Boolean {
return supportFragmentManager.fragments.filterIsInstance<AudioPlayerFragment>()
.firstOrNull()
?.let(action)
?: false
}
} }

View File

@ -69,7 +69,7 @@ class NoInternetActivity : BaseActivity() {
super.onNewIntent(intent) super.onNewIntent(intent)
if (intent.getBooleanExtra(IntentData.openAudioPlayer, false)) { if (intent.getBooleanExtra(IntentData.openAudioPlayer, false)) {
NavigationHelper.startAudioPlayer(this, offlinePlayer = true) NavigationHelper.openAudioPlayerFragment(this, offlinePlayer = true)
} }
} }
} }

View File

@ -114,7 +114,7 @@ class DownloadsAdapter(
root.context.startActivity(intent) root.context.startActivity(intent)
} else { } else {
BackgroundHelper.playOnBackgroundOffline(root.context, download.videoId, downloadTab) BackgroundHelper.playOnBackgroundOffline(root.context, download.videoId, downloadTab)
NavigationHelper.startAudioPlayer(root.context, offlinePlayer = true) NavigationHelper.openAudioPlayerFragment(root.context, offlinePlayer = true)
} }
} }

View File

@ -252,6 +252,10 @@ class AudioPlayerFragment : Fragment(), AudioPlayerOptions {
} }
} }
fun playNextVideo(videoId: String) {
playerController?.navigateVideo(videoId)
}
@SuppressLint("ClickableViewAccessibility") @SuppressLint("ClickableViewAccessibility")
private fun initializeTransitionLayout() { private fun initializeTransitionLayout() {
if (mainActivity == null) return if (mainActivity == null) return

View File

@ -247,7 +247,7 @@ class DownloadsFragmentPage : DynamicLayoutManagerFragment() {
shuffle = true shuffle = true
) )
NavigationHelper.startAudioPlayer(requireContext(), offlinePlayer = true) NavigationHelper.openAudioPlayerFragment(requireContext(), offlinePlayer = true)
} }
} }

View File

@ -749,7 +749,7 @@ class PlayerFragment : Fragment(), OnlinePlayerOptions {
keepVideoPlayerAlive = true keepVideoPlayerAlive = true
) )
killPlayerFragment() killPlayerFragment()
NavigationHelper.startAudioPlayer(requireContext()) NavigationHelper.openAudioPlayerFragment(requireContext())
} }
private fun updateFullscreenOrientation() { private fun updateFullscreenOrientation() {
@ -1020,7 +1020,7 @@ class PlayerFragment : Fragment(), OnlinePlayerOptions {
/** /**
* Manually skip to another video. * Manually skip to another video.
*/ */
private fun playNextVideo(nextId: String) { fun playNextVideo(nextId: String) {
playerController.sendCustomCommand( playerController.sendCustomCommand(
AbstractPlayerService.runPlayerActionCommand, AbstractPlayerService.runPlayerActionCommand,
bundleOf(PlayerCommand.PLAY_VIDEO_BY_ID.name to nextId) bundleOf(PlayerCommand.PLAY_VIDEO_BY_ID.name to nextId)

View File

@ -14,7 +14,6 @@ import com.github.libretube.db.obj.WatchPosition
import com.github.libretube.enums.ShareObjectType import com.github.libretube.enums.ShareObjectType
import com.github.libretube.extensions.parcelable import com.github.libretube.extensions.parcelable
import com.github.libretube.extensions.toID import com.github.libretube.extensions.toID
import com.github.libretube.helpers.BackgroundHelper
import com.github.libretube.helpers.DownloadHelper import com.github.libretube.helpers.DownloadHelper
import com.github.libretube.helpers.NavigationHelper import com.github.libretube.helpers.NavigationHelper
import com.github.libretube.helpers.PlayerHelper import com.github.libretube.helpers.PlayerHelper
@ -58,8 +57,7 @@ class VideoOptionsBottomSheet : BaseBottomSheet() {
when (optionsList[which]) { when (optionsList[which]) {
// Start the background mode // Start the background mode
R.string.playOnBackground -> { R.string.playOnBackground -> {
BackgroundHelper.playOnBackground(requireContext(), videoId) NavigationHelper.navigateAudio(requireContext(), videoId, minimizeByDefault = true)
NavigationHelper.startAudioPlayer(requireContext(), minimizeByDefault = true)
} }
// Add Video to Playlist Dialog // Add Video to Playlist Dialog
R.string.addToPlaylist -> { R.string.addToPlaylist -> {