Merge pull request #998 from Bnyro/master

previous and next buttons for the player
This commit is contained in:
Bnyro 2022-08-08 17:25:39 +02:00 committed by GitHub
commit 45b10393e3
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
9 changed files with 100 additions and 19 deletions

View File

@ -164,6 +164,7 @@ class PlayerFragment : BaseFragment() {
private var defaultSubtitleCode = ""
private var sponsorBlockEnabled = true
private var sponsorBlockNotifications = true
private var skipButtonsEnabled = false
/**
* for autoplay
@ -176,6 +177,11 @@ class PlayerFragment : BaseFragment() {
*/
private lateinit var nowPlayingNotification: NowPlayingNotification
/**
* history of played videos in the current lifecycle
*/
val videoIds = mutableListOf<String>()
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
arguments?.let {
@ -204,7 +210,7 @@ class PlayerFragment : BaseFragment() {
setUserPrefs()
if (autoplayEnabled == true) playerBinding.autoplayIV.setImageResource(R.drawable.ic_toggle_on)
if (autoplayEnabled) playerBinding.autoplayIV.setImageResource(R.drawable.ic_toggle_on)
val mainActivity = activity as MainActivity
if (autoRotationEnabled) {
@ -314,6 +320,11 @@ class PlayerFragment : BaseFragment() {
if (defaultSubtitleCode.contains("-")) {
defaultSubtitleCode = defaultSubtitleCode.split("-")[0]
}
skipButtonsEnabled = PreferenceHelper.getBoolean(
PreferenceKeys.SKIP_BUTTONS,
false
)
}
private fun initializeTransitionLayout() {
@ -566,8 +577,6 @@ class PlayerFragment : BaseFragment() {
playerBinding.fullscreen.setImageResource(R.drawable.ic_fullscreen_exit)
playerBinding.exoTitle.visibility = View.VISIBLE
scaleControls(1.3F)
val mainActivity = activity as MainActivity
if (!autoRotationEnabled) {
// different orientations of the video are only available when auto rotation is disabled
@ -602,8 +611,6 @@ class PlayerFragment : BaseFragment() {
playerBinding.fullscreen.setImageResource(R.drawable.ic_fullscreen)
playerBinding.exoTitle.visibility = View.INVISIBLE
scaleControls(1F)
if (!autoRotationEnabled) {
// switch back to portrait mode if auto rotation disabled
val mainActivity = activity as MainActivity
@ -613,11 +620,6 @@ class PlayerFragment : BaseFragment() {
Globals.IS_FULL_SCREEN = false
}
private fun scaleControls(scaleFactor: Float) {
playerBinding.exoPlayPause.scaleX = scaleFactor
playerBinding.exoPlayPause.scaleY = scaleFactor
}
private fun toggleDescription() {
if (binding.descLinLayout.isVisible) {
// hide the description and chapters
@ -746,6 +748,7 @@ class PlayerFragment : BaseFragment() {
}
}
}
videoIds += videoId!!
}
run()
}
@ -754,7 +757,18 @@ class PlayerFragment : BaseFragment() {
* set the videoId of the next stream for autoplay
*/
private fun setNextStream() {
nextStreamId = streams.relatedStreams!![0].url.toID()
// don't play a video if it got played before already
var index = 0
while (nextStreamId == null || nextStreamId == videoId!! ||
(
videoIds.contains(nextStreamId) &&
videoIds.indexOf(videoId) > videoIds.indexOf(nextStreamId)
)
) {
nextStreamId = streams.relatedStreams!![index].url.toID()
if (index + 1 < streams.relatedStreams!!.size) index += 1
else break
}
if (playlistId == null) return
if (!this::autoPlayHelper.isInitialized) autoPlayHelper = AutoPlayHelper(playlistId!!)
// search for the next videoId in the playlist
@ -823,17 +837,16 @@ class PlayerFragment : BaseFragment() {
// used for autoplay and skipping to next video
private fun playNextVideo() {
if (nextStreamId == null) return
// check whether there is a new video in the queue
// by making sure that the next and the current video aren't the same
saveWatchPosition()
// forces the comments to reload for the new video
commentsLoaded = false
binding.commentsRecView.adapter = null
if (videoId != nextStreamId) {
// save the id of the next stream as videoId and load the next video
videoId = nextStreamId
playVideo()
}
// save the id of the next stream as videoId and load the next video
videoId = nextStreamId
playVideo()
}
private fun prepareExoPlayerView() {
@ -882,7 +895,7 @@ class PlayerFragment : BaseFragment() {
}
// duration that's not greater than 0 indicates that the video is live
if (!(response.duration!! > 0)) {
if (response.duration!! <= 0) {
isLive = true
handleLiveVideo()
}
@ -1052,6 +1065,22 @@ class PlayerFragment : BaseFragment() {
Toast.makeText(context, R.string.login_first, Toast.LENGTH_SHORT).show()
}
}
// next and previous buttons
playerBinding.skipPrev.visibility = if (
skipButtonsEnabled && videoIds.indexOf(videoId!!) != 0
) View.VISIBLE else View.INVISIBLE
playerBinding.skipNext.visibility = if (skipButtonsEnabled) View.VISIBLE else View.INVISIBLE
playerBinding.skipPrev.setOnClickListener {
val index = videoIds.indexOf(videoId!!) - 1
videoId = videoIds[index]
playVideo()
}
playerBinding.skipNext.setOnClickListener {
playNextVideo()
}
}
private fun enableDoubleTapToSeek() {

View File

@ -58,6 +58,7 @@ object PreferenceKeys {
const val PLAYER_AUDIO_FORMAT = "player_audio_format"
const val PLAYER_AUDIO_QUALITY = "player_audio_quality"
const val DEFAULT_SUBTITLE = "default_subtitle"
const val SKIP_BUTTONS = "skip_buttons"
/**
* Download

View File

@ -0,0 +1,10 @@
<vector xmlns:android="http://schemas.android.com/apk/res/android"
android:width="24dp"
android:height="24dp"
android:tint="?attr/colorControlNormal"
android:viewportWidth="24"
android:viewportHeight="24">
<path
android:fillColor="@android:color/white"
android:pathData="M6,18l8.5,-6L6,6v12zM16,6v12h2V6h-2z" />
</vector>

View File

@ -0,0 +1,10 @@
<vector xmlns:android="http://schemas.android.com/apk/res/android"
android:width="24dp"
android:height="24dp"
android:tint="?attr/colorControlNormal"
android:viewportWidth="24"
android:viewportHeight="24">
<path
android:fillColor="@android:color/white"
android:pathData="M6,6h2v12L6,18zM9.5,12l8.5,6L18,6z" />
</vector>

View File

@ -19,7 +19,6 @@
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_gravity="center"
android:layout_marginStart="30dp"
android:visibility="invisible">
<ImageView
@ -61,7 +60,6 @@
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_gravity="center"
android:layout_marginEnd="30dp"
android:visibility="invisible">
<ImageView

View File

@ -291,12 +291,28 @@
android:gravity="center"
android:padding="20dp">
<ImageView
android:id="@+id/skip_prev"
style="@style/PlayerControlCenter"
android:background="?android:selectableItemBackgroundBorderless"
android:src="@drawable/ic_prev"
android:visibility="invisible"
app:tint="@android:color/white" />
<ImageButton
android:id="@id/exo_play_pause"
style="@style/ExoStyledControls.Button.Center.PlayPause"
android:background="?android:selectableItemBackgroundBorderless"
app:tint="@android:color/white" />
<ImageView
android:id="@+id/skip_next"
style="@style/PlayerControlCenter"
android:background="?android:selectableItemBackgroundBorderless"
android:src="@drawable/ic_next"
android:visibility="invisible"
app:tint="@android:color/white" />
</LinearLayout>
</merge>

View File

@ -292,4 +292,6 @@
<string name="downloadsucceeded">Download succeeded</string>
<string name="share_with_time">Share with start time</string>
<string name="export_subscriptions">Export Subscriptions</string>
<string name="skip_buttons">Skip buttons</string>
<string name="skip_buttons_summary">Show buttons to skip to the next or previous video.</string>
</resources>

View File

@ -107,6 +107,14 @@
</style>
<style name="PlayerControlCenter">
<item name="android:layout_width">42dp</item>
<item name="android:layout_height">42dp</item>
<item name="android:backgroundTint">@android:color/white</item>
<item name="android:layout_marginStart">10dp</item>
<item name="android:layout_marginEnd">10dp</item>
</style>
<style name="PlayerControlTop">
<item name="android:padding">9dp</item>

View File

@ -77,6 +77,13 @@
app:key="default_subtitle"
app:title="@string/default_subtitle_language" />
<SwitchPreferenceCompat
android:defaultValue="false"
android:icon="@drawable/ic_next"
android:summary="@string/skip_buttons_summary"
app:key="skip_buttons"
app:title="@string/skip_buttons" />
</PreferenceCategory>
<PreferenceCategory app:title="@string/behavior">