mirror of
https://github.com/bbara04/Purefin.git
synced 2026-03-31 17:10:08 +02:00
Only show the latest media on the HomePage
This commit is contained in:
@@ -26,19 +26,21 @@ class HomePageViewModel @Inject constructor(
|
||||
private val jellyfinApiClient: JellyfinApiClient
|
||||
) : ViewModel() {
|
||||
|
||||
init {
|
||||
loadHomePageData()
|
||||
}
|
||||
|
||||
private val _continueWatching = MutableStateFlow<List<ContinueWatchingItem>>(emptyList())
|
||||
val continueWatching = _continueWatching.asStateFlow()
|
||||
|
||||
private val _libraries = MutableStateFlow<List<LibraryItem>>(emptyList())
|
||||
val libraries = _libraries.asStateFlow()
|
||||
|
||||
private val _libraryContent = MutableStateFlow<Map<UUID, List<PosterItem>>>(emptyMap())
|
||||
val libraryContent = _libraryContent.asStateFlow()
|
||||
private val _libraryItems = MutableStateFlow<Map<UUID, List<PosterItem>>>(emptyMap())
|
||||
val libraryItems = _libraryItems.asStateFlow()
|
||||
|
||||
private val _latestLibraryContent = MutableStateFlow<Map<UUID, List<PosterItem>>>(emptyMap())
|
||||
val latestLibraryContent = _latestLibraryContent.asStateFlow()
|
||||
|
||||
init {
|
||||
loadHomePageData()
|
||||
}
|
||||
|
||||
fun loadContinueWatching() {
|
||||
viewModelScope.launch {
|
||||
@@ -68,34 +70,84 @@ class HomePageViewModel @Inject constructor(
|
||||
|
||||
fun loadLibraries() {
|
||||
viewModelScope.launch {
|
||||
val libraries: List<BaseItemDto> = jellyfinApiClient.getLibraries()
|
||||
val mappedLibraries = libraries.map {
|
||||
LibraryItem(
|
||||
name = it.name!!,
|
||||
id = it.id
|
||||
)
|
||||
loadLibrariesInternal()
|
||||
}
|
||||
}
|
||||
|
||||
private suspend fun loadLibrariesInternal() {
|
||||
val libraries: List<BaseItemDto> = jellyfinApiClient.getLibraries()
|
||||
val mappedLibraries = libraries.map {
|
||||
LibraryItem(
|
||||
name = it.name!!,
|
||||
id = it.id
|
||||
)
|
||||
}
|
||||
_libraries.value = mappedLibraries
|
||||
}
|
||||
|
||||
fun loadAllLibraryItems() {
|
||||
viewModelScope.launch {
|
||||
if (_libraries.value.isEmpty()) {
|
||||
loadLibrariesInternal()
|
||||
}
|
||||
_libraries.value = mappedLibraries
|
||||
mappedLibraries.forEach { library ->
|
||||
loadLibrary(library.id)
|
||||
_libraries.value.forEach { library ->
|
||||
loadLibraryItems(library.id)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
fun loadLibrary(libraryId: UUID) {
|
||||
if (_libraryContent.value.containsKey(libraryId)) return
|
||||
private fun loadLibraryItems(libraryId: UUID) {
|
||||
viewModelScope.launch {
|
||||
val libraryItems = jellyfinApiClient.getLibrary(libraryId)
|
||||
val posterItems = libraryItems.map {
|
||||
val libraryItems: List<BaseItemDto> = jellyfinApiClient.getLibrary(libraryId)
|
||||
val libraryPosterItems = libraryItems.map {
|
||||
PosterItem(
|
||||
id = it.id,
|
||||
title = it.name ?: "Unknown",
|
||||
colors = listOf(Color.Blue, Color.Cyan),
|
||||
isLatest = false
|
||||
title = it.name ?: "Unknown"
|
||||
)
|
||||
}
|
||||
_libraryContent.update { currentMap ->
|
||||
currentMap + (libraryId to posterItems)
|
||||
_libraryItems.update { currentMap ->
|
||||
currentMap + (libraryId to libraryPosterItems)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
fun loadAllShownLibraryItems() {
|
||||
viewModelScope.launch {
|
||||
if (_libraries.value.isEmpty()) {
|
||||
loadLibrariesInternal()
|
||||
}
|
||||
_libraries.value.forEach { library ->
|
||||
loadLatestLibraryItems(library.id)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
fun loadLatestLibraryItems(libraryId: UUID) {
|
||||
if (_libraryItems.value.containsKey(libraryId)) return
|
||||
val libraryItems = _libraryItems.value[libraryId]
|
||||
viewModelScope.launch {
|
||||
val latestLibraryItems = jellyfinApiClient.getLatestFromLibrary(libraryId)
|
||||
val latestLibraryPosterItem = latestLibraryItems.mapNotNull {
|
||||
when (it.type) {
|
||||
BaseItemKind.MOVIE -> PosterItem(
|
||||
id = it.id,
|
||||
title = it.name ?: "Unknown"
|
||||
)
|
||||
BaseItemKind.EPISODE -> PosterItem(
|
||||
id = it.seriesId!!,
|
||||
title = it.seriesName ?: "Unknown"
|
||||
)
|
||||
|
||||
BaseItemKind.SEASON -> PosterItem(
|
||||
id = it.seriesId!!,
|
||||
title = it.seriesName ?: "Unknown"
|
||||
)
|
||||
else -> null
|
||||
}
|
||||
}
|
||||
_latestLibraryContent.update { currentMap ->
|
||||
currentMap + (libraryId to latestLibraryPosterItem)
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -103,6 +155,8 @@ class HomePageViewModel @Inject constructor(
|
||||
fun loadHomePageData() {
|
||||
loadContinueWatching()
|
||||
loadLibraries()
|
||||
loadAllLibraryItems()
|
||||
loadAllShownLibraryItems()
|
||||
}
|
||||
|
||||
fun logout() {
|
||||
|
||||
@@ -23,7 +23,7 @@ fun HomeContent(
|
||||
) {
|
||||
|
||||
val libraries by viewModel.libraries.collectAsState()
|
||||
val libraryContent by viewModel.libraryContent.collectAsState()
|
||||
val libraryContent by viewModel.latestLibraryContent.collectAsState()
|
||||
|
||||
LazyColumn(
|
||||
modifier = modifier
|
||||
|
||||
@@ -19,9 +19,7 @@ data class LibraryItem(
|
||||
|
||||
data class PosterItem(
|
||||
val id: UUID,
|
||||
val title: String,
|
||||
val isLatest: Boolean,
|
||||
val colors: List<Color>
|
||||
val title: String
|
||||
)
|
||||
|
||||
data class HomeNavItem(
|
||||
|
||||
@@ -10,6 +10,7 @@ import org.jellyfin.sdk.api.client.extensions.authenticateUserByName
|
||||
import org.jellyfin.sdk.api.client.extensions.itemsApi
|
||||
import org.jellyfin.sdk.api.client.extensions.libraryApi
|
||||
import org.jellyfin.sdk.api.client.extensions.userApi
|
||||
import org.jellyfin.sdk.api.client.extensions.userLibraryApi
|
||||
import org.jellyfin.sdk.createJellyfin
|
||||
import org.jellyfin.sdk.model.ClientInfo
|
||||
import org.jellyfin.sdk.model.api.BaseItemDto
|
||||
@@ -115,4 +116,24 @@ class JellyfinApiClient @Inject constructor(
|
||||
return response.content.items
|
||||
}
|
||||
|
||||
/**
|
||||
* Fetches the latest media items from a specified library including Movie, Episode, Season.
|
||||
*
|
||||
* @param libraryId The UUID of the library to fetch from
|
||||
* @return A list of [BaseItemDto] representing the latest media items that includes Movie, Episode, Season, or an empty list if not configured
|
||||
*/
|
||||
suspend fun getLatestFromLibrary(libraryId: UUID): List<BaseItemDto> {
|
||||
if (!ensureConfigured()) {
|
||||
return emptyList()
|
||||
}
|
||||
val response = api.userLibraryApi.getLatestMedia(
|
||||
userId = getUserId(),
|
||||
parentId = libraryId,
|
||||
includeItemTypes = listOf(BaseItemKind.MOVIE, BaseItemKind.EPISODE, BaseItemKind.SEASON),
|
||||
limit = 10
|
||||
)
|
||||
Log.d("getLatestFromLibrary response: {}", response.content.toString())
|
||||
return response.content
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user