Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Playlist Options Dialog + Clone Playlist Option #583

Merged
merged 4 commits into from
Jun 20, 2022
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Original file line number Diff line number Diff line change
Expand Up @@ -21,7 +21,8 @@ import com.github.libretube.obj.StreamItem
import com.github.libretube.util.RetrofitInstance
import com.squareup.picasso.Picasso
import java.io.IOException
import kotlinx.coroutines.GlobalScope
import kotlinx.coroutines.CoroutineScope
import kotlinx.coroutines.Dispatchers
import kotlinx.coroutines.launch
import retrofit2.HttpException

Expand Down Expand Up @@ -92,7 +93,7 @@ class PlaylistAdapter(

private fun removeFromPlaylist(token: String, position: Int) {
fun run() {
GlobalScope.launch {
CoroutineScope(Dispatchers.IO).launch {
val response = try {
RetrofitInstance.api.removeFromPlaylist(
token,
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -13,6 +13,7 @@ import androidx.fragment.app.FragmentManager
import androidx.recyclerview.widget.RecyclerView
import com.github.libretube.MainActivity
import com.github.libretube.R
import com.github.libretube.dialogs.PlaylistOptionsDialog
import com.github.libretube.dialogs.VideoOptionsDialog
import com.github.libretube.fragments.PlayerFragment
import com.github.libretube.obj.SearchItem
Expand Down Expand Up @@ -153,6 +154,12 @@ class SearchViewHolder(
val bundle = bundleOf("playlist_id" to item.url)
activity.navController.navigate(R.id.playlistFragment, bundle)
}
v.setOnLongClickListener {
val playlistId = item.url!!.replace("/playlist?list=", "")
PlaylistOptionsDialog(playlistId, v.context)
.show(childFragmentManager, "PlaylistOptionsDialog")
true
}
}

fun bind(searchItem: SearchItem) {
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,77 @@
package com.github.libretube.dialogs

import android.app.Dialog
import android.content.Context
import android.os.Bundle
import android.util.Log
import android.widget.ArrayAdapter
import androidx.fragment.app.DialogFragment
import com.github.libretube.R
import com.github.libretube.obj.PlaylistId
import com.github.libretube.util.RetrofitInstance
import com.google.android.material.dialog.MaterialAlertDialogBuilder
import java.io.IOException
import kotlinx.coroutines.CoroutineScope
import kotlinx.coroutines.Dispatchers
import kotlinx.coroutines.launch
import retrofit2.HttpException

class PlaylistOptionsDialog(
private val playlistId: String,
context: Context
) : DialogFragment() {
val TAG = "PlaylistOptionsDialog"

private val optionsList = listOf(
context.getString(R.string.clonePlaylist),
context.getString(R.string.share)
)

override fun onCreateDialog(savedInstanceState: Bundle?): Dialog {
val dialog = MaterialAlertDialogBuilder(requireContext())
.setNegativeButton(R.string.cancel) { dialog, _ ->
dialog.dismiss()
}
.setAdapter(
ArrayAdapter(
requireContext(),
R.layout.video_options_dialog_item,
optionsList
)
) { _, which ->
when (which) {
// Clone the playlist to the users Piped account
0 -> {
val sharedPref =
context?.getSharedPreferences("token", Context.MODE_PRIVATE)
val token = sharedPref?.getString("token", "")!!
importPlaylist(token, playlistId)
}
// share the playlist
1 -> {
val shareDialog = ShareDialog(playlistId, true)
// using parentFragmentManager is important here
shareDialog.show(parentFragmentManager, "ShareDialog")
}
}
}
return dialog.show()
}

private fun importPlaylist(token: String, playlistId: String) {
fun run() {
CoroutineScope(Dispatchers.IO).launch {
val response = try {
RetrofitInstance.api.importPlaylist(token, PlaylistId(playlistId))
} catch (e: IOException) {
println(e)
return@launch
} catch (e: HttpException) {
return@launch
}
Log.e(TAG, response.toString())
}
}
run()
}
}
30 changes: 20 additions & 10 deletions app/src/main/java/com/github/libretube/dialogs/ShareDialog.kt
Original file line number Diff line number Diff line change
Expand Up @@ -3,12 +3,17 @@ package com.github.libretube.dialogs
import android.app.Dialog
import android.content.Intent
import android.os.Bundle
import androidx.core.content.ContentProviderCompat.requireContext
import androidx.fragment.app.DialogFragment
import androidx.preference.PreferenceManager
import com.github.libretube.R
import com.github.libretube.util.RetrofitInstance.url
import com.google.android.material.dialog.MaterialAlertDialogBuilder

class ShareDialog(private val videoId: String) : DialogFragment() {
class ShareDialog(
private val id: String,
private val isPlaylist: Boolean
) : DialogFragment() {

override fun onCreateDialog(savedInstanceState: Bundle?): Dialog {
return activity?.let {
Expand All @@ -25,17 +30,22 @@ class ShareDialog(private val videoId: String) : DialogFragment() {
.setTitle(context?.getString(R.string.share))
.setItems(
shareOptions
) { _, id ->
val url = when (id) {
0 -> "https://piped.kavin.rocks/watch?v=$videoId"
1 -> "https://youtu.be/$videoId"
2 -> "$instanceUrl/watch?v=$videoId" // only available for custom instances
else -> "https://piped.kavin.rocks/watch?v=$videoId"
) { _, which ->
val host = when (which) {
0 -> "https://piped.kavin.rocks"
1 -> "https://youtube.com"
// only available for custom instances
else -> instanceUrl
}
val path = if (!isPlaylist) "/watch?v=$id" else "/playlist?list=$id"
val url = "$host$path"

val intent = Intent()
intent.action = Intent.ACTION_SEND
intent.putExtra(Intent.EXTRA_TEXT, url)
intent.type = "text/plain"
intent.apply {
action = Intent.ACTION_SEND
putExtra(Intent.EXTRA_TEXT, url)
type = "text/plain"
}
context?.startActivity(
Intent.createChooser(intent, context?.getString(R.string.shareTo))
)
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -19,7 +19,7 @@ class VideoOptionsDialog(private val videoId: String, context: Context) : Dialog
/**
* List that stores the different menu options. In the future could be add more options here.
*/
private val list = listOf(
private val optionsList = listOf(
context.getString(R.string.playOnBackground),
context.getString(R.string.addToPlaylist),
context.getString(R.string.share)
Expand All @@ -37,9 +37,9 @@ class VideoOptionsDialog(private val videoId: String, context: Context) : Dialog
ArrayAdapter(
requireContext(),
R.layout.video_options_dialog_item,
list
optionsList
)
) { dialog, which ->
) { _, which ->
// For now, this checks the position of the option with the position that is in the
// list. I don't like it, but we will do like this for now.
when (which) {
Expand All @@ -66,13 +66,10 @@ class VideoOptionsDialog(private val videoId: String, context: Context) : Dialog
}
}
2 -> {
val shareDialog = ShareDialog(videoId)
val shareDialog = ShareDialog(videoId, false)
// using parentFragmentManager is important here
shareDialog.show(parentFragmentManager, "ShareDialog")
}
else -> {
dialog.dismiss()
}
}
}
.show()
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -564,7 +564,7 @@ class PlayerFragment : Fragment() {

// share button
view.findViewById<LinearLayout>(R.id.relPlayer_share).setOnClickListener {
val shareDialog = ShareDialog(videoId!!)
val shareDialog = ShareDialog(videoId!!, false)
shareDialog.show(childFragmentManager, "ShareDialog")
}
// check if livestream
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,7 @@ import android.util.Log
import android.view.LayoutInflater
import android.view.View
import android.view.ViewGroup
import android.widget.ProgressBar
import android.widget.ScrollView
import android.widget.TextView
import androidx.fragment.app.Fragment
Expand Down Expand Up @@ -45,10 +46,11 @@ class PlaylistFragment : Fragment() {
super.onViewCreated(view, savedInstanceState)

playlistId = playlistId!!.replace("/playlist?list=", "")
view.findViewById<TextView>(R.id.playlist_name).text = playlistId
val recyclerView = view.findViewById<RecyclerView>(R.id.playlist_recView)
recyclerView.layoutManager = LinearLayoutManager(context)

val progressBar = view.findViewById<ProgressBar>(R.id.playlist_progress)
progressBar.visibility = View.VISIBLE
fetchPlaylist(view)
}

Expand All @@ -68,6 +70,7 @@ class PlaylistFragment : Fragment() {
nextPage = response.nextpage
isLoading = false
runOnUiThread {
view.findViewById<ProgressBar>(R.id.playlist_progress).visibility = View.GONE
view.findViewById<TextView>(R.id.playlist_name).text = response.name
view.findViewById<TextView>(R.id.playlist_uploader).text = response.uploader
view.findViewById<TextView>(R.id.playlist_totVideos).text =
Expand Down
6 changes: 6 additions & 0 deletions app/src/main/java/com/github/libretube/util/PipedApi.kt
Original file line number Diff line number Diff line change
Expand Up @@ -117,6 +117,12 @@ interface PipedApi {
@Body channels: List<String>
): Message

@POST("import/playlist")
suspend fun importPlaylist(
@Header("Authorization") token: String,
@Body playlistId: PlaylistId
): Message

@GET("user/playlists")
suspend fun playlists(@Header("Authorization") token: String): List<Playlists>

Expand Down
21 changes: 17 additions & 4 deletions app/src/main/res/layout/fragment_playlist.xml
Original file line number Diff line number Diff line change
@@ -1,10 +1,22 @@
<?xml version="1.0" encoding="utf-8"?>
<ScrollView xmlns:android="http://schemas.android.com/apk/res/android"
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
android:layout_width="match_parent"
android:layout_height="match_parent"
tools:context=".fragments.PlaylistFragment"
android:id="@+id/playlist_scrollview">
tools:context=".fragments.PlaylistFragment">

<ProgressBar
android:id="@+id/playlist_progress"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_centerHorizontal="true"
android:layout_centerVertical="true"
android:visibility="gone"/>

<ScrollView
android:layout_width="match_parent"
android:layout_height="match_parent"
android:id="@+id/playlist_scrollview">

<LinearLayout
android:orientation="vertical"
Expand Down Expand Up @@ -47,5 +59,6 @@

</LinearLayout>

</ScrollView>

</ScrollView>
</RelativeLayout>
1 change: 1 addition & 0 deletions app/src/main/res/values/strings.xml
Original file line number Diff line number Diff line change
Expand Up @@ -200,4 +200,5 @@
<string name="pauseOnScreenOff">Autopause</string>
<string name="pauseOnScreenOff_summary">Pause the player when the screen is turned off.</string>
<string name="autoplay_summary">Automatically play the next video when the current is finished.</string>
<string name="clonePlaylist">Clone playlist</string>
</resources>