diff --git a/app/src/main/java/com/github/damontecres/wholphin/data/model/BaseItem.kt b/app/src/main/java/com/github/damontecres/wholphin/data/model/BaseItem.kt index 312b7446..a9673131 100644 --- a/app/src/main/java/com/github/damontecres/wholphin/data/model/BaseItem.kt +++ b/app/src/main/java/com/github/damontecres/wholphin/data/model/BaseItem.kt @@ -72,8 +72,7 @@ data class BaseItem( @Transient val aspectRatio: Float? = data.primaryImageAspectRatio?.toFloat()?.takeIf { it > 0 } - @Transient - val indexNumber = data.indexNumber ?: dateAsIndex() + val indexNumber get() = data.indexNumber val playbackPosition get() = data.userData?.playbackPositionTicks?.ticks ?: Duration.ZERO diff --git a/app/src/main/java/com/github/damontecres/wholphin/ui/detail/series/SeriesViewModel.kt b/app/src/main/java/com/github/damontecres/wholphin/ui/detail/series/SeriesViewModel.kt index 4c0fb81b..8ae7a579 100644 --- a/app/src/main/java/com/github/damontecres/wholphin/ui/detail/series/SeriesViewModel.kt +++ b/app/src/main/java/com/github/damontecres/wholphin/ui/detail/series/SeriesViewModel.kt @@ -39,6 +39,7 @@ import com.github.damontecres.wholphin.util.GetEpisodesRequestHandler import com.github.damontecres.wholphin.util.GetItemsRequestHandler import com.github.damontecres.wholphin.util.LoadingExceptionHandler import com.github.damontecres.wholphin.util.LoadingState +import com.google.common.cache.CacheBuilder import dagger.assisted.Assisted import dagger.assisted.AssistedFactory import dagger.assisted.AssistedInject @@ -57,6 +58,7 @@ import kotlinx.coroutines.withContext import org.jellyfin.sdk.api.client.ApiClient import org.jellyfin.sdk.api.client.extensions.libraryApi import org.jellyfin.sdk.api.client.extensions.tvShowsApi +import org.jellyfin.sdk.api.client.extensions.userLibraryApi import org.jellyfin.sdk.model.api.BaseItemKind import org.jellyfin.sdk.model.api.ItemFields import org.jellyfin.sdk.model.api.ItemSortBy @@ -293,14 +295,16 @@ class SeriesViewModel listOf( ItemFields.MEDIA_SOURCES, ItemFields.MEDIA_SOURCE_COUNT, - ItemFields.MEDIA_STREAMS, ItemFields.OVERVIEW, ItemFields.CUSTOM_RATING, - ItemFields.TRICKPLAY, ItemFields.PRIMARY_IMAGE_ASPECT_RATIO, - ItemFields.PEOPLE, ), ) + Timber.v( + "loadEpisodesInternal: episodeId=%s, episodeNumber=%s", + episodeId, + episodeNumber, + ) val pager = ApiRequestPager(api, request, GetEpisodesRequestHandler, viewModelScope) pager.init(episodeNumber ?: 0) val initialIndex = @@ -504,19 +508,34 @@ class SeriesViewModel } private var peopleInEpisodeJob: Job? = null + private val peopleInEpisodeCache = + CacheBuilder + .newBuilder() + .maximumSize(25) + .build>() suspend fun lookupPeopleInEpisode(item: BaseItem) { peopleInEpisodeJob?.cancel() if (peopleInEpisode.value?.itemId != item.id) { peopleInEpisode.setValueOnMain(PeopleInItem()) + val result = + peopleInEpisodeCache + .get(item.id) { + viewModelScope.async(Dispatchers.IO) { + val list = + api.userLibraryApi + .getItem(item.id) + .content.people + ?.map { Person.fromDto(it, api) } + .orEmpty() + + PeopleInItem(item.id, list) + } + } peopleInEpisodeJob = viewModelScope.launch(ExceptionHandler()) { delay(250) - val people = - item.data.people - ?.letNotEmpty { it.map { Person.fromDto(it, api) } } - .orEmpty() - peopleInEpisode.setValueOnMain(PeopleInItem(item.id, people)) + peopleInEpisode.setValueOnMain(result.await()) } } }