Remove need for SQLDelight primitive adapters

This commit is contained in:
arkon 2023-07-29 16:14:23 -04:00
parent 6a558ad119
commit cd91ea9b77
31 changed files with 67 additions and 83 deletions

View file

@ -170,7 +170,6 @@ dependencies {
implementation(androidx.paging.compose) implementation(androidx.paging.compose)
implementation(libs.bundles.sqlite) implementation(libs.bundles.sqlite)
implementation(libs.sqldelight.primitive.adapters)
implementation(kotlinx.reflect) implementation(kotlinx.reflect)

View file

@ -151,9 +151,9 @@ class SyncChaptersWithSource(
val reAdded = mutableListOf<Chapter>() val reAdded = mutableListOf<Chapter>()
val deletedChapterNumbers = TreeSet<Float>() val deletedChapterNumbers = TreeSet<Double>()
val deletedReadChapterNumbers = TreeSet<Float>() val deletedReadChapterNumbers = TreeSet<Double>()
val deletedBookmarkedChapterNumbers = TreeSet<Float>() val deletedBookmarkedChapterNumbers = TreeSet<Double>()
toDelete.forEach { chapter -> toDelete.forEach { chapter ->
if (chapter.read) deletedReadChapterNumbers.add(chapter.chapterNumber) if (chapter.read) deletedReadChapterNumbers.add(chapter.chapterNumber)

View file

@ -12,7 +12,7 @@ fun Chapter.toSChapter(): SChapter {
it.url = url it.url = url
it.name = name it.name = name
it.date_upload = dateUpload it.date_upload = dateUpload
it.chapter_number = chapterNumber it.chapter_number = chapterNumber.toFloat()
it.scanlator = scanlator it.scanlator = scanlator
} }
} }
@ -22,7 +22,7 @@ fun Chapter.copyFromSChapter(sChapter: SChapter): Chapter {
name = sChapter.name, name = sChapter.name,
url = sChapter.url, url = sChapter.url,
dateUpload = sChapter.date_upload, dateUpload = sChapter.date_upload,
chapterNumber = sChapter.chapter_number, chapterNumber = sChapter.chapter_number.toDouble(),
scanlator = sChapter.scanlator?.ifBlank { null }, scanlator = sChapter.scanlator?.ifBlank { null },
) )
} }
@ -48,6 +48,6 @@ fun Chapter.toDbChapter(): DbChapter = ChapterImpl().also {
it.last_page_read = lastPageRead.toInt() it.last_page_read = lastPageRead.toInt()
it.date_fetch = dateFetch it.date_fetch = dateFetch
it.date_upload = dateUpload it.date_upload = dateUpload
it.chapter_number = chapterNumber it.chapter_number = chapterNumber.toFloat()
it.source_order = sourceOrder.toInt() it.source_order = sourceOrder.toInt()
} }

View file

