Covers now update automatcally with library, local covers instant change now

This commit is contained in:
Jay 2020-01-11 14:27:36 -08:00
parent 36c513b4c4
commit 73d1b6ac27
12 changed files with 47 additions and 4 deletions

View File

@ -36,6 +36,8 @@ open class MangaImpl : Manga {
override var hide_title: Boolean = false override var hide_title: Boolean = false
var last_cover_fetch: Long = 0
override fun copyFrom(other: SManga) { override fun copyFrom(other: SManga) {
if (other is MangaImpl && (other as MangaImpl)::title.isInitialized && other.title != title) if (other is MangaImpl && (other as MangaImpl)::title.isInitialized && other.title != title)
title = other.title title = other.title

View File

@ -14,6 +14,7 @@ import androidx.core.app.NotificationCompat.GROUP_ALERT_SUMMARY
import androidx.core.app.NotificationManagerCompat import androidx.core.app.NotificationManagerCompat
import androidx.core.content.ContextCompat import androidx.core.content.ContextCompat
import eu.kanade.tachiyomi.R import eu.kanade.tachiyomi.R
import eu.kanade.tachiyomi.data.cache.CoverCache
import eu.kanade.tachiyomi.data.database.DatabaseHelper import eu.kanade.tachiyomi.data.database.DatabaseHelper
import eu.kanade.tachiyomi.data.database.models.Category import eu.kanade.tachiyomi.data.database.models.Category
import eu.kanade.tachiyomi.data.database.models.Chapter import eu.kanade.tachiyomi.data.database.models.Chapter
@ -48,7 +49,9 @@ import rx.schedulers.Schedulers
import timber.log.Timber import timber.log.Timber
import uy.kohesive.injekt.Injekt import uy.kohesive.injekt.Injekt
import uy.kohesive.injekt.api.get import uy.kohesive.injekt.api.get
import uy.kohesive.injekt.injectLazy
import java.util.ArrayList import java.util.ArrayList
import java.util.Date
import java.util.concurrent.atomic.AtomicInteger import java.util.concurrent.atomic.AtomicInteger
/** /**
@ -292,7 +295,7 @@ class LibraryUpdateService(
// Initialize the variables holding the progress of the updates. // Initialize the variables holding the progress of the updates.
val count = AtomicInteger(0) val count = AtomicInteger(0)
// List containing new updates // List containing new updates
val newUpdates = ArrayList<Pair<Manga, Array<Chapter>>>() val newUpdates = ArrayList<Pair<LibraryManga, Array<Chapter>>>()
// list containing failed updates // list containing failed updates
val failedUpdates = ArrayList<Manga>() val failedUpdates = ArrayList<Manga>()
// List containing categories that get included in downloads. // List containing categories that get included in downloads.
@ -340,6 +343,10 @@ class LibraryUpdateService(
if (downloadNew && hasDownloads) { if (downloadNew && hasDownloads) {
DownloadService.start(this) DownloadService.start(this)
} }
if (preferences.refreshCoversToo().getOrDefault()) {
updateDetails(newUpdates.map { it.first }).observeOn(Schedulers.io())
.subscribeOn(Schedulers.io()).subscribe {}
}
} }
if (failedUpdates.isNotEmpty()) { if (failedUpdates.isNotEmpty()) {
@ -393,6 +400,7 @@ class LibraryUpdateService(
fun updateDetails(mangaToUpdate: List<LibraryManga>): Observable<LibraryManga> { fun updateDetails(mangaToUpdate: List<LibraryManga>): Observable<LibraryManga> {
// Initialize the variables holding the progress of the updates. // Initialize the variables holding the progress of the updates.
val count = AtomicInteger(0) val count = AtomicInteger(0)
val coverCache by injectLazy<CoverCache>()
// Emit each manga and update it sequentially. // Emit each manga and update it sequentially.
return Observable.from(mangaToUpdate) return Observable.from(mangaToUpdate)
@ -407,6 +415,8 @@ class LibraryUpdateService(
.map { networkManga -> .map { networkManga ->
manga.copyFrom(networkManga) manga.copyFrom(networkManga)
db.insertManga(manga).executeAsBlocking() db.insertManga(manga).executeAsBlocking()
coverCache.deleteFromCache(manga.thumbnail_url)
manga.last_cover_fetch = Date().time
manga manga
} }
.onErrorReturn { manga } .onErrorReturn { manga }

View File

@ -129,6 +129,8 @@ object PreferenceKeys {
const val skipPreMigration = "skip_pre_migration" const val skipPreMigration = "skip_pre_migration"
const val refreshCoversToo = "refresh_covers_too"
@Deprecated("Use the preferences of the source") @Deprecated("Use the preferences of the source")
fun sourceUsername(sourceId: Long) = "pref_source_username_$sourceId" fun sourceUsername(sourceId: Long) = "pref_source_username_$sourceId"

View File

@ -199,6 +199,8 @@ class PreferencesHelper(val context: Context) {
fun defaultMangaOrder() = rxPrefs.getString("default_manga_order", "") fun defaultMangaOrder() = rxPrefs.getString("default_manga_order", "")
fun refreshCoversToo() = rxPrefs.getBoolean(Keys.refreshCoversToo, true)
fun upgradeFilters() { fun upgradeFilters() {
val filterDl = rxPrefs.getBoolean(Keys.filterDownloaded, false).getOrDefault() val filterDl = rxPrefs.getBoolean(Keys.filterDownloaded, false).getOrDefault()
val filterUn = rxPrefs.getBoolean(Keys.filterUnread, false).getOrDefault() val filterUn = rxPrefs.getBoolean(Keys.filterUnread, false).getOrDefault()

View File

@ -1,13 +1,14 @@
package eu.kanade.tachiyomi.ui.library package eu.kanade.tachiyomi.ui.library
import android.view.View import android.view.View
import androidx.recyclerview.widget.RecyclerView
import com.bumptech.glide.load.engine.DiskCacheStrategy import com.bumptech.glide.load.engine.DiskCacheStrategy
import com.bumptech.glide.signature.ObjectKey
import eu.davidea.flexibleadapter.FlexibleAdapter import eu.davidea.flexibleadapter.FlexibleAdapter
import eu.davidea.flexibleadapter.items.IFlexible
import eu.kanade.tachiyomi.data.glide.GlideApp import eu.kanade.tachiyomi.data.glide.GlideApp
import eu.kanade.tachiyomi.source.LocalSource import eu.kanade.tachiyomi.source.LocalSource
import kotlinx.android.synthetic.main.catalogue_grid_item.* import kotlinx.android.synthetic.main.catalogue_grid_item.*
import androidx.recyclerview.widget.RecyclerView
import eu.davidea.flexibleadapter.items.IFlexible
/** /**
* Class used to hold the displayed data of a manga in the library, like the cover or the title. * Class used to hold the displayed data of a manga in the library, like the cover or the title.
@ -56,6 +57,7 @@ class LibraryGridHolder(
GlideApp.with(view.context) GlideApp.with(view.context)
.load(item.manga) .load(item.manga)
.diskCacheStrategy(DiskCacheStrategy.RESOURCE) .diskCacheStrategy(DiskCacheStrategy.RESOURCE)
.signature(ObjectKey(item.manga.last_cover_fetch.toString()))
.centerCrop() .centerCrop()
.into(thumbnail) .into(thumbnail)
} }

View File

@ -7,6 +7,7 @@ import eu.kanade.tachiyomi.data.glide.GlideApp
import eu.kanade.tachiyomi.source.LocalSource import eu.kanade.tachiyomi.source.LocalSource
import kotlinx.android.synthetic.main.catalogue_list_item.* import kotlinx.android.synthetic.main.catalogue_list_item.*
import androidx.recyclerview.widget.RecyclerView import androidx.recyclerview.widget.RecyclerView
import com.bumptech.glide.signature.ObjectKey
import eu.davidea.flexibleadapter.items.IFlexible import eu.davidea.flexibleadapter.items.IFlexible
/** /**
@ -58,6 +59,7 @@ class LibraryListHolder(
GlideApp.with(itemView.context) GlideApp.with(itemView.context)
.load(item.manga) .load(item.manga)
.diskCacheStrategy(DiskCacheStrategy.RESOURCE) .diskCacheStrategy(DiskCacheStrategy.RESOURCE)
.signature(ObjectKey(item.manga.last_cover_fetch.toString()))
.centerCrop() .centerCrop()
.circleCrop() .circleCrop()
.dontAnimate() .dontAnimate()

View File

@ -7,6 +7,7 @@ import eu.kanade.tachiyomi.data.database.DatabaseHelper
import eu.kanade.tachiyomi.data.database.models.Category import eu.kanade.tachiyomi.data.database.models.Category
import eu.kanade.tachiyomi.data.database.models.Manga import eu.kanade.tachiyomi.data.database.models.Manga
import eu.kanade.tachiyomi.data.database.models.MangaCategory import eu.kanade.tachiyomi.data.database.models.MangaCategory
import eu.kanade.tachiyomi.data.database.models.MangaImpl
import eu.kanade.tachiyomi.data.download.DownloadManager import eu.kanade.tachiyomi.data.download.DownloadManager
import eu.kanade.tachiyomi.data.preference.PreferencesHelper import eu.kanade.tachiyomi.data.preference.PreferencesHelper
import eu.kanade.tachiyomi.data.preference.getOrDefault import eu.kanade.tachiyomi.data.preference.getOrDefault
@ -36,6 +37,7 @@ import java.io.InputStream
import java.util.ArrayList import java.util.ArrayList
import java.util.Collections import java.util.Collections
import java.util.Comparator import java.util.Comparator
import java.util.Date
/** /**
* Class containing library information. * Class containing library information.
@ -464,6 +466,7 @@ class LibraryPresenter(
if (manga.thumbnail_url != null && manga.favorite) { if (manga.thumbnail_url != null && manga.favorite) {
coverCache.copyToCache(manga.thumbnail_url!!, inputStream) coverCache.copyToCache(manga.thumbnail_url!!, inputStream)
(manga as? MangaImpl)?.last_cover_fetch = Date().time
return true return true
} }
return false return false

View File

@ -28,6 +28,7 @@ import com.bumptech.glide.load.resource.bitmap.RoundedCorners
import com.bumptech.glide.request.RequestListener import com.bumptech.glide.request.RequestListener
import com.bumptech.glide.request.target.CustomTarget import com.bumptech.glide.request.target.CustomTarget
import com.bumptech.glide.request.transition.Transition import com.bumptech.glide.request.transition.Transition
import com.bumptech.glide.signature.ObjectKey
import com.google.android.material.snackbar.BaseTransientBottomBar import com.google.android.material.snackbar.BaseTransientBottomBar
import com.google.android.material.snackbar.Snackbar import com.google.android.material.snackbar.Snackbar
import com.jakewharton.rxbinding.support.v4.widget.refreshes import com.jakewharton.rxbinding.support.v4.widget.refreshes
@ -36,6 +37,7 @@ import com.jakewharton.rxbinding.view.longClicks
import eu.kanade.tachiyomi.R import eu.kanade.tachiyomi.R
import eu.kanade.tachiyomi.data.database.models.Category import eu.kanade.tachiyomi.data.database.models.Category
import eu.kanade.tachiyomi.data.database.models.Manga import eu.kanade.tachiyomi.data.database.models.Manga
import eu.kanade.tachiyomi.data.database.models.MangaImpl
import eu.kanade.tachiyomi.data.glide.GlideApp import eu.kanade.tachiyomi.data.glide.GlideApp
import eu.kanade.tachiyomi.data.notification.NotificationReceiver import eu.kanade.tachiyomi.data.notification.NotificationReceiver
import eu.kanade.tachiyomi.data.preference.PreferencesHelper import eu.kanade.tachiyomi.data.preference.PreferencesHelper
@ -60,6 +62,7 @@ import eu.kanade.tachiyomi.util.updateLayoutParams
import eu.kanade.tachiyomi.util.updatePaddingRelative import eu.kanade.tachiyomi.util.updatePaddingRelative
import jp.wasabeef.glide.transformations.CropSquareTransformation import jp.wasabeef.glide.transformations.CropSquareTransformation
import jp.wasabeef.glide.transformations.MaskTransformation import jp.wasabeef.glide.transformations.MaskTransformation
import kotlinx.android.synthetic.main.catalogue_list_item.*
import kotlinx.android.synthetic.main.manga_info_controller.* import kotlinx.android.synthetic.main.manga_info_controller.*
import uy.kohesive.injekt.injectLazy import uy.kohesive.injekt.injectLazy
import java.io.File import java.io.File
@ -269,17 +272,20 @@ class MangaInfoController : NucleusController<MangaInfoPresenter>(),
setFavoriteDrawable(manga.favorite) setFavoriteDrawable(manga.favorite)
// Set cover if it wasn't already. // Set cover if it wasn't already.
if (manga_cover.drawable == null && !manga.thumbnail_url.isNullOrEmpty()) { if (!manga.thumbnail_url.isNullOrEmpty()) {
GlideApp.with(view.context) GlideApp.with(view.context)
.load(manga) .load(manga)
.diskCacheStrategy(DiskCacheStrategy.RESOURCE) .diskCacheStrategy(DiskCacheStrategy.RESOURCE)
.signature(ObjectKey((manga as MangaImpl).last_cover_fetch.toString()))
.centerCrop() .centerCrop()
.into(manga_cover) .into(manga_cover)
if (backdrop != null) { if (backdrop != null) {
//GlideApp.with(view.context).clear(backdrop)
GlideApp.with(view.context) GlideApp.with(view.context)
.load(manga) .load(manga)
.diskCacheStrategy(DiskCacheStrategy.RESOURCE) .diskCacheStrategy(DiskCacheStrategy.RESOURCE)
.signature(ObjectKey((manga as MangaImpl).last_cover_fetch.toString()))
.centerCrop() .centerCrop()
.into(backdrop) .into(backdrop)
} }

View File

@ -10,6 +10,7 @@ import eu.kanade.tachiyomi.data.database.DatabaseHelper
import eu.kanade.tachiyomi.data.database.models.Category import eu.kanade.tachiyomi.data.database.models.Category
import eu.kanade.tachiyomi.data.database.models.Manga import eu.kanade.tachiyomi.data.database.models.Manga
import eu.kanade.tachiyomi.data.database.models.MangaCategory import eu.kanade.tachiyomi.data.database.models.MangaCategory
import eu.kanade.tachiyomi.data.database.models.MangaImpl
import eu.kanade.tachiyomi.data.download.DownloadManager import eu.kanade.tachiyomi.data.download.DownloadManager
import eu.kanade.tachiyomi.source.Source import eu.kanade.tachiyomi.source.Source
import eu.kanade.tachiyomi.ui.base.presenter.BasePresenter import eu.kanade.tachiyomi.ui.base.presenter.BasePresenter
@ -92,6 +93,8 @@ class MangaInfoPresenter(
manga.copyFrom(networkManga) manga.copyFrom(networkManga)
manga.initialized = true manga.initialized = true
db.insertManga(manga).executeAsBlocking() db.insertManga(manga).executeAsBlocking()
coverCache.deleteFromCache(manga.thumbnail_url)
(manga as? MangaImpl)?.last_cover_fetch = Date().time
manga manga
} }
.subscribeOn(Schedulers.io()) .subscribeOn(Schedulers.io())

View File

@ -9,6 +9,7 @@ import eu.kanade.tachiyomi.data.cache.CoverCache
import eu.kanade.tachiyomi.data.database.DatabaseHelper import eu.kanade.tachiyomi.data.database.DatabaseHelper
import eu.kanade.tachiyomi.data.database.models.History import eu.kanade.tachiyomi.data.database.models.History
import eu.kanade.tachiyomi.data.database.models.Manga import eu.kanade.tachiyomi.data.database.models.Manga
import eu.kanade.tachiyomi.data.database.models.MangaImpl
import eu.kanade.tachiyomi.data.download.DownloadManager import eu.kanade.tachiyomi.data.download.DownloadManager
import eu.kanade.tachiyomi.data.preference.PreferencesHelper import eu.kanade.tachiyomi.data.preference.PreferencesHelper
import eu.kanade.tachiyomi.data.track.TrackManager import eu.kanade.tachiyomi.data.track.TrackManager
@ -530,6 +531,7 @@ class ReaderPresenter(
val thumbUrl = manga.thumbnail_url ?: throw Exception("Image url not found") val thumbUrl = manga.thumbnail_url ?: throw Exception("Image url not found")
if (manga.favorite) { if (manga.favorite) {
coverCache.copyToCache(thumbUrl, stream()) coverCache.copyToCache(thumbUrl, stream())
(manga as? MangaImpl)?.last_cover_fetch = Date().time
SetAsCoverResult.Success SetAsCoverResult.Success
} else { } else {
SetAsCoverResult.AddToLibraryFirst SetAsCoverResult.AddToLibraryFirst

View File

@ -170,6 +170,12 @@ class SettingsLibraryController : SettingsController() {
summaryRes = R.string.pref_remove_articles_summary summaryRes = R.string.pref_remove_articles_summary
defaultValue = false defaultValue = false
} }
switchPreference {
key = Keys.refreshCoversToo
titleRes = R.string.pref_refresh_covers_too
summaryRes = R.string.pref_refresh_covers_too_summary
defaultValue = true
}
} }
class LibraryColumnsDialog : DialogController() { class LibraryColumnsDialog : DialogController() {

View File

@ -190,6 +190,9 @@
<string name="lock_never">Never</string> <string name="lock_never">Never</string>
<string name="lock_after_mins">After %1$s minutes</string> <string name="lock_after_mins">After %1$s minutes</string>
<string name="search_hint">Search title, tags, source</string> <string name="search_hint">Search title, tags, source</string>
<string name="pref_refresh_covers_too">Automatically refresh covers</string>
<string name="pref_refresh_covers_too_summary">Refresh covers in library as well
when updating library (overwrites local covers)</string>
<!-- Extension section --> <!-- Extension section -->
<string name="all_lang">All</string> <string name="all_lang">All</string>