diff --git a/.idea/misc.xml b/.idea/misc.xml index faf84286..426a31e4 100644 --- a/.idea/misc.xml +++ b/.idea/misc.xml @@ -73,8 +73,10 @@ + - + + diff --git a/app/src/main/java/com/kl3jvi/animity/bindings/ViewBindings.kt b/app/src/main/java/com/kl3jvi/animity/bindings/ViewBindings.kt index 65aa5d82..8d282f5a 100644 --- a/app/src/main/java/com/kl3jvi/animity/bindings/ViewBindings.kt +++ b/app/src/main/java/com/kl3jvi/animity/bindings/ViewBindings.kt @@ -26,16 +26,21 @@ object ViewBindings { } @JvmStatic - @BindingAdapter("drawable") - fun setImageDrawable(image: ImageView, drawable: Drawable?) { - if (drawable != null) { - GlideApp.with(image.context) - .load(R.drawable.ic_play_tv) - .diskCacheStrategy(DiskCacheStrategy.AUTOMATIC) - .into(image) - } + @BindingAdapter(value = ["imageUrl", "placeholder", "error"], requireAll = false) + fun loadImage( + imageView: ImageView, + imageUrl: String?, + placeholder: Drawable?, + error: Drawable? + ) { + imageView + .load(imageUrl) { + placeholder(placeholder) + error(error) + } } + @JvmStatic @BindingAdapter("avatarImage") fun setAvatarImage(image: ImageView, url: String?) { diff --git a/app/src/main/java/com/kl3jvi/animity/domain/use_cases/GetAnimesUseCase.kt b/app/src/main/java/com/kl3jvi/animity/domain/use_cases/GetAnimesUseCase.kt index 2a5fb257..05a25c77 100644 --- a/app/src/main/java/com/kl3jvi/animity/domain/use_cases/GetAnimesUseCase.kt +++ b/app/src/main/java/com/kl3jvi/animity/domain/use_cases/GetAnimesUseCase.kt @@ -19,7 +19,7 @@ class GetAnimesUseCase @Inject constructor( private val homeRepository: HomeRepositoryImpl, private val ioDispatcher: CoroutineDispatcher ) { - suspend operator fun invoke(): Flow>> = flow { + operator fun invoke(): Flow>> = flow { coroutineScope { try { val mutableListOfAnimeMetaModel = mutableListOf() diff --git a/app/src/main/java/com/kl3jvi/animity/ui/adapters/AnimeCardAdapter.kt b/app/src/main/java/com/kl3jvi/animity/ui/adapters/AnimeCardAdapter.kt index 444f6ed5..70ac073b 100644 --- a/app/src/main/java/com/kl3jvi/animity/ui/adapters/AnimeCardAdapter.kt +++ b/app/src/main/java/com/kl3jvi/animity/ui/adapters/AnimeCardAdapter.kt @@ -8,6 +8,7 @@ import androidx.recyclerview.widget.ListAdapter import androidx.recyclerview.widget.RecyclerView import com.kl3jvi.animity.data.model.ui_models.AnimeMetaModel import com.kl3jvi.animity.databinding.ItemCardAnimeBinding +import com.kl3jvi.animity.databinding.ItemCardAnimeExperimentalBinding import com.kl3jvi.animity.ui.fragments.home.HomeFragmentDirections import com.kl3jvi.animity.ui.fragments.profile.ProfileFragmentDirections diff --git a/app/src/main/java/com/kl3jvi/animity/ui/fragments/details/DetailsFragment.kt b/app/src/main/java/com/kl3jvi/animity/ui/fragments/details/DetailsFragment.kt index a26aeea8..f1189220 100644 --- a/app/src/main/java/com/kl3jvi/animity/ui/fragments/details/DetailsFragment.kt +++ b/app/src/main/java/com/kl3jvi/animity/ui/fragments/details/DetailsFragment.kt @@ -88,12 +88,12 @@ class DetailsFragment : BaseFragment() when (res) { is Resource.Success -> { res.data?.let { info -> - binding.expandTextView.text = info.plotSummary + binding.animeInfoLayout.textOverview.text = info.plotSummary binding.releaseDate.text = info.releasedTime binding.status.text = info.status binding.type.text = info.type - binding.expandTextView.visibility = VISIBLE + binding.animeInfoLayout.textOverview.visibility = VISIBLE binding.releaseDate.visibility = VISIBLE binding.status.visibility = VISIBLE binding.type.visibility = VISIBLE @@ -129,7 +129,7 @@ class DetailsFragment : BaseFragment() } } is Resource.Loading -> { - binding.expandTextView.visibility = GONE + binding.animeInfoLayout.textOverview.visibility = GONE binding.releaseDate.visibility = GONE binding.status.visibility = GONE binding.type.visibility = GONE diff --git a/app/src/main/java/com/kl3jvi/animity/ui/fragments/details/DetailsViewModel.kt b/app/src/main/java/com/kl3jvi/animity/ui/fragments/details/DetailsViewModel.kt index d758b093..e47c20ad 100644 --- a/app/src/main/java/com/kl3jvi/animity/ui/fragments/details/DetailsViewModel.kt +++ b/app/src/main/java/com/kl3jvi/animity/ui/fragments/details/DetailsViewModel.kt @@ -18,7 +18,6 @@ import kotlinx.coroutines.ExperimentalCoroutinesApi import kotlinx.coroutines.flow.Flow import kotlinx.coroutines.flow.flatMapLatest import kotlinx.coroutines.launch -import kotlinx.coroutines.withContext import javax.inject.Inject @HiltViewModel @@ -60,11 +59,13 @@ class DetailsViewModel @Inject constructor( val lastEpisodeReleaseTime = Transformations.switchMap(_url) { - getAnimeDetailsUseCase.fetchEpisodeReleaseTime(it.split("/").last()).asLiveData(Dispatchers.IO + viewModelScope.coroutineContext) + getAnimeDetailsUseCase.fetchEpisodeReleaseTime(it.split("/").last()) + .asLiveData(Dispatchers.IO + viewModelScope.coroutineContext) } val isOnDatabase = Transformations.switchMap(_url) { url -> - getAnimeDetailsUseCase.checkIfExists(url).asLiveData(Dispatchers.IO + viewModelScope.coroutineContext) + getAnimeDetailsUseCase.checkIfExists(url) + .asLiveData(Dispatchers.IO + viewModelScope.coroutineContext) } fun passUrl(url: String) { @@ -72,10 +73,8 @@ class DetailsViewModel @Inject constructor( Log.e("Category URL", url) } - fun insert(anime: AnimeMetaModel) = viewModelScope.launch { - withContext(Dispatchers.IO) { // Dispatchers.IO (main-safety block) - animeRepository.insertFavoriteAnime(anime) // Dispatchers.IO (main-safety block) - } + fun insert(anime: AnimeMetaModel) = viewModelScope.launch(Dispatchers.IO) { + animeRepository.insertFavoriteAnime(anime) } fun updateAnimeFavorite(id: Int?): Flow> { @@ -86,10 +85,8 @@ class DetailsViewModel @Inject constructor( return getAnimeDetailsFromAnilistUseCase(anime?.title.toString()) } - fun delete(anime: AnimeMetaModel) = viewModelScope.launch { - withContext(Dispatchers.IO) { // Dispatchers.IO (main-safety block) - animeRepository.deleteAnime(anime) // Dispatchers.IO (main-safety block) - } + fun delete(anime: AnimeMetaModel) = viewModelScope.launch(Dispatchers.IO) { + animeRepository.deleteAnime(anime) } } diff --git a/app/src/main/java/com/kl3jvi/animity/ui/fragments/favorites/FavoritesFragment.kt b/app/src/main/java/com/kl3jvi/animity/ui/fragments/favorites/FavoritesFragment.kt index 2a4d07b9..885cde00 100644 --- a/app/src/main/java/com/kl3jvi/animity/ui/fragments/favorites/FavoritesFragment.kt +++ b/app/src/main/java/com/kl3jvi/animity/ui/fragments/favorites/FavoritesFragment.kt @@ -75,9 +75,10 @@ class FavoritesFragment : Fragment(R.layout.fragment_favorites) { private fun observeAniList() { - collectFlow(viewModel.favoriteAnimesList) { animeList -> - val list = animeList.data?.user?.favourites?.anime?.edges?.map { - Log.e("HASHED", + collectFlow(viewModel.favoriteAnimeList) { animeList -> + val list = animeList?.data?.user?.favourites?.anime?.edges?.map { + Log.e( + "HASHED", it?.node?.title?.romaji?.lowercase(Locale.getDefault()).hashCode().toString() ) AnimeMetaModel( diff --git a/app/src/main/java/com/kl3jvi/animity/ui/fragments/favorites/FavoritesViewModel.kt b/app/src/main/java/com/kl3jvi/animity/ui/fragments/favorites/FavoritesViewModel.kt index f414739e..160fa5b0 100644 --- a/app/src/main/java/com/kl3jvi/animity/ui/fragments/favorites/FavoritesViewModel.kt +++ b/app/src/main/java/com/kl3jvi/animity/ui/fragments/favorites/FavoritesViewModel.kt @@ -1,6 +1,12 @@ package com.kl3jvi.animity.ui.fragments.favorites -import androidx.lifecycle.* +import android.util.Log +import androidx.lifecycle.LiveData +import androidx.lifecycle.ViewModel +import androidx.lifecycle.asLiveData +import androidx.lifecycle.viewModelScope +import com.apollographql.apollo3.api.ApolloResponse +import com.kl3jvi.animity.FavoritesAnimeQuery import com.kl3jvi.animity.data.model.ui_models.AnimeMetaModel import com.kl3jvi.animity.data.repository.fragment_repositories.UserRepositoryImpl import com.kl3jvi.animity.data.repository.persistence_repository.PersistenceRepositoryImpl @@ -9,6 +15,7 @@ import com.kl3jvi.animity.domain.use_cases.GetUserSessionUseCase import com.kl3jvi.animity.persistence.AnimeRepository import dagger.hilt.android.lifecycle.HiltViewModel import kotlinx.coroutines.CoroutineDispatcher +import kotlinx.coroutines.Dispatchers import kotlinx.coroutines.ExperimentalCoroutinesApi import kotlinx.coroutines.flow.* import kotlinx.coroutines.launch @@ -24,15 +31,29 @@ class FavoritesViewModel @Inject constructor( private val userRepo: UserRepositoryImpl, private val ioDispatcher: CoroutineDispatcher ) : ViewModel() { - private val _listOfIds = MutableLiveData>() - val listOfIds: LiveData> = _listOfIds + private var _favoriteAnimeList = + MutableStateFlow?>(null) + val favoriteAnimeList = _favoriteAnimeList.asStateFlow() val favoriteFromDatabase: LiveData> = animeRepository.getFavoriteAnimes.asLiveData(ioDispatcher + viewModelScope.coroutineContext) - val favoriteAnimesList = getUserSessionUseCase().flatMapLatest { - getFavoriteAnimesUseCase(it.data?.viewer?.id, 1) - }.flowOn(ioDispatcher) + init { + getFavoriteAnimes() + } + + private fun getFavoriteAnimes() { + viewModelScope.launch(Dispatchers.IO) { + getUserSessionUseCase().flatMapLatest { + getFavoriteAnimesUseCase(it.data?.viewer?.id, 1) + }.flowOn(ioDispatcher) + .catch { e -> Log.e("Error", e.message.orEmpty()) } + .collect { + _favoriteAnimeList.value = it + } + } + } + fun insertRemoteToLocalDb(list: List) = viewModelScope.launch { persistenceRepository.insertAnimeList(list) diff --git a/app/src/main/java/com/kl3jvi/animity/ui/fragments/home/HomeFragment.kt b/app/src/main/java/com/kl3jvi/animity/ui/fragments/home/HomeFragment.kt index e1573d14..b97d4b45 100644 --- a/app/src/main/java/com/kl3jvi/animity/ui/fragments/home/HomeFragment.kt +++ b/app/src/main/java/com/kl3jvi/animity/ui/fragments/home/HomeFragment.kt @@ -48,7 +48,6 @@ class HomeFragment : Fragment(R.layout.fragment_home) { private fun fetchHomeData() { observeLiveData(viewModel.homeData, viewLifecycleOwner) { res -> - when (res) { is Resource.Error -> { binding.mainRv.hide() diff --git a/app/src/main/java/com/kl3jvi/animity/ui/fragments/home/HomeViewModel.kt b/app/src/main/java/com/kl3jvi/animity/ui/fragments/home/HomeViewModel.kt index 70e8380c..4aee9215 100644 --- a/app/src/main/java/com/kl3jvi/animity/ui/fragments/home/HomeViewModel.kt +++ b/app/src/main/java/com/kl3jvi/animity/ui/fragments/home/HomeViewModel.kt @@ -9,12 +9,10 @@ import com.kl3jvi.animity.ui.adapters.homeAdapter.HomeRecyclerViewItem import com.kl3jvi.animity.utils.Resource import dagger.hilt.android.lifecycle.HiltViewModel import kotlinx.coroutines.CoroutineDispatcher -import kotlinx.coroutines.Dispatchers import kotlinx.coroutines.flow.catch import kotlinx.coroutines.flow.flowOn import kotlinx.coroutines.flow.launchIn import kotlinx.coroutines.flow.onEach -import kotlinx.coroutines.launch import javax.inject.Inject @HiltViewModel @@ -31,12 +29,12 @@ class HomeViewModel @Inject constructor( } private fun getHomePageData() { - viewModelScope.launch { - getAnimesUseCase().flowOn(Dispatchers.IO).catch { e -> - e.printStackTrace() - }.onEach { - _homeData.value = it - }.launchIn(viewModelScope) - } + + getAnimesUseCase().flowOn(ioDispatcher).catch { e -> + e.printStackTrace() + }.onEach { + _homeData.value = it + }.launchIn(viewModelScope) + } } diff --git a/app/src/main/res/layout/fragment_details.xml b/app/src/main/res/layout/fragment_details.xml index 59142eee..4a29dd2f 100644 --- a/app/src/main/res/layout/fragment_details.xml +++ b/app/src/main/res/layout/fragment_details.xml @@ -56,6 +56,7 @@ - - - - - - - - - - + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/app/src/main/res/layout/item_anime_details.xml b/app/src/main/res/layout/item_anime_details.xml new file mode 100644 index 00000000..c03842e9 --- /dev/null +++ b/app/src/main/res/layout/item_anime_details.xml @@ -0,0 +1,49 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/app/src/main/res/layout/item_card_anime_experimental.xml b/app/src/main/res/layout/item_card_anime_experimental.xml new file mode 100644 index 00000000..1b23963c --- /dev/null +++ b/app/src/main/res/layout/item_card_anime_experimental.xml @@ -0,0 +1,82 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/app/src/main/res/layout/item_horizontal_recycler.xml b/app/src/main/res/layout/item_horizontal_recycler.xml index 046d0959..951bd866 100644 --- a/app/src/main/res/layout/item_horizontal_recycler.xml +++ b/app/src/main/res/layout/item_horizontal_recycler.xml @@ -4,7 +4,7 @@ xmlns:tools="http://schemas.android.com/tools" android:id="@+id/innerRv" android:layout_width="match_parent" - android:layout_height="180dp" + android:layout_height="wrap_content" android:orientation="horizontal" app:layoutManager="androidx.recyclerview.widget.LinearLayoutManager" tools:listitem="@layout/item_card_anime"> diff --git a/app/src/main/res/values/colors.xml b/app/src/main/res/values/colors.xml index c5b4bc9d..1705eed9 100644 --- a/app/src/main/res/values/colors.xml +++ b/app/src/main/res/values/colors.xml @@ -26,13 +26,15 @@ #2B2C30 #2B2C30 - #111111 + @color/colorPrimary #048a81 #28a745 #007bff - + #17293F + #FFC42E + #A7A7A9 #048a81 #66B5B5B5 diff --git a/app/src/main/res/values/dimens.xml b/app/src/main/res/values/dimens.xml index a20e6848..87e7b2f7 100644 --- a/app/src/main/res/values/dimens.xml +++ b/app/src/main/res/values/dimens.xml @@ -14,4 +14,9 @@ 5dp 10dp 32dp + 8dp + 4dp + 20dp + 8dp + 20dp \ No newline at end of file diff --git a/app/src/main/res/values/themes.xml b/app/src/main/res/values/themes.xml index ce1d868f..d1acd122 100644 --- a/app/src/main/res/values/themes.xml +++ b/app/src/main/res/values/themes.xml @@ -61,6 +61,21 @@ true + + + + + + 1dp + 18sp + 14sp + 12sp + 24sp + 20sp + + + + + + + + \ No newline at end of file