@ -99,7 +99,7 @@ fun getComicInfo(manga: Manga, chapter: Chapter, chapterUrl: String, categories:
title = ComicInfo.Title(chapter.name), title = ComicInfo.Title(chapter.name),
series = ComicInfo.Series(manga.title), series = ComicInfo.Series(manga.title),
number = chapter.chapterNumber.takeIf { it >= 0 }?.let { number = chapter.chapterNumber.takeIf { it >= 0 }?.let {
if ((it.rem(1) == 0.0F)) { if ((it.rem(1) == 0.0)) {
ComicInfo.Number(it.toInt().toString()) ComicInfo.Number(it.toInt().toString())
} else { } else {
ComicInfo.Number(it.toString()) ComicInfo.Number(it.toString())

View file

@ -22,7 +22,7 @@ fun Track.toDbTrack(): DbTrack = DbTrack.create(syncId).also {
it.last_chapter_read = lastChapterRead.toFloat() it.last_chapter_read = lastChapterRead.toFloat()
it.total_chapters = totalChapters.toInt() it.total_chapters = totalChapters.toInt()
it.status = status.toInt() it.status = status.toInt()
it.score = score it.score = score.toFloat()
it.tracking_url = remoteUrl it.tracking_url = remoteUrl
it.started_reading_date = startDate it.started_reading_date = startDate
it.finished_reading_date = finishDate it.finished_reading_date = finishDate
@ -40,7 +40,7 @@ fun DbTrack.toDomainTrack(idRequired: Boolean = true): Track? {
lastChapterRead = last_chapter_read.toDouble(), lastChapterRead = last_chapter_read.toDouble(),
totalChapters = total_chapters.toLong(), totalChapters = total_chapters.toLong(),
status = status.toLong(), status = status.toLong(),
score = score, score = score.toDouble(),
remoteUrl = tracking_url, remoteUrl = tracking_url,
startDate = started_reading_date, startDate = started_reading_date,
finishDate = finished_reading_date, finishDate = finished_reading_date,

View file

@ -98,7 +98,7 @@ fun TrackInfoDialogHome(
}, },
onChaptersClick = { onChapterClick(item) }, onChaptersClick = { onChapterClick(item) },
score = item.service.displayScore(item.track.toDbTrack()) score = item.service.displayScore(item.track.toDbTrack())
.takeIf { supportsScoring && item.track.score != 0F }, .takeIf { supportsScoring && item.track.score != 0.0 },
onScoreClick = { onScoreClick(item) } onScoreClick = { onScoreClick(item) }
.takeIf { supportsScoring }, .takeIf { supportsScoring },
startDate = remember(item.track.startDate) { dateFormat.format(item.track.startDate) } startDate = remember(item.track.startDate) { dateFormat.format(item.track.startDate) }

View file

@ -8,6 +8,6 @@ private val formatter = DecimalFormat(
DecimalFormatSymbols().apply { decimalSeparator = '.' }, DecimalFormatSymbols().apply { decimalSeparator = '.' },
) )
fun formatChapterNumber(chapterNumber: Float): String { fun formatChapterNumber(chapterNumber: Double): String {
return formatter.format(chapterNumber) return formatter.format(chapterNumber)
} }

View file

@ -5,7 +5,6 @@ import android.os.Build
import androidx.core.content.ContextCompat import androidx.core.content.ContextCompat
import androidx.sqlite.db.SupportSQLiteDatabase import androidx.sqlite.db.SupportSQLiteDatabase
import androidx.sqlite.db.framework.FrameworkSQLiteOpenHelperFactory import androidx.sqlite.db.framework.FrameworkSQLiteOpenHelperFactory
import app.cash.sqldelight.adapter.primitive.FloatColumnAdapter
import app.cash.sqldelight.db.SqlDriver import app.cash.sqldelight.db.SqlDriver
import app.cash.sqldelight.driver.android.AndroidSqliteDriver import app.cash.sqldelight.driver.android.AndroidSqliteDriver
import eu.kanade.domain.base.BasePreferences import eu.kanade.domain.base.BasePreferences
@ -38,15 +37,13 @@ import tachiyomi.core.preference.PreferenceStore
import tachiyomi.core.provider.AndroidBackupFolderProvider import tachiyomi.core.provider.AndroidBackupFolderProvider
import tachiyomi.core.provider.AndroidDownloadFolderProvider import tachiyomi.core.provider.AndroidDownloadFolderProvider
import tachiyomi.data.AndroidDatabaseHandler import tachiyomi.data.AndroidDatabaseHandler
import tachiyomi.data.Chapters
import tachiyomi.data.Database import tachiyomi.data.Database
import tachiyomi.data.DatabaseHandler import tachiyomi.data.DatabaseHandler
import tachiyomi.data.DateColumnAdapter
import tachiyomi.data.History import tachiyomi.data.History
import tachiyomi.data.Manga_sync
import tachiyomi.data.Mangas import tachiyomi.data.Mangas
import tachiyomi.data.dateAdapter import tachiyomi.data.StringListColumnAdapter
import tachiyomi.data.listOfStringsAdapter import tachiyomi.data.UpdateStrategyColumnAdapter
import tachiyomi.data.updateStrategyAdapter
import tachiyomi.domain.backup.service.BackupPreferences import tachiyomi.domain.backup.service.BackupPreferences
import tachiyomi.domain.download.service.DownloadPreferences import tachiyomi.domain.download.service.DownloadPreferences
import tachiyomi.domain.library.service.LibraryPreferences import tachiyomi.domain.library.service.LibraryPreferences
@ -93,18 +90,12 @@ class AppModule(val app: Application) : InjektModule {
addSingletonFactory { addSingletonFactory {
Database( Database(
driver = get(), driver = get(),
chaptersAdapter = Chapters.Adapter(
chapter_numberAdapter = FloatColumnAdapter,
),
historyAdapter = History.Adapter( historyAdapter = History.Adapter(
last_readAdapter = dateAdapter, last_readAdapter = DateColumnAdapter,
),
manga_syncAdapter = Manga_sync.Adapter(
scoreAdapter = FloatColumnAdapter,
), ),
mangasAdapter = Mangas.Adapter( mangasAdapter = Mangas.Adapter(
genreAdapter = listOfStringsAdapter, genreAdapter = StringListColumnAdapter,
update_strategyAdapter = updateStrategyAdapter, update_strategyAdapter = UpdateStrategyColumnAdapter,
), ),
) )
} }

View file

@ -30,12 +30,11 @@ import logcat.LogPriority
import okio.buffer import okio.buffer
import okio.gzip import okio.gzip
import okio.sink import okio.sink
import tachiyomi.core.util.lang.toLong
import tachiyomi.core.util.system.logcat import tachiyomi.core.util.system.logcat
import tachiyomi.data.DatabaseHandler import tachiyomi.data.DatabaseHandler
import tachiyomi.data.Manga_sync import tachiyomi.data.Manga_sync
import tachiyomi.data.Mangas import tachiyomi.data.Mangas
import tachiyomi.data.updateStrategyAdapter import tachiyomi.data.UpdateStrategyColumnAdapter
import tachiyomi.domain.backup.service.BackupPreferences import tachiyomi.domain.backup.service.BackupPreferences
import tachiyomi.domain.category.interactor.GetCategories import tachiyomi.domain.category.interactor.GetCategories
import tachiyomi.domain.category.model.Category import tachiyomi.domain.category.model.Category
@ -415,7 +414,7 @@ class BackupManager(
track.last_chapter_read, track.last_chapter_read,
track.total_chapters, track.total_chapters,
track.status, track.status,
track.score.toDouble(), track.score,
track.remote_url, track.remote_url,
track.start_date, track.start_date,
track.finish_date, track.finish_date,
@ -536,7 +535,7 @@ class BackupManager(
coverLastModified = manga.coverLastModified, coverLastModified = manga.coverLastModified,
dateAdded = manga.dateAdded, dateAdded = manga.dateAdded,
mangaId = manga.id, mangaId = manga.id,
updateStrategy = manga.updateStrategy.let(updateStrategyAdapter::encode), updateStrategy = manga.updateStrategy.let(UpdateStrategyColumnAdapter::encode),
) )
} }
return manga.id return manga.id

View file

@ -26,7 +26,7 @@ data class BackupChapter(
return Chapter.create().copy( return Chapter.create().copy(
url = this@BackupChapter.url, url = this@BackupChapter.url,
name = this@BackupChapter.name, name = this@BackupChapter.name,
chapterNumber = this@BackupChapter.chapterNumber, chapterNumber = this@BackupChapter.chapterNumber.toDouble(),
scanlator = this@BackupChapter.scanlator, scanlator = this@BackupChapter.scanlator,
read = this@BackupChapter.read, read = this@BackupChapter.read,
bookmark = this@BackupChapter.bookmark, bookmark = this@BackupChapter.bookmark,
@ -39,11 +39,11 @@ data class BackupChapter(
} }
} }
val backupChapterMapper = { _: Long, _: Long, url: String, name: String, scanlator: String?, read: Boolean, bookmark: Boolean, lastPageRead: Long, chapterNumber: Float, source_order: Long, dateFetch: Long, dateUpload: Long, lastModifiedAt: Long -> val backupChapterMapper = { _: Long, _: Long, url: String, name: String, scanlator: String?, read: Boolean, bookmark: Boolean, lastPageRead: Long, chapterNumber: Double, source_order: Long, dateFetch: Long, dateUpload: Long, lastModifiedAt: Long ->
BackupChapter( BackupChapter(
url = url, url = url,
name = name, name = name,
chapterNumber = chapterNumber, chapterNumber = chapterNumber.toFloat(),
scanlator = scanlator, scanlator = scanlator,
read = read, read = read,
bookmark = bookmark, bookmark = bookmark,

View file

@ -44,7 +44,7 @@ data class BackupTracking(
title = this@BackupTracking.title, title = this@BackupTracking.title,
lastChapterRead = this@BackupTracking.lastChapterRead.toDouble(), lastChapterRead = this@BackupTracking.lastChapterRead.toDouble(),
totalChapters = this@BackupTracking.totalChapters.toLong(), totalChapters = this@BackupTracking.totalChapters.toLong(),
score = this@BackupTracking.score, score = this@BackupTracking.score.toDouble(),
status = this@BackupTracking.status.toLong(), status = this@BackupTracking.status.toLong(),
startDate = this@BackupTracking.startedReadingDate, startDate = this@BackupTracking.startedReadingDate,
finishDate = this@BackupTracking.finishedReadingDate, finishDate = this@BackupTracking.finishedReadingDate,
@ -54,7 +54,7 @@ data class BackupTracking(
} }
val backupTrackMapper = { val backupTrackMapper = {
_: Long, _: Long, syncId: Long, mediaId: Long, libraryId: Long?, title: String, lastChapterRead: Double, totalChapters: Long, status: Long, score: Float, remoteUrl: String, startDate: Long, finishDate: Long -> _: Long, _: Long, syncId: Long, mediaId: Long, libraryId: Long?, title: String, lastChapterRead: Double, totalChapters: Long, status: Long, score: Double, remoteUrl: String, startDate: Long, finishDate: Long ->
BackupTracking( BackupTracking(
syncId = syncId.toInt(), syncId = syncId.toInt(),
mediaId = mediaId, mediaId = mediaId,
@ -63,7 +63,7 @@ val backupTrackMapper = {
title = title, title = title,
lastChapterRead = lastChapterRead.toFloat(), lastChapterRead = lastChapterRead.toFloat(),
totalChapters = totalChapters.toInt(), totalChapters = totalChapters.toInt(),
score = score, score = score.toFloat(),
status = status.toInt(), status = status.toInt(),
startedReadingDate = startDate, startedReadingDate = startDate,
finishedReadingDate = finishDate, finishedReadingDate = finishDate,

View file

@ -36,7 +36,7 @@ fun Chapter.toDomainChapter(): DomainChapter? {
url = url, url = url,
name = name, name = name,
dateUpload = date_upload, dateUpload = date_upload,
chapterNumber = chapter_number, chapterNumber = chapter_number.toDouble(),
scanlator = scanlator, scanlator = scanlator,
lastModifiedAt = last_modified, lastModifiedAt = last_modified,
) )

View file

@ -65,7 +65,7 @@ abstract class TrackService(val id: Long) {
abstract fun getScoreList(): List<String> abstract fun getScoreList(): List<String>
// TODO: Store all scores as 10 point in the future maybe? // TODO: Store all scores as 10 point in the future maybe?
open fun get10PointScore(track: DomainTrack): Float { open fun get10PointScore(track: DomainTrack): Double {
return track.score return track.score
} }

View file

@ -93,9 +93,9 @@ class Anilist(id: Long) : TrackService(id), DeletableTrackService {
} }
} }
override fun get10PointScore(track: DomainTrack): Float { override fun get10PointScore(track: DomainTrack): Double {
// Score is stored in 100 point format // Score is stored in 100 point format
return track.score / 10f return track.score / 10.0
} }
override fun indexToScore(index: Int): Float { override fun indexToScore(index: Int): Float {

View file

@ -6,6 +6,6 @@ fun SChapter.copyFrom(other: Chapters) {
name = other.name name = other.name
url = other.url url = other.url
date_upload = other.date_upload date_upload = other.date_upload
chapter_number = other.chapter_number chapter_number = other.chapter_number.toFloat()
scanlator = other.scanlator scanlator = other.scanlator
} }

View file

@ -137,15 +137,13 @@ class StatsScreenModel(
private fun getTrackMeanScore(scoredMangaTrackMap: Map<Long, List<Track>>): Double { private fun getTrackMeanScore(scoredMangaTrackMap: Map<Long, List<Track>>): Double {
return scoredMangaTrackMap return scoredMangaTrackMap
.map { (_, tracks) -> .map { (_, tracks) ->
tracks.map { tracks.map(::get10PointScore).average()
get10PointScore(it)
}.average()
} }
.fastFilter { !it.isNaN() } .fastFilter { !it.isNaN() }
.average() .average()
} }
private fun get10PointScore(track: Track): Float { private fun get10PointScore(track: Track): Double {
val service = trackManager.getService(track.syncId)!! val service = trackManager.getService(track.syncId)!!
return service.get10PointScore(track) return service.get10PointScore(track)
} }

View file

@ -4,23 +4,23 @@ import app.cash.sqldelight.ColumnAdapter
import eu.kanade.tachiyomi.source.model.UpdateStrategy import eu.kanade.tachiyomi.source.model.UpdateStrategy
import java.util.Date import java.util.Date
val dateAdapter = object : ColumnAdapter<Date, Long> { object DateColumnAdapter : ColumnAdapter<Date, Long> {
override fun decode(databaseValue: Long): Date = Date(databaseValue) override fun decode(databaseValue: Long): Date = Date(databaseValue)
override fun encode(value: Date): Long = value.time override fun encode(value: Date): Long = value.time
} }
private const val listOfStringsSeparator = ", " private const val LIST_OF_STRINGS_SEPARATOR = ", "
val listOfStringsAdapter = object : ColumnAdapter<List<String>, String> { object StringListColumnAdapter : ColumnAdapter<List<String>, String> {
override fun decode(databaseValue: String) = override fun decode(databaseValue: String) =
if (databaseValue.isEmpty()) { if (databaseValue.isEmpty()) {
emptyList() emptyList()
} else { } else {
databaseValue.split(listOfStringsSeparator) databaseValue.split(LIST_OF_STRINGS_SEPARATOR)
} }
override fun encode(value: List<String>) = value.joinToString(separator = listOfStringsSeparator) override fun encode(value: List<String>) = value.joinToString(separator = LIST_OF_STRINGS_SEPARATOR)
} }
val updateStrategyAdapter = object : ColumnAdapter<UpdateStrategy, Long> { object UpdateStrategyColumnAdapter : ColumnAdapter<UpdateStrategy, Long> {
override fun decode(databaseValue: Long): UpdateStrategy = override fun decode(databaseValue: Long): UpdateStrategy =
UpdateStrategy.entries.getOrElse(databaseValue.toInt()) { UpdateStrategy.ALWAYS_UPDATE } UpdateStrategy.entries.getOrElse(databaseValue.toInt()) { UpdateStrategy.ALWAYS_UPDATE }

View file

@ -2,7 +2,7 @@ package tachiyomi.data.chapter
import tachiyomi.domain.chapter.model.Chapter import tachiyomi.domain.chapter.model.Chapter
val chapterMapper: (Long, Long, String, String, String?, Boolean, Boolean, Long, Float, Long, Long, Long, Long) -> Chapter = val chapterMapper: (Long, Long, String, String, String?, Boolean, Boolean, Long, Double, Long, Long, Long, Long) -> Chapter =
{ id, mangaId, url, name, scanlator, read, bookmark, lastPageRead, chapterNumber, sourceOrder, dateFetch, dateUpload, lastModifiedAt -> { id, mangaId, url, name, scanlator, read, bookmark, lastPageRead, chapterNumber, sourceOrder, dateFetch, dateUpload, lastModifiedAt ->
Chapter( Chapter(
id = id, id = id,

View file

@ -14,7 +14,7 @@ val historyMapper: (Long, Long, Date?, Long) -> History = { id, chapterId, readA
) )
} }
val historyWithRelationsMapper: (Long, Long, Long, String, String?, Long, Boolean, Long, Float, Date?, Long) -> HistoryWithRelations = { val historyWithRelationsMapper: (Long, Long, Long, String, String?, Long, Boolean, Long, Double, Date?, Long) -> HistoryWithRelations = {
historyId, mangaId, chapterId, title, thumbnailUrl, sourceId, isFavorite, coverLastModified, chapterNumber, readAt, readDuration -> historyId, mangaId, chapterId, title, thumbnailUrl, sourceId, isFavorite, coverLastModified, chapterNumber, readAt, readDuration ->
HistoryWithRelations( HistoryWithRelations(
id = historyId, id = historyId,

View file

@ -2,11 +2,10 @@ package tachiyomi.data.manga
import kotlinx.coroutines.flow.Flow import kotlinx.coroutines.flow.Flow
import logcat.LogPriority import logcat.LogPriority
import tachiyomi.core.util.lang.toLong
import tachiyomi.core.util.system.logcat import tachiyomi.core.util.system.logcat
import tachiyomi.data.DatabaseHandler import tachiyomi.data.DatabaseHandler
import tachiyomi.data.listOfStringsAdapter import tachiyomi.data.StringListColumnAdapter
import tachiyomi.data.updateStrategyAdapter import tachiyomi.data.UpdateStrategyColumnAdapter
import tachiyomi.domain.library.model.LibraryManga import tachiyomi.domain.library.model.LibraryManga
import tachiyomi.domain.manga.model.Manga import tachiyomi.domain.manga.model.Manga
import tachiyomi.domain.manga.model.MangaUpdate import tachiyomi.domain.manga.model.MangaUpdate
@ -129,7 +128,7 @@ class MangaRepositoryImpl(
artist = value.artist, artist = value.artist,
author = value.author, author = value.author,
description = value.description, description = value.description,
genre = value.genre?.let(listOfStringsAdapter::encode), genre = value.genre?.let(StringListColumnAdapter::encode),
title = value.title, title = value.title,
status = value.status, status = value.status,
thumbnailUrl = value.thumbnailUrl, thumbnailUrl = value.thumbnailUrl,
@ -143,7 +142,7 @@ class MangaRepositoryImpl(
coverLastModified = value.coverLastModified, coverLastModified = value.coverLastModified,
dateAdded = value.dateAdded, dateAdded = value.dateAdded,
mangaId = value.id, mangaId = value.id,
updateStrategy = value.updateStrategy?.let(updateStrategyAdapter::encode), updateStrategy = value.updateStrategy?.let(UpdateStrategyColumnAdapter::encode),
) )
} }
} }

View file

@ -2,7 +2,7 @@ package tachiyomi.data.track
import tachiyomi.domain.track.model.Track import tachiyomi.domain.track.model.Track
val trackMapper: (Long, Long, Long, Long, Long?, String, Double, Long, Long, Float, String, Long, Long) -> Track = val trackMapper: (Long, Long, Long, Long, Long?, String, Double, Long, Long, Double, String, Long, Long) -> Track =
{ id, mangaId, syncId, remoteId, libraryId, title, lastChapterRead, totalChapters, status, score, remoteUrl, startDate, finishDate -> { id, mangaId, syncId, remoteId, libraryId, title, lastChapterRead, totalChapters, status, score, remoteUrl, startDate, finishDate ->
Track( Track(
id = id, id = id,

View file

@ -1,5 +1,4 @@
import kotlin.Boolean; import kotlin.Boolean;
import kotlin.Float;
CREATE TABLE chapters( CREATE TABLE chapters(
_id INTEGER NOT NULL PRIMARY KEY, _id INTEGER NOT NULL PRIMARY KEY,
@ -10,7 +9,7 @@ CREATE TABLE chapters(
read INTEGER AS Boolean NOT NULL, read INTEGER AS Boolean NOT NULL,
bookmark INTEGER AS Boolean NOT NULL, bookmark INTEGER AS Boolean NOT NULL,
last_page_read INTEGER NOT NULL, last_page_read INTEGER NOT NULL,
chapter_number REAL AS Float NOT NULL, chapter_number REAL NOT NULL,
source_order INTEGER NOT NULL, source_order INTEGER NOT NULL,
date_fetch INTEGER NOT NULL, date_fetch INTEGER NOT NULL,
date_upload INTEGER NOT NULL, date_upload INTEGER NOT NULL,

View file

@ -1,5 +1,3 @@
import kotlin.Float;
CREATE TABLE manga_sync( CREATE TABLE manga_sync(
_id INTEGER NOT NULL PRIMARY KEY, _id INTEGER NOT NULL PRIMARY KEY,
manga_id INTEGER NOT NULL, manga_id INTEGER NOT NULL,
@ -10,7 +8,7 @@ CREATE TABLE manga_sync(
last_chapter_read REAL NOT NULL, last_chapter_read REAL NOT NULL,
total_chapters INTEGER NOT NULL, total_chapters INTEGER NOT NULL,
status INTEGER NOT NULL, status INTEGER NOT NULL,
score REAL AS Float NOT NULL, score REAL NOT NULL,
remote_url TEXT NOT NULL, remote_url TEXT NOT NULL,
start_date INTEGER NOT NULL, start_date INTEGER NOT NULL,
finish_date INTEGER NOT NULL, finish_date INTEGER NOT NULL,

View file

@ -11,7 +11,7 @@ data class Chapter(
val url: String, val url: String,
val name: String, val name: String,
val dateUpload: Long, val dateUpload: Long,
val chapterNumber: Float, val chapterNumber: Double,
val scanlator: String?, val scanlator: String?,
val lastModifiedAt: Long, val lastModifiedAt: Long,
) { ) {
@ -30,7 +30,7 @@ data class Chapter(
url = "", url = "",
name = "", name = "",
dateUpload = -1, dateUpload = -1,
chapterNumber = -1f, chapterNumber = -1.0,
scanlator = null, scanlator = null,
lastModifiedAt = 0, lastModifiedAt = 0,
) )

View file

@ -11,7 +11,7 @@ data class ChapterUpdate(
val url: String? = null, val url: String? = null,
val name: String? = null, val name: String? = null,
val dateUpload: Long? = null, val dateUpload: Long? = null,
val chapterNumber: Float? = null, val chapterNumber: Double? = null,
val scanlator: String? = null, val scanlator: String? = null,
) )

View file

@ -30,9 +30,9 @@ object ChapterRecognition {
*/ */
private val unwantedWhiteSpace = Regex("""\s(?=extra|special|omake)""") private val unwantedWhiteSpace = Regex("""\s(?=extra|special|omake)""")
fun parseChapterNumber(mangaTitle: String, chapterName: String, chapterNumber: Float? = null): Float { fun parseChapterNumber(mangaTitle: String, chapterName: String, chapterNumber: Double? = null): Double {
// If chapter number is known return. // If chapter number is known return.
if (chapterNumber != null && (chapterNumber == -2f || chapterNumber > -1f)) { if (chapterNumber != null && (chapterNumber == -2.0 || chapterNumber > -1.0)) {
return chapterNumber return chapterNumber
} }
@ -57,7 +57,7 @@ object ChapterRecognition {
// Take the first number encountered. // Take the first number encountered.
number.find(name)?.let { return getChapterNumberFromMatch(it) } number.find(name)?.let { return getChapterNumberFromMatch(it) }
return chapterNumber ?: -1f return chapterNumber ?: -1.0
} }
/** /**
@ -65,9 +65,9 @@ object ChapterRecognition {
* @param match result of regex * @param match result of regex
* @return chapter number if found else null * @return chapter number if found else null
*/ */
private fun getChapterNumberFromMatch(match: MatchResult): Float { private fun getChapterNumberFromMatch(match: MatchResult): Double {
return match.let { return match.let {
val initial = it.groups[1]?.value?.toFloat()!! val initial = it.groups[1]?.value?.toDouble()!!
val subChapterDecimal = it.groups[2]?.value val subChapterDecimal = it.groups[2]?.value
val subChapterAlpha = it.groups[3]?.value val subChapterAlpha = it.groups[3]?.value
val addition = checkForDecimal(subChapterDecimal, subChapterAlpha) val addition = checkForDecimal(subChapterDecimal, subChapterAlpha)

View file

@ -3,16 +3,16 @@ package tachiyomi.domain.chapter.service
import tachiyomi.domain.chapter.model.Chapter import tachiyomi.domain.chapter.model.Chapter
import kotlin.math.floor import kotlin.math.floor
fun List<Float>.missingChaptersCount(): Int { fun List<Double>.missingChaptersCount(): Int {
if (this.isEmpty()) { if (this.isEmpty()) {
return 0 return 0
} }
val chapters = this val chapters = this
// Ignore unknown chapter numbers // Ignore unknown chapter numbers
.filterNot { it == -1f } .filterNot { it == -1.0 }
// Convert to integers, as we cannot check if 16.5 is missing // Convert to integers, as we cannot check if 16.5 is missing
.map(Float::toInt) .map(Double::toInt)
// Only keep unique chapters so that -1 or 16 are not counted multiple times // Only keep unique chapters so that -1 or 16 are not counted multiple times
.distinct() .distinct()
.sorted() .sorted()
@ -43,7 +43,7 @@ fun calculateChapterGap(higherChapter: Chapter?, lowerChapter: Chapter?): Int {
return calculateChapterGap(higherChapter.chapterNumber, lowerChapter.chapterNumber) return calculateChapterGap(higherChapter.chapterNumber, lowerChapter.chapterNumber)
} }
fun calculateChapterGap(higherChapterNumber: Float, lowerChapterNumber: Float): Int { fun calculateChapterGap(higherChapterNumber: Double, lowerChapterNumber: Double): Int {
if (higherChapterNumber < 0f || lowerChapterNumber < 0f) return 0 if (higherChapterNumber < 0.0 || lowerChapterNumber < 0.0) return 0
return floor(higherChapterNumber).toInt() - floor(lowerChapterNumber).toInt() - 1 return floor(higherChapterNumber).toInt() - floor(lowerChapterNumber).toInt() - 1
} }

View file

@ -8,7 +8,7 @@ data class HistoryWithRelations(
val chapterId: Long, val chapterId: Long,
val mangaId: Long, val mangaId: Long,
val title: String, val title: String,
val chapterNumber: Float, val chapterNumber: Double,
val readAt: Date?, val readAt: Date?,
val readDuration: Long, val readDuration: Long,
val coverData: MangaCover, val coverData: MangaCover,

View file

@ -10,7 +10,7 @@ data class Track(
val lastChapterRead: Double, val lastChapterRead: Double,
val totalChapters: Long, val totalChapters: Long,
val status: Long, val status: Long,
val score: Float, val score: Double,
val remoteUrl: String, val remoteUrl: String,
val startDate: Long, val startDate: Long,
val finishDate: Long, val finishDate: Long,

View file

@ -80,7 +80,6 @@ leakcanary-plumber = { module = "com.squareup.leakcanary:plumber-android", versi
sqldelight-android-driver = { module = "app.cash.sqldelight:android-driver", version.ref = "sqldelight" } sqldelight-android-driver = { module = "app.cash.sqldelight:android-driver", version.ref = "sqldelight" }
sqldelight-coroutines = { module = "app.cash.sqldelight:coroutines-extensions-jvm", version.ref = "sqldelight" } sqldelight-coroutines = { module = "app.cash.sqldelight:coroutines-extensions-jvm", version.ref = "sqldelight" }
sqldelight-android-paging = { module = "app.cash.sqldelight:androidx-paging3-extensions", version.ref = "sqldelight" } sqldelight-android-paging = { module = "app.cash.sqldelight:androidx-paging3-extensions", version.ref = "sqldelight" }
sqldelight-primitive-adapters = { module = "app.cash.sqldelight:primitive-adapters", version.ref = "sqldelight" }
sqldelight-dialects-sql = { module = "app.cash.sqldelight:sqlite-3-38-dialect", version.ref = "sqldelight" } sqldelight-dialects-sql = { module = "app.cash.sqldelight:sqlite-3-38-dialect", version.ref = "sqldelight" }
sqldelight-gradle = { module = "app.cash.sqldelight:gradle-plugin", version.ref = "sqldelight" } sqldelight-gradle = { module = "app.cash.sqldelight:gradle-plugin", version.ref = "sqldelight" }
@ -101,7 +100,7 @@ js-engine = ["quickjs-android"]
sqlite = ["sqlite-framework", "sqlite-ktx", "sqlite-android"] sqlite = ["sqlite-framework", "sqlite-ktx", "sqlite-android"]
coil = ["coil-core", "coil-gif", "coil-compose"] coil = ["coil-core", "coil-gif", "coil-compose"]
shizuku = ["shizuku-api", "shizuku-provider"] shizuku = ["shizuku-api", "shizuku-provider"]
sqldelight = ["sqldelight-android-driver", "sqldelight-coroutines", "sqldelight-android-paging", "sqldelight-primitive-adapters"] sqldelight = ["sqldelight-android-driver", "sqldelight-coroutines", "sqldelight-android-paging"]
voyager = ["voyager-navigator", "voyager-tab-navigator", "voyager-transitions"] voyager = ["voyager-navigator", "voyager-tab-navigator", "voyager-transitions"]
richtext = ["richtext-commonmark", "richtext-m3"] richtext = ["richtext-commonmark", "richtext-m3"]
test = ["junit", "kotest-assertions", "mockk"] test = ["junit", "kotest-assertions", "mockk"]

View file

@ -264,7 +264,9 @@ actual class LocalSource(
chapterFile.nameWithoutExtension chapterFile.nameWithoutExtension
} }
date_upload = chapterFile.lastModified() date_upload = chapterFile.lastModified()
chapter_number = ChapterRecognition.parseChapterNumber(manga.title, this.name, this.chapter_number) chapter_number = ChapterRecognition
.parseChapterNumber(manga.title, this.name, this.chapter_number.toDouble())
.toFloat()
val format = Format.valueOf(chapterFile) val format = Format.valueOf(chapterFile)
if (format is Format.Epub) { if (format is Format.Epub) {