mirror of
https://github.com/mihonapp/mihon.git
synced 2025-06-25 10:37:51 +02:00
Download badge
This commit is contained in:
@ -18,6 +18,8 @@ interface Manga : SManga {
|
||||
|
||||
var unread: Int
|
||||
|
||||
var downloadTotal: Int
|
||||
|
||||
var category: Int
|
||||
|
||||
fun setChapterOrder(order: Int) {
|
||||
|
@ -34,6 +34,8 @@ class MangaImpl : Manga {
|
||||
|
||||
@Transient override var unread: Int = 0
|
||||
|
||||
@Transient override var downloadTotal: Int = 0
|
||||
|
||||
@Transient override var category: Int = 0
|
||||
|
||||
override fun equals(other: Any?): Boolean {
|
||||
|
@ -105,6 +105,8 @@ object PreferenceKeys {
|
||||
|
||||
const val defaultCategory = "default_category"
|
||||
|
||||
const val downloadBadge = "pref_display_download_badge"
|
||||
|
||||
fun sourceUsername(sourceId: Long) = "pref_source_username_$sourceId"
|
||||
|
||||
fun sourcePassword(sourceId: Long) = "pref_source_password_$sourceId"
|
||||
|
@ -141,6 +141,8 @@ class PreferencesHelper(val context: Context) {
|
||||
|
||||
fun libraryAsList() = rxPrefs.getBoolean(Keys.libraryAsList, false)
|
||||
|
||||
fun downloadBadge() = rxPrefs.getBoolean(Keys.downloadBadge, false)
|
||||
|
||||
fun filterDownloaded() = rxPrefs.getBoolean(Keys.filterDownloaded, false)
|
||||
|
||||
fun filterUnread() = rxPrefs.getBoolean(Keys.filterUnread, false)
|
||||
|
@ -196,6 +196,7 @@ class LibraryController(
|
||||
is LibraryNavigationView.FilterGroup -> onFilterChanged()
|
||||
is LibraryNavigationView.SortGroup -> onSortChanged()
|
||||
is LibraryNavigationView.DisplayGroup -> reattachAdapter()
|
||||
is LibraryNavigationView.BadgeGroup -> onDownloadBadgeChanged()
|
||||
}
|
||||
}
|
||||
|
||||
@ -285,6 +286,10 @@ class LibraryController(
|
||||
(activity as? AppCompatActivity)?.supportInvalidateOptionsMenu()
|
||||
}
|
||||
|
||||
private fun onDownloadBadgeChanged(){
|
||||
presenter.requestDownloadBadgesUpdate()
|
||||
}
|
||||
|
||||
/**
|
||||
* Called when the sorting mode is changed.
|
||||
*/
|
||||
|
@ -5,7 +5,12 @@ import com.bumptech.glide.load.engine.DiskCacheStrategy
|
||||
import eu.davidea.flexibleadapter.FlexibleAdapter
|
||||
import eu.kanade.tachiyomi.data.database.models.Manga
|
||||
import eu.kanade.tachiyomi.data.glide.GlideApp
|
||||
import eu.kanade.tachiyomi.data.preference.PreferencesHelper
|
||||
import eu.kanade.tachiyomi.data.preference.getOrDefault
|
||||
import eu.kanade.tachiyomi.source.LocalSource
|
||||
import kotlinx.android.synthetic.main.catalogue_grid_item.view.*
|
||||
import uy.kohesive.injekt.Injekt
|
||||
import uy.kohesive.injekt.api.get
|
||||
|
||||
/**
|
||||
* Class used to hold the displayed data of a manga in the library, like the cover or the title.
|
||||
@ -19,7 +24,9 @@ import kotlinx.android.synthetic.main.catalogue_grid_item.view.*
|
||||
class LibraryGridHolder(
|
||||
private val view: View,
|
||||
private val adapter: FlexibleAdapter<*>
|
||||
|
||||
) : LibraryHolder(view, adapter) {
|
||||
private val preferences: PreferencesHelper = Injekt.get()
|
||||
|
||||
/**
|
||||
* Method called from [LibraryCategoryAdapter.onBindViewHolder]. It updates the data for this
|
||||
@ -36,6 +43,15 @@ class LibraryGridHolder(
|
||||
visibility = if (manga.unread > 0) View.VISIBLE else View.GONE
|
||||
text = manga.unread.toString()
|
||||
}
|
||||
// Update the download count and its visibility.
|
||||
with(view.download_text) {
|
||||
visibility = if (manga.downloadTotal > 0 && preferences.downloadBadge().getOrDefault()) View.VISIBLE else View.GONE
|
||||
text = manga.downloadTotal.toString()
|
||||
}
|
||||
//set local visibility if its local manga
|
||||
with(view.local_text){
|
||||
visibility = if(manga.source == LocalSource.ID) View.VISIBLE else View.GONE
|
||||
}
|
||||
|
||||
// Update the cover.
|
||||
GlideApp.with(view.context).clear(view.thumbnail)
|
||||
|
@ -5,7 +5,12 @@ import com.bumptech.glide.load.engine.DiskCacheStrategy
|
||||
import eu.davidea.flexibleadapter.FlexibleAdapter
|
||||
import eu.kanade.tachiyomi.data.database.models.Manga
|
||||
import eu.kanade.tachiyomi.data.glide.GlideApp
|
||||
import eu.kanade.tachiyomi.data.preference.PreferencesHelper
|
||||
import eu.kanade.tachiyomi.data.preference.getOrDefault
|
||||
import eu.kanade.tachiyomi.source.LocalSource
|
||||
import kotlinx.android.synthetic.main.catalogue_list_item.view.*
|
||||
import uy.kohesive.injekt.Injekt
|
||||
import uy.kohesive.injekt.api.get
|
||||
|
||||
/**
|
||||
* Class used to hold the displayed data of a manga in the library, like the cover or the title.
|
||||
@ -21,6 +26,7 @@ class LibraryListHolder(
|
||||
private val view: View,
|
||||
private val adapter: FlexibleAdapter<*>
|
||||
) : LibraryHolder(view, adapter) {
|
||||
private val preferences: PreferencesHelper = Injekt.get()
|
||||
|
||||
/**
|
||||
* Method called from [LibraryCategoryAdapter.onBindViewHolder]. It updates the data for this
|
||||
@ -37,6 +43,15 @@ class LibraryListHolder(
|
||||
visibility = if (manga.unread > 0) View.VISIBLE else View.GONE
|
||||
text = manga.unread.toString()
|
||||
}
|
||||
// Update the download count and its visibility.
|
||||
with(itemView.download_text) {
|
||||
visibility = if (manga.downloadTotal > 0 && preferences.downloadBadge().getOrDefault()) View.VISIBLE else View.GONE
|
||||
text = manga.downloadTotal.toString()
|
||||
}
|
||||
//show local text badge if local manga
|
||||
with(itemView.local_text) {
|
||||
visibility = if (manga.source == LocalSource.ID) View.VISIBLE else View.GONE
|
||||
}
|
||||
|
||||
// Create thumbnail onclick to simulate long click
|
||||
itemView.thumbnail.setOnClickListener {
|
||||
@ -55,4 +70,4 @@ class LibraryListHolder(
|
||||
.into(itemView.thumbnail)
|
||||
}
|
||||
|
||||
}
|
||||
}
|
||||
|
@ -25,7 +25,7 @@ class LibraryNavigationView @JvmOverloads constructor(context: Context, attrs: A
|
||||
/**
|
||||
* List of groups shown in the view.
|
||||
*/
|
||||
private val groups = listOf(FilterGroup(), SortGroup(), DisplayGroup())
|
||||
private val groups = listOf(FilterGroup(), SortGroup(), DisplayGroup(), BadgeGroup())
|
||||
|
||||
/**
|
||||
* Adapter instance.
|
||||
@ -166,6 +166,23 @@ class LibraryNavigationView @JvmOverloads constructor(context: Context, attrs: A
|
||||
|
||||
}
|
||||
|
||||
inner class BadgeGroup : Group {
|
||||
private val downloadBadge = Item.CheckboxGroup(R.string.action_display_download_badge, this)
|
||||
override val header = null
|
||||
override val footer= null
|
||||
override val items = listOf(downloadBadge)
|
||||
override fun initModels() {
|
||||
downloadBadge.checked = preferences.downloadBadge().getOrDefault()
|
||||
}
|
||||
|
||||
override fun onItemClicked(item: Item) {
|
||||
item as Item.CheckboxGroup
|
||||
item.checked = !item.checked
|
||||
preferences.downloadBadge().set((item.checked))
|
||||
adapter.notifyItemChanged(item)
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Display group, to show the library as a list or a grid.
|
||||
*/
|
||||
|
@ -53,6 +53,11 @@ class LibraryPresenter(
|
||||
*/
|
||||
private val filterTriggerRelay = BehaviorRelay.create(Unit)
|
||||
|
||||
/**
|
||||
* Relay used to apply the UI update to the last emission of the library.
|
||||
*/
|
||||
private val downloadTriggerRelay = BehaviorRelay.create(Unit)
|
||||
|
||||
/**
|
||||
* Relay used to apply the selected sorting method to the last emission of the library.
|
||||
*/
|
||||
@ -76,6 +81,8 @@ class LibraryPresenter(
|
||||
librarySubscription = getLibraryObservable()
|
||||
.combineLatest(filterTriggerRelay.observeOn(Schedulers.io()),
|
||||
{ lib, _ -> Pair(lib.first, applyFilters(lib.second)) })
|
||||
.combineLatest(downloadTriggerRelay.observeOn(Schedulers.io()),
|
||||
{ lib, _ -> Pair(lib.first, addDownloadTotal(lib.second)) })
|
||||
.combineLatest(sortTriggerRelay.observeOn(Schedulers.io()),
|
||||
{ lib, _ -> Pair(lib.first, applySort(lib.second)) })
|
||||
.map { Pair(it.first, it.second.mapValues { it.value.map(::LibraryItem) }) }
|
||||
@ -141,6 +148,48 @@ class LibraryPresenter(
|
||||
return map.mapValues { entry -> entry.value.filter(filterFn) }
|
||||
}
|
||||
|
||||
/**
|
||||
* Adds Downloaded chapter count to manga
|
||||
*
|
||||
* @param map the map to filter.
|
||||
*/
|
||||
private fun addDownloadTotal(map: Map<Int, List<Manga>>): Map<Int, List<Manga>> {
|
||||
// Cached list of downloaded manga directories given a source id.
|
||||
if (preferences.downloadBadge().getOrDefault()) {
|
||||
val mangaDirsForSource = mutableMapOf<Long, Map<String?, UniFile>>()
|
||||
|
||||
// Cached list of downloaded chapter directories for a manga.
|
||||
val chapterDirectories = mutableMapOf<Long, Int>()
|
||||
|
||||
for ((key, mangaList) in map) {
|
||||
for (manga in mangaList) {
|
||||
manga.downloadTotal = getDownloadedCountFromDirectory(manga, mangaDirsForSource, chapterDirectories)
|
||||
}
|
||||
}
|
||||
}
|
||||
return map;
|
||||
}
|
||||
|
||||
//Get count of downloaded chapters for a manga
|
||||
fun getDownloadedCountFromDirectory(manga: Manga, mangaDirsForSource: MutableMap<Long, Map<String?, UniFile>>, chapterDirectories: MutableMap<Long, Int>): Int {
|
||||
val source = sourceManager.get(manga.source) ?: return 0;
|
||||
// Get the directories for the source of the manga.
|
||||
val dirsForSource = mangaDirsForSource.getOrPut(source.id) {
|
||||
val sourceDir = downloadManager.findSourceDir(source)
|
||||
sourceDir?.listFiles()?.associateBy { it.name }.orEmpty()
|
||||
}
|
||||
val mangaDirName = downloadManager.getMangaDirName(manga)
|
||||
val mangaDir = dirsForSource[mangaDirName] ?: return 0
|
||||
|
||||
chapterDirectories.getOrPut(manga.id!!) {
|
||||
if (mangaDir.listFiles()?.isNotEmpty() ?: false) {
|
||||
return mangaDir.listFiles()!!.size
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
/**
|
||||
* Applies library sorting to the given map of manga.
|
||||
*
|
||||
@ -236,6 +285,13 @@ class LibraryPresenter(
|
||||
filterTriggerRelay.call(Unit)
|
||||
}
|
||||
|
||||
/**
|
||||
* Requests the library to have download badges added.
|
||||
*/
|
||||
fun requestDownloadBadgesUpdate() {
|
||||
downloadTriggerRelay.call(Unit)
|
||||
}
|
||||
|
||||
/**
|
||||
* Requests the library to be sorted.
|
||||
*/
|
||||
|
Reference in New Issue
Block a user