(Temporary) remove chapters list from downloads
This commit is contained in:
@@ -18,8 +18,7 @@ data class DownloadState(
|
||||
val currentPage: Int = 0,
|
||||
val eta: Long = -1L,
|
||||
val localManga: LocalManga? = null,
|
||||
val downloadedChapters: LongArray = LongArray(0),
|
||||
val scheduledChapters: LongArray = LongArray(0),
|
||||
val downloadedChapters: Int = 0,
|
||||
val timestamp: Long = System.currentTimeMillis(),
|
||||
) {
|
||||
|
||||
@@ -42,68 +41,17 @@ data class DownloadState(
|
||||
.putLong(DATA_ETA, eta)
|
||||
.putLong(DATA_TIMESTAMP, timestamp)
|
||||
.putString(DATA_ERROR, error)
|
||||
.putLongArray(DATA_CHAPTERS, downloadedChapters)
|
||||
.putLongArray(DATA_CHAPTERS_SRC, scheduledChapters)
|
||||
.putInt(DATA_CHAPTERS, downloadedChapters)
|
||||
.putBoolean(DATA_INDETERMINATE, isIndeterminate)
|
||||
.putBoolean(DATA_PAUSED, isPaused)
|
||||
.build()
|
||||
|
||||
override fun equals(other: Any?): Boolean {
|
||||
if (this === other) return true
|
||||
if (javaClass != other?.javaClass) return false
|
||||
|
||||
other as DownloadState
|
||||
|
||||
if (manga != other.manga) return false
|
||||
if (isIndeterminate != other.isIndeterminate) return false
|
||||
if (isPaused != other.isPaused) return false
|
||||
if (isStopped != other.isStopped) return false
|
||||
if (error != other.error) return false
|
||||
if (totalChapters != other.totalChapters) return false
|
||||
if (currentChapter != other.currentChapter) return false
|
||||
if (totalPages != other.totalPages) return false
|
||||
if (currentPage != other.currentPage) return false
|
||||
if (eta != other.eta) return false
|
||||
if (localManga != other.localManga) return false
|
||||
if (!downloadedChapters.contentEquals(other.downloadedChapters)) return false
|
||||
if (!scheduledChapters.contentEquals(other.scheduledChapters)) return false
|
||||
if (timestamp != other.timestamp) return false
|
||||
if (max != other.max) return false
|
||||
if (progress != other.progress) return false
|
||||
if (percent != other.percent) return false
|
||||
|
||||
return true
|
||||
}
|
||||
|
||||
override fun hashCode(): Int {
|
||||
var result = manga.hashCode()
|
||||
result = 31 * result + isIndeterminate.hashCode()
|
||||
result = 31 * result + isPaused.hashCode()
|
||||
result = 31 * result + isStopped.hashCode()
|
||||
result = 31 * result + (error?.hashCode() ?: 0)
|
||||
result = 31 * result + totalChapters
|
||||
result = 31 * result + currentChapter
|
||||
result = 31 * result + totalPages
|
||||
result = 31 * result + currentPage
|
||||
result = 31 * result + eta.hashCode()
|
||||
result = 31 * result + (localManga?.hashCode() ?: 0)
|
||||
result = 31 * result + downloadedChapters.contentHashCode()
|
||||
result = 31 * result + scheduledChapters.contentHashCode()
|
||||
result = 31 * result + timestamp.hashCode()
|
||||
result = 31 * result + max
|
||||
result = 31 * result + progress
|
||||
result = 31 * result + percent.hashCode()
|
||||
return result
|
||||
}
|
||||
|
||||
|
||||
companion object {
|
||||
|
||||
private const val DATA_MANGA_ID = "manga_id"
|
||||
private const val DATA_MAX = "max"
|
||||
private const val DATA_PROGRESS = "progress"
|
||||
private const val DATA_CHAPTERS = "chapter"
|
||||
private const val DATA_CHAPTERS_SRC = "chapters_src"
|
||||
private const val DATA_CHAPTERS = "chapter_cnt"
|
||||
private const val DATA_ETA = "eta"
|
||||
private const val DATA_TIMESTAMP = "timestamp"
|
||||
private const val DATA_ERROR = "error"
|
||||
@@ -126,8 +74,6 @@ data class DownloadState(
|
||||
|
||||
fun getTimestamp(data: Data): Date = Date(data.getLong(DATA_TIMESTAMP, 0L))
|
||||
|
||||
fun getDownloadedChapters(data: Data): LongArray = data.getLongArray(DATA_CHAPTERS) ?: LongArray(0)
|
||||
|
||||
fun getScheduledChapters(data: Data): LongArray = data.getLongArray(DATA_CHAPTERS_SRC) ?: LongArray(0)
|
||||
fun getDownloadedChapters(data: Data): Int = data.getInt(DATA_CHAPTERS, 0)
|
||||
}
|
||||
}
|
||||
|
||||
@@ -2,28 +2,20 @@ package org.koitharu.kotatsu.download.ui.list
|
||||
|
||||
import android.transition.TransitionManager
|
||||
import android.view.View
|
||||
import androidx.core.content.ContextCompat
|
||||
import androidx.core.view.isVisible
|
||||
import androidx.lifecycle.LifecycleOwner
|
||||
import androidx.recyclerview.widget.DividerItemDecoration
|
||||
import androidx.recyclerview.widget.RecyclerView
|
||||
import androidx.work.WorkInfo
|
||||
import coil.ImageLoader
|
||||
import com.hannesdorfmann.adapterdelegates4.dsl.adapterDelegateViewBinding
|
||||
import org.koitharu.kotatsu.R
|
||||
import org.koitharu.kotatsu.core.ui.BaseListAdapter
|
||||
import org.koitharu.kotatsu.core.ui.image.TrimTransformation
|
||||
import org.koitharu.kotatsu.core.util.ext.drawableEnd
|
||||
import org.koitharu.kotatsu.core.util.ext.enqueueWith
|
||||
import org.koitharu.kotatsu.core.util.ext.isAnimationsEnabled
|
||||
import org.koitharu.kotatsu.core.util.ext.newImageRequest
|
||||
import org.koitharu.kotatsu.core.util.ext.source
|
||||
import org.koitharu.kotatsu.core.util.ext.textAndVisible
|
||||
import org.koitharu.kotatsu.databinding.ItemDownloadBinding
|
||||
import org.koitharu.kotatsu.download.ui.list.chapters.DownloadChapter
|
||||
import org.koitharu.kotatsu.download.ui.list.chapters.downloadChapterAD
|
||||
import org.koitharu.kotatsu.list.ui.ListModelDiffCallback
|
||||
import org.koitharu.kotatsu.list.ui.adapter.ListItemType
|
||||
import org.koitharu.kotatsu.list.ui.model.ListModel
|
||||
import org.koitharu.kotatsu.parsers.util.format
|
||||
|
||||
@@ -36,9 +28,7 @@ fun downloadItemAD(
|
||||
) {
|
||||
|
||||
val percentPattern = context.resources.getString(R.string.percent_string_pattern)
|
||||
val expandIcon = ContextCompat.getDrawable(context, R.drawable.ic_expand_collapse)
|
||||
val chaptersAdapter = BaseListAdapter<DownloadChapter>()
|
||||
.addDelegate(ListItemType.CHAPTER, downloadChapterAD())
|
||||
// val expandIcon = ContextCompat.getDrawable(context, R.drawable.ic_expand_collapse)
|
||||
|
||||
val clickListener = object : View.OnClickListener, View.OnLongClickListener {
|
||||
override fun onClick(v: View) {
|
||||
@@ -59,8 +49,6 @@ fun downloadItemAD(
|
||||
binding.buttonResume.setOnClickListener(clickListener)
|
||||
itemView.setOnClickListener(clickListener)
|
||||
itemView.setOnLongClickListener(clickListener)
|
||||
binding.recyclerViewChapters.addItemDecoration(DividerItemDecoration(context, RecyclerView.VERTICAL))
|
||||
binding.recyclerViewChapters.adapter = chaptersAdapter
|
||||
|
||||
bind { payloads ->
|
||||
if (ListModelDiffCallback.PAYLOAD_CHECKED_CHANGED in payloads && context.isAnimationsEnabled) {
|
||||
@@ -76,10 +64,8 @@ fun downloadItemAD(
|
||||
source(item.manga.source)
|
||||
enqueueWith(coil)
|
||||
}
|
||||
binding.textViewTitle.isChecked = item.isExpanded
|
||||
binding.textViewTitle.drawableEnd = if (item.isExpandable) expandIcon else null
|
||||
binding.cardDetails.isVisible = item.isExpanded
|
||||
chaptersAdapter.items = item.chapters
|
||||
// binding.textViewTitle.isChecked = item.isExpanded
|
||||
// binding.textViewTitle.drawableEnd = if (item.isExpandable) expandIcon else null
|
||||
when (item.workState) {
|
||||
WorkInfo.State.ENQUEUED,
|
||||
WorkInfo.State.BLOCKED -> {
|
||||
@@ -117,11 +103,11 @@ fun downloadItemAD(
|
||||
binding.progressBar.isVisible = false
|
||||
binding.progressBar.isEnabled = true
|
||||
binding.textViewPercent.isVisible = false
|
||||
if (item.totalChapters > 0) {
|
||||
if (item.chaptersDownloaded > 0) {
|
||||
binding.textViewDetails.text = context.resources.getQuantityString(
|
||||
R.plurals.chapters,
|
||||
item.totalChapters,
|
||||
item.totalChapters,
|
||||
item.chaptersDownloaded,
|
||||
item.chaptersDownloaded,
|
||||
)
|
||||
binding.textViewDetails.isVisible = true
|
||||
} else {
|
||||
|
||||
@@ -2,7 +2,6 @@ package org.koitharu.kotatsu.download.ui.list
|
||||
|
||||
import android.text.format.DateUtils
|
||||
import androidx.work.WorkInfo
|
||||
import org.koitharu.kotatsu.download.ui.list.chapters.DownloadChapter
|
||||
import org.koitharu.kotatsu.list.ui.ListModelDiffCallback
|
||||
import org.koitharu.kotatsu.list.ui.model.ListModel
|
||||
import org.koitharu.kotatsu.parsers.model.Manga
|
||||
@@ -17,11 +16,10 @@ data class DownloadItemModel(
|
||||
val manga: Manga,
|
||||
val error: String?,
|
||||
val max: Int,
|
||||
val totalChapters: Int,
|
||||
val progress: Int,
|
||||
val eta: Long,
|
||||
val timestamp: Date,
|
||||
val chapters: List<DownloadChapter>,
|
||||
val chaptersDownloaded: Int,
|
||||
val isExpanded: Boolean,
|
||||
) : ListModel, Comparable<DownloadItemModel> {
|
||||
|
||||
@@ -38,7 +36,7 @@ data class DownloadItemModel(
|
||||
get() = workState == WorkInfo.State.RUNNING && isPaused
|
||||
|
||||
val isExpandable: Boolean
|
||||
get() = chapters.isNotEmpty()
|
||||
get() = false // TODO
|
||||
|
||||
fun getEtaString(): CharSequence? = if (hasEta) {
|
||||
DateUtils.getRelativeTimeSpanString(
|
||||
|
||||
@@ -28,7 +28,6 @@ import org.koitharu.kotatsu.core.util.ext.MutableEventFlow
|
||||
import org.koitharu.kotatsu.core.util.ext.call
|
||||
import org.koitharu.kotatsu.core.util.ext.daysDiff
|
||||
import org.koitharu.kotatsu.download.domain.DownloadState
|
||||
import org.koitharu.kotatsu.download.ui.list.chapters.DownloadChapter
|
||||
import org.koitharu.kotatsu.download.ui.worker.DownloadWorker
|
||||
import org.koitharu.kotatsu.list.ui.model.EmptyState
|
||||
import org.koitharu.kotatsu.list.ui.model.ListHeader
|
||||
@@ -239,8 +238,6 @@ class DownloadsViewModel @Inject constructor(
|
||||
val mangaId = DownloadState.getMangaId(workData)
|
||||
if (mangaId == 0L) return null
|
||||
val manga = getManga(mangaId) ?: return null
|
||||
val downloadedChapters = DownloadState.getDownloadedChapters(workData)
|
||||
val scheduledChapters = DownloadState.getScheduledChapters(workData).toSet()
|
||||
return DownloadItemModel(
|
||||
id = id,
|
||||
workState = state,
|
||||
@@ -252,19 +249,8 @@ class DownloadsViewModel @Inject constructor(
|
||||
progress = DownloadState.getProgress(workData),
|
||||
eta = DownloadState.getEta(workData),
|
||||
timestamp = DownloadState.getTimestamp(workData),
|
||||
totalChapters = downloadedChapters.size,
|
||||
chaptersDownloaded = DownloadState.getDownloadedChapters(workData),
|
||||
isExpanded = isExpanded,
|
||||
chapters = manga.chapters?.mapNotNull {
|
||||
if (it.id in scheduledChapters) {
|
||||
DownloadChapter(
|
||||
number = it.number,
|
||||
name = it.name,
|
||||
isDownloaded = it.id in downloadedChapters,
|
||||
)
|
||||
} else {
|
||||
null
|
||||
}
|
||||
}.orEmpty(),
|
||||
)
|
||||
}
|
||||
|
||||
|
||||
@@ -38,6 +38,7 @@ import okio.buffer
|
||||
import okio.sink
|
||||
import org.koitharu.kotatsu.R
|
||||
import org.koitharu.kotatsu.core.exceptions.TooManyRequestExceptions
|
||||
import org.koitharu.kotatsu.core.model.ids
|
||||
import org.koitharu.kotatsu.core.network.CommonHeaders
|
||||
import org.koitharu.kotatsu.core.network.MangaHttpClient
|
||||
import org.koitharu.kotatsu.core.parser.MangaDataRepository
|
||||
@@ -46,7 +47,6 @@ import org.koitharu.kotatsu.core.prefs.AppSettings
|
||||
import org.koitharu.kotatsu.core.util.Throttler
|
||||
import org.koitharu.kotatsu.core.util.ext.awaitFinishedWorkInfosByTag
|
||||
import org.koitharu.kotatsu.core.util.ext.awaitUpdateWork
|
||||
import org.koitharu.kotatsu.core.util.ext.awaitWorkInfoById
|
||||
import org.koitharu.kotatsu.core.util.ext.awaitWorkInfosByTag
|
||||
import org.koitharu.kotatsu.core.util.ext.deleteAwait
|
||||
import org.koitharu.kotatsu.core.util.ext.deleteWork
|
||||
@@ -106,10 +106,10 @@ class DownloadWorker @AssistedInject constructor(
|
||||
val mangaId = inputData.getLong(MANGA_ID, 0L)
|
||||
val manga = mangaDataRepository.findMangaById(mangaId) ?: return Result.failure()
|
||||
val chaptersIds = inputData.getLongArray(CHAPTERS_IDS)?.takeUnless { it.isEmpty() }
|
||||
val downloadedIds = getDoneChapters()
|
||||
lastPublishedState = DownloadState(manga, isIndeterminate = true)
|
||||
val downloadedIds = getDoneChapters(manga)
|
||||
publishState(DownloadState(manga, isIndeterminate = true))
|
||||
return try {
|
||||
downloadMangaImpl(chaptersIds, downloadedIds)
|
||||
downloadMangaImpl(manga, chaptersIds, downloadedIds)
|
||||
Result.success(currentState.toWorkData())
|
||||
} catch (e: CancellationException) {
|
||||
withContext(NonCancellable) {
|
||||
@@ -147,10 +147,11 @@ class DownloadWorker @AssistedInject constructor(
|
||||
}
|
||||
|
||||
private suspend fun downloadMangaImpl(
|
||||
subject: Manga,
|
||||
includedIds: LongArray?,
|
||||
excludedIds: LongArray,
|
||||
excludedIds: Set<Long>,
|
||||
) {
|
||||
var manga = currentState.manga
|
||||
var manga = subject
|
||||
val chaptersToSkip = excludedIds.toMutableSet()
|
||||
withMangaLock(manga) {
|
||||
ContextCompat.registerReceiver(
|
||||
@@ -178,16 +179,9 @@ class DownloadWorker @AssistedInject constructor(
|
||||
}
|
||||
}
|
||||
val chapters = getChapters(mangaDetails, includedIds)
|
||||
publishState(
|
||||
currentState.copy(scheduledChapters = LongArray(chapters.size) { i -> chapters[i].id }),
|
||||
)
|
||||
for ((chapterIndex, chapter) in chapters.withIndex()) {
|
||||
if (chaptersToSkip.remove(chapter.id)) {
|
||||
publishState(
|
||||
currentState.copy(
|
||||
downloadedChapters = currentState.downloadedChapters + chapter.id,
|
||||
),
|
||||
)
|
||||
publishState(currentState.copy(downloadedChapters = currentState.downloadedChapters + 1))
|
||||
continue
|
||||
}
|
||||
val pages = runFailsafe(pausingHandle) {
|
||||
@@ -225,11 +219,7 @@ class DownloadWorker @AssistedInject constructor(
|
||||
localStorageChanges.emit(LocalMangaInput.of(output.rootFile).getManga())
|
||||
}.onFailure(Throwable::printStackTraceDebug)
|
||||
}
|
||||
publishState(
|
||||
currentState.copy(
|
||||
downloadedChapters = currentState.downloadedChapters + chapter.id,
|
||||
),
|
||||
)
|
||||
publishState(currentState.copy(downloadedChapters = currentState.downloadedChapters + 1))
|
||||
}
|
||||
publishState(currentState.copy(isIndeterminate = true, eta = -1L))
|
||||
output.mergeWithExisting()
|
||||
@@ -336,11 +326,9 @@ class DownloadWorker @AssistedInject constructor(
|
||||
setProgress(state.toWorkData())
|
||||
}
|
||||
|
||||
private suspend fun getDoneChapters(): LongArray {
|
||||
val work = WorkManager.getInstance(applicationContext).awaitWorkInfoById(id)
|
||||
?: return LongArray(0)
|
||||
return DownloadState.getDownloadedChapters(work.progress)
|
||||
}
|
||||
private suspend fun getDoneChapters(manga: Manga) = runCatchingCancellable {
|
||||
localMangaRepository.getDetails(manga).chapters?.ids()
|
||||
}.getOrNull().orEmpty()
|
||||
|
||||
private fun getChapters(
|
||||
manga: Manga,
|
||||
|
||||
@@ -104,31 +104,6 @@
|
||||
app:layout_constraintTop_toBottomOf="@id/textView_status"
|
||||
tools:text="@tools:sample/lorem[3]" />
|
||||
|
||||
<com.google.android.material.card.MaterialCardView
|
||||
android:id="@+id/card_details"
|
||||
android:layout_width="0dp"
|
||||
android:layout_height="0dp"
|
||||
android:layout_marginHorizontal="12dp"
|
||||
android:layout_marginTop="12dp"
|
||||
app:layout_constraintEnd_toEndOf="parent"
|
||||
app:layout_constraintHeight_default="wrap"
|
||||
app:layout_constraintHeight_max="280dp"
|
||||
app:layout_constraintStart_toStartOf="parent"
|
||||
app:layout_constraintTop_toBottomOf="@id/progressBar"
|
||||
app:shapeAppearance="?shapeAppearanceCornerMedium">
|
||||
|
||||
<androidx.recyclerview.widget.RecyclerView
|
||||
android:id="@+id/recyclerView_chapters"
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="match_parent"
|
||||
android:orientation="vertical"
|
||||
android:scrollbars="vertical"
|
||||
app:layoutManager="androidx.recyclerview.widget.LinearLayoutManager"
|
||||
tools:itemCount="200"
|
||||
tools:listitem="@layout/item_chapter_download" />
|
||||
|
||||
</com.google.android.material.card.MaterialCardView>
|
||||
|
||||
<Button
|
||||
android:id="@+id/button_pause"
|
||||
style="?materialButtonOutlinedStyle"
|
||||
@@ -139,7 +114,7 @@
|
||||
android:text="@string/pause"
|
||||
android:visibility="gone"
|
||||
app:layout_constraintEnd_toStartOf="@id/button_resume"
|
||||
app:layout_constraintTop_toBottomOf="@id/card_details"
|
||||
app:layout_constraintTop_toBottomOf="@id/progressBar"
|
||||
tools:visibility="visible" />
|
||||
|
||||
<Button
|
||||
@@ -152,7 +127,7 @@
|
||||
android:text="@string/resume"
|
||||
android:visibility="gone"
|
||||
app:layout_constraintEnd_toStartOf="@id/button_cancel"
|
||||
app:layout_constraintTop_toBottomOf="@id/card_details" />
|
||||
app:layout_constraintTop_toBottomOf="@id/progressBar" />
|
||||
|
||||
<Button
|
||||
android:id="@+id/button_cancel"
|
||||
@@ -164,7 +139,7 @@
|
||||
android:text="@android:string/cancel"
|
||||
android:visibility="gone"
|
||||
app:layout_constraintEnd_toEndOf="parent"
|
||||
app:layout_constraintTop_toBottomOf="@id/card_details"
|
||||
app:layout_constraintTop_toBottomOf="@id/progressBar"
|
||||
tools:visibility="visible" />
|
||||
|
||||
</androidx.constraintlayout.widget.ConstraintLayout>
|
||||
|
||||
Reference in New Issue
Block a user