mirror of
https://github.com/libre-tube/LibreTube.git
synced 2025-04-27 23:40:33 +05:30
migrate watch positions to room
This commit is contained in:
parent
17626419a2
commit
3eadc46780
@ -4,11 +4,11 @@ import android.view.LayoutInflater
|
||||
import android.view.ViewGroup
|
||||
import androidx.fragment.app.FragmentManager
|
||||
import androidx.recyclerview.widget.RecyclerView
|
||||
import com.github.libretube.database.DatabaseHelper
|
||||
import com.github.libretube.databinding.WatchHistoryRowBinding
|
||||
import com.github.libretube.dialogs.VideoOptionsDialog
|
||||
import com.github.libretube.extensions.setFormattedDuration
|
||||
import com.github.libretube.obj.WatchHistoryItem
|
||||
import com.github.libretube.preferences.PreferenceHelper
|
||||
import com.github.libretube.util.ConnectionHelper
|
||||
import com.github.libretube.util.NavigationHelper
|
||||
import com.github.libretube.util.setWatchProgressLength
|
||||
@ -21,7 +21,7 @@ class WatchHistoryAdapter(
|
||||
private val TAG = "WatchHistoryAdapter"
|
||||
|
||||
fun removeFromWatchHistory(position: Int) {
|
||||
PreferenceHelper.removeFromWatchHistory(position)
|
||||
DatabaseHelper.removeFromWatchHistory(position)
|
||||
watchHistory.removeAt(position)
|
||||
notifyDataSetChanged()
|
||||
}
|
||||
@ -54,12 +54,12 @@ class WatchHistoryAdapter(
|
||||
NavigationHelper.navigateVideo(root.context, video.videoId)
|
||||
}
|
||||
root.setOnLongClickListener {
|
||||
VideoOptionsDialog(video.videoId!!)
|
||||
VideoOptionsDialog(video.videoId)
|
||||
.show(childFragmentManager, VideoOptionsDialog::class.java.name)
|
||||
true
|
||||
}
|
||||
|
||||
watchProgress.setWatchProgressLength(video.videoId!!, video.duration)
|
||||
watchProgress.setWatchProgressLength(video.videoId, video.duration)
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -3,8 +3,23 @@ package com.github.libretube.database
|
||||
import androidx.room.Database
|
||||
import androidx.room.RoomDatabase
|
||||
import com.github.libretube.obj.WatchHistoryItem
|
||||
import com.github.libretube.obj.WatchPosition
|
||||
|
||||
@Database(entities = [WatchHistoryItem::class], version = 1)
|
||||
@Database(
|
||||
entities = [
|
||||
WatchHistoryItem::class,
|
||||
WatchPosition::class
|
||||
],
|
||||
version = 2
|
||||
)
|
||||
abstract class AppDatabase : RoomDatabase() {
|
||||
/**
|
||||
* Watch History
|
||||
*/
|
||||
abstract fun watchHistoryDao(): WatchHistoryDao
|
||||
|
||||
/**
|
||||
* Watch Positions
|
||||
*/
|
||||
abstract fun watchPositionDao(): WatchPositionDao
|
||||
}
|
||||
|
@ -2,6 +2,7 @@ package com.github.libretube.database
|
||||
|
||||
import com.github.libretube.obj.Streams
|
||||
import com.github.libretube.obj.WatchHistoryItem
|
||||
import com.github.libretube.obj.WatchPosition
|
||||
import com.github.libretube.util.toID
|
||||
|
||||
object DatabaseHelper {
|
||||
@ -20,4 +21,30 @@ object DatabaseHelper {
|
||||
DatabaseHolder.database.watchHistoryDao().insertAll(watchHistoryItem)
|
||||
}.start()
|
||||
}
|
||||
|
||||
fun removeFromWatchHistory(index: Int) {
|
||||
Thread {
|
||||
DatabaseHolder.database.watchHistoryDao().delete(
|
||||
DatabaseHolder.database.watchHistoryDao().getAll()[index]
|
||||
)
|
||||
}.start()
|
||||
}
|
||||
|
||||
fun saveWatchPosition(videoId: String, position: Long) {
|
||||
val watchPosition = WatchPosition(
|
||||
videoId,
|
||||
position
|
||||
)
|
||||
Thread {
|
||||
DatabaseHolder.database.watchPositionDao().insertAll(watchPosition)
|
||||
}.start()
|
||||
}
|
||||
|
||||
fun removeWatchPosition(videoId: String) {
|
||||
Thread {
|
||||
DatabaseHolder.database.watchPositionDao().delete(
|
||||
DatabaseHolder.database.watchPositionDao().findById(videoId)
|
||||
)
|
||||
}.start()
|
||||
}
|
||||
}
|
||||
|
@ -12,6 +12,8 @@ object DatabaseHolder {
|
||||
context,
|
||||
AppDatabase::class.java,
|
||||
DATABASE_NAME
|
||||
).build()
|
||||
)
|
||||
.fallbackToDestructiveMigration()
|
||||
.build()
|
||||
}
|
||||
}
|
||||
|
@ -3,6 +3,7 @@ package com.github.libretube.database
|
||||
import androidx.room.Dao
|
||||
import androidx.room.Delete
|
||||
import androidx.room.Insert
|
||||
import androidx.room.OnConflictStrategy
|
||||
import androidx.room.Query
|
||||
import com.github.libretube.obj.WatchHistoryItem
|
||||
|
||||
@ -14,7 +15,7 @@ interface WatchHistoryDao {
|
||||
@Query("SELECT * FROM watchHistoryItem WHERE videoId LIKE :videoId LIMIT 1")
|
||||
fun findById(videoId: String): WatchHistoryItem
|
||||
|
||||
@Insert
|
||||
@Insert(onConflict = OnConflictStrategy.REPLACE)
|
||||
fun insertAll(vararg watchHistoryItems: WatchHistoryItem)
|
||||
|
||||
@Delete
|
||||
|
@ -0,0 +1,23 @@
|
||||
package com.github.libretube.database
|
||||
|
||||
import androidx.room.Dao
|
||||
import androidx.room.Delete
|
||||
import androidx.room.Insert
|
||||
import androidx.room.OnConflictStrategy
|
||||
import androidx.room.Query
|
||||
import com.github.libretube.obj.WatchPosition
|
||||
|
||||
@Dao
|
||||
interface WatchPositionDao {
|
||||
@Query("SELECT * FROM watchPosition")
|
||||
fun getAll(): List<WatchPosition>
|
||||
|
||||
@Query("SELECT * FROM watchPosition WHERE videoId LIKE :videoId LIMIT 1")
|
||||
fun findById(videoId: String): WatchPosition
|
||||
|
||||
@Insert(onConflict = OnConflictStrategy.REPLACE)
|
||||
fun insertAll(vararg watchPositions: WatchPosition)
|
||||
|
||||
@Delete
|
||||
fun delete(watchPosition: WatchPosition)
|
||||
}
|
@ -3,15 +3,23 @@ package com.github.libretube.util
|
||||
import android.view.View
|
||||
import android.view.ViewTreeObserver
|
||||
import android.widget.LinearLayout
|
||||
import com.github.libretube.preferences.PreferenceHelper
|
||||
import com.github.libretube.database.DatabaseHolder
|
||||
import com.github.libretube.obj.WatchPosition
|
||||
|
||||
/**
|
||||
* shows the already watched time under the video
|
||||
*/
|
||||
fun View?.setWatchProgressLength(videoId: String, duration: Long) {
|
||||
val view = this!!
|
||||
val positions = PreferenceHelper.getWatchPositions()
|
||||
var positions = listOf<WatchPosition>()
|
||||
var newWidth: Long? = null
|
||||
|
||||
val thread = Thread {
|
||||
positions = DatabaseHolder.database.watchPositionDao().getAll()
|
||||
}
|
||||
thread.start()
|
||||
thread.join()
|
||||
|
||||
view.getViewTreeObserver()
|
||||
.addOnGlobalLayoutListener(object : ViewTreeObserver.OnGlobalLayoutListener {
|
||||
override fun onGlobalLayout() {
|
||||
|
@ -38,6 +38,7 @@ import com.github.libretube.adapters.ChaptersAdapter
|
||||
import com.github.libretube.adapters.CommentsAdapter
|
||||
import com.github.libretube.adapters.TrendingAdapter
|
||||
import com.github.libretube.database.DatabaseHelper
|
||||
import com.github.libretube.database.DatabaseHolder
|
||||
import com.github.libretube.databinding.DoubleTapOverlayBinding
|
||||
import com.github.libretube.databinding.ExoStyledPlayerControlViewBinding
|
||||
import com.github.libretube.databinding.FragmentPlayerBinding
|
||||
@ -51,6 +52,7 @@ import com.github.libretube.obj.ChapterSegment
|
||||
import com.github.libretube.obj.Segment
|
||||
import com.github.libretube.obj.Segments
|
||||
import com.github.libretube.obj.Streams
|
||||
import com.github.libretube.obj.WatchPosition
|
||||
import com.github.libretube.preferences.PreferenceHelper
|
||||
import com.github.libretube.preferences.PreferenceKeys
|
||||
import com.github.libretube.services.BackgroundMode
|
||||
@ -444,8 +446,7 @@ class PlayerFragment : BaseFragment() {
|
||||
val newParams = if (index != 0) {
|
||||
// caption selected
|
||||
|
||||
// get the caption name and language
|
||||
val captionLanguage = subtitlesNamesList[index]
|
||||
// get the caption language code
|
||||
val captionLanguageCode = subtitleCodesList[index]
|
||||
|
||||
// select the new caption preference
|
||||
@ -814,13 +815,13 @@ class PlayerFragment : BaseFragment() {
|
||||
// save the watch position if video isn't finished and option enabled
|
||||
private fun saveWatchPosition() {
|
||||
if (watchPositionsEnabled && exoPlayer.currentPosition != exoPlayer.duration) {
|
||||
PreferenceHelper.saveWatchPosition(
|
||||
DatabaseHelper.saveWatchPosition(
|
||||
videoId!!,
|
||||
exoPlayer.currentPosition
|
||||
)
|
||||
} else if (watchPositionsEnabled) {
|
||||
// delete watch position if video has ended
|
||||
PreferenceHelper.removeWatchPosition(videoId!!)
|
||||
DatabaseHelper.removeWatchPosition(videoId!!)
|
||||
}
|
||||
}
|
||||
|
||||
@ -934,7 +935,12 @@ class PlayerFragment : BaseFragment() {
|
||||
|
||||
private fun seekToWatchPosition() {
|
||||
// seek to saved watch position if available
|
||||
val watchPositions = PreferenceHelper.getWatchPositions()
|
||||
var watchPositions = listOf<WatchPosition>()
|
||||
val thread = Thread {
|
||||
watchPositions = DatabaseHolder.database.watchPositionDao().getAll()
|
||||
}
|
||||
thread.start()
|
||||
thread.join()
|
||||
var position: Long? = null
|
||||
watchPositions.forEach {
|
||||
if (it.videoId == videoId &&
|
||||
|
@ -12,7 +12,6 @@ import com.github.libretube.database.DatabaseHolder
|
||||
import com.github.libretube.databinding.FragmentWatchHistoryBinding
|
||||
import com.github.libretube.extensions.BaseFragment
|
||||
import com.github.libretube.obj.WatchHistoryItem
|
||||
import kotlinx.coroutines.runBlocking
|
||||
|
||||
class WatchHistoryFragment : BaseFragment() {
|
||||
private val TAG = "WatchHistoryFragment"
|
||||
|
@ -1,7 +1,11 @@
|
||||
package com.github.libretube.obj
|
||||
|
||||
import androidx.room.ColumnInfo
|
||||
import androidx.room.Entity
|
||||
|
||||
@Entity
|
||||
class CustomInstance(
|
||||
var name: String = "",
|
||||
@ColumnInfo var name: String = "",
|
||||
var apiUrl: String = "",
|
||||
var frontendUrl: String = ""
|
||||
)
|
||||
|
@ -1,6 +1,11 @@
|
||||
package com.github.libretube.obj
|
||||
|
||||
import androidx.room.ColumnInfo
|
||||
import androidx.room.Entity
|
||||
import androidx.room.PrimaryKey
|
||||
|
||||
@Entity(tableName = "watchPosition")
|
||||
data class WatchPosition(
|
||||
val videoId: String = "",
|
||||
val position: Long = 0L
|
||||
@PrimaryKey val videoId: String = "",
|
||||
@ColumnInfo val position: Long = 0L
|
||||
)
|
||||
|
@ -6,10 +6,6 @@ import androidx.preference.PreferenceManager
|
||||
import com.fasterxml.jackson.core.type.TypeReference
|
||||
import com.fasterxml.jackson.databind.ObjectMapper
|
||||
import com.github.libretube.obj.CustomInstance
|
||||
import com.github.libretube.obj.Streams
|
||||
import com.github.libretube.obj.WatchHistoryItem
|
||||
import com.github.libretube.obj.WatchPosition
|
||||
import com.github.libretube.util.toID
|
||||
|
||||
object PreferenceHelper {
|
||||
private val TAG = "PreferenceHelper"
|
||||
@ -135,114 +131,6 @@ object PreferenceHelper {
|
||||
editor.putString("search_history", json).apply()
|
||||
}
|
||||
|
||||
fun addToWatchHistory(videoId: String, streams: Streams) {
|
||||
removeFromWatchHistory(videoId)
|
||||
|
||||
val watchHistoryItem = WatchHistoryItem(
|
||||
videoId,
|
||||
streams.title,
|
||||
streams.uploadDate,
|
||||
streams.uploader,
|
||||
streams.uploaderUrl.toID(),
|
||||
streams.uploaderAvatar,
|
||||
streams.thumbnailUrl,
|
||||
streams.duration
|
||||
)
|
||||
|
||||
val watchHistory = getWatchHistory()
|
||||
|
||||
watchHistory += watchHistoryItem
|
||||
|
||||
// remove oldest item when the watch history is longer than the pref
|
||||
val maxWatchHistorySize = getString(PreferenceKeys.WATCH_HISTORY_SIZE, "unlimited")
|
||||
if (maxWatchHistorySize != "unlimited" && watchHistory.size > maxWatchHistorySize.toInt()) {
|
||||
watchHistory.removeAt(0)
|
||||
}
|
||||
|
||||
val json = mapper.writeValueAsString(watchHistory)
|
||||
editor.putString("watch_history", json).apply()
|
||||
}
|
||||
|
||||
fun removeFromWatchHistory(videoId: String) {
|
||||
val watchHistory = getWatchHistory()
|
||||
|
||||
var indexToRemove: Int? = null
|
||||
watchHistory.forEachIndexed { index, item ->
|
||||
if (item.videoId == videoId) indexToRemove = index
|
||||
}
|
||||
if (indexToRemove == null) return
|
||||
watchHistory.removeAt(indexToRemove!!)
|
||||
val json = mapper.writeValueAsString(watchHistory)
|
||||
editor.putString("watch_history", json).commit()
|
||||
}
|
||||
|
||||
fun removeFromWatchHistory(position: Int) {
|
||||
val watchHistory = getWatchHistory()
|
||||
watchHistory.removeAt(position)
|
||||
|
||||
val json = mapper.writeValueAsString(watchHistory)
|
||||
editor.putString("watch_history", json).commit()
|
||||
}
|
||||
|
||||
fun getWatchHistory(): ArrayList<WatchHistoryItem> {
|
||||
val json: String = settings.getString("watch_history", "")!!
|
||||
val type = mapper.typeFactory.constructCollectionType(
|
||||
List::class.java,
|
||||
WatchHistoryItem::class.java
|
||||
)
|
||||
|
||||
return try {
|
||||
mapper.readValue(json, type)
|
||||
} catch (e: Exception) {
|
||||
arrayListOf()
|
||||
}
|
||||
}
|
||||
|
||||
fun saveWatchPosition(videoId: String, position: Long) {
|
||||
val watchPositions = getWatchPositions()
|
||||
val watchPositionItem = WatchPosition(videoId, position)
|
||||
|
||||
var indexToRemove: Int? = null
|
||||
watchPositions.forEachIndexed { index, item ->
|
||||
if (item.videoId == videoId) indexToRemove = index
|
||||
}
|
||||
|
||||
if (indexToRemove != null) watchPositions.removeAt(indexToRemove!!)
|
||||
|
||||
watchPositions += watchPositionItem
|
||||
|
||||
val json = mapper.writeValueAsString(watchPositions)
|
||||
editor.putString("watch_positions", json).commit()
|
||||
}
|
||||
|
||||
fun removeWatchPosition(videoId: String) {
|
||||
val watchPositions = getWatchPositions()
|
||||
|
||||
var indexToRemove: Int? = null
|
||||
watchPositions.forEachIndexed { index, item ->
|
||||
if (item.videoId == videoId) indexToRemove = index
|
||||
}
|
||||
|
||||
if (indexToRemove != null) watchPositions.removeAt(indexToRemove!!)
|
||||
|
||||
val json = mapper.writeValueAsString(watchPositions)
|
||||
editor.putString("watch_positions", json).commit()
|
||||
}
|
||||
|
||||
fun getWatchPositions(): ArrayList<WatchPosition> {
|
||||
val json: String = settings.getString("watch_positions", "")!!
|
||||
val type = mapper.typeFactory.constructCollectionType(
|
||||
List::class.java,
|
||||
WatchPosition::class.java
|
||||
)
|
||||
|
||||
return try {
|
||||
mapper.readValue(json, type)
|
||||
} catch (e: Exception) {
|
||||
arrayListOf()
|
||||
}
|
||||
}
|
||||
|
||||
fun setLatestVideoId(videoId: String) {
|
||||
editor.putString(PreferenceKeys.LAST_STREAM_VIDEO_ID, videoId)
|
||||
}
|
||||
|
Loading…
x
Reference in New Issue
Block a user