Skip to content

书架排序支持#426

Merged
dmzz-yyhyy merged 6 commits into
refactoringfrom
bookshelf_reorder
May 31, 2026
Merged

书架排序支持#426
dmzz-yyhyy merged 6 commits into
refactoringfrom
bookshelf_reorder

Conversation

@yukonisen

@yukonisen yukonisen commented May 23, 2026

Copy link
Copy Markdown
Collaborator

这个 PR 为书架新增(书架顺序/书本顺序)排序功能 (resolve #309 )
修复探索页面的状态保存 (resolve #393 )

提示:还包含API版本4的预改动

Copy link
Copy Markdown
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

书架的排序包括

  • 默认:按照添加顺序的逆序
  • 字数
  • 名称排序:首字母(A-Z),汉语字符使用tinypinyin获取拼音后按照字母顺序排序
    除了默认排序之外都支持反转顺序

Copy link
Copy Markdown
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

编辑书架页的改动主要包括使用LazyColumn列表,使用应用内置的设置项控件,移除书架页自定义的设置项控件

Copy link
Copy Markdown
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

单独提取 BookshelfHomeActions 因为传参过多

Copy link
Copy Markdown
Owner

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

可以提取这种东西,但其实可以放到UiState里去

Copy link
Copy Markdown
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

对书架主页进行了拆分,因为原有文件过长

Copy link
Copy Markdown
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

同样属于书架主页UI文件的拆分

Copy link
Copy Markdown
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

同样属于书架主页UI文件的拆分

Copy link
Copy Markdown
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

重新排序reorder包括 排序书架 和 排序书架的书本
排序书架可以调整所有书架的顺序,排序书架书本是排序书架内书本的顺序。

Copy link
Copy Markdown
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

对探索主页的修改主要包括:

  • 保存状态
  • 更新了应用内统一PrimaryTabRow样式

Copilot AI left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Pull request overview

This PR adds bookshelf sorting/reordering capabilities (for both books and bookshelves) and improves state persistence on the Explore home page, addressing #309 and #393.

Changes:

  • Add new bookshelf sort modes (default/latest/name/word count) with optional reverse, and new reorder screens for manual ordering.
  • Persist and restore Explore home page UI state (titles + loaded content) to avoid unnecessary reloads.
  • Introduce new dependencies/resources and a DB migration to support the new sorting fields and UI.

Reviewed changes

Copilot reviewed 34 out of 34 changed files in this pull request and generated 9 comments.

Show a summary per file
File Description
settings.gradle.kts Adds an additional Maven repository for dependency resolution.
gradle/libs.versions.toml Adds reorderable dependency version/catalog entry (and is used for new deps).
app/src/main/res/values/strings.xml Adds strings for sort/reorder UI and exit confirmation prompts.
app/src/main/res/drawable/sort_24px.xml Adds sort icon resource.
app/src/main/res/drawable/edit_square_24px.xml Adds edit icon resource.
app/src/main/res/drawable/drag_indicator_24px.xml Adds drag-handle icon resource.
app/src/main/kotlin/indi/dmzz_yyhyy/lightnovelreader/ui/home/settings/data/MenuOptions.kt Adds sort-type menu options mapping to BookshelfSortType.
app/src/main/kotlin/indi/dmzz_yyhyy/lightnovelreader/ui/home/explore/home/ExploreHomeViewModel.kt Updates Explore init/page-loading logic to better preserve state.
app/src/main/kotlin/indi/dmzz_yyhyy/lightnovelreader/ui/home/explore/home/ExploreHomeScreen.kt Uses saveable list state and adjusts tab indicator/top app bar colors.
app/src/main/kotlin/indi/dmzz_yyhyy/lightnovelreader/ui/home/bookshelf/reorder/BookshelfReorderScreen.kt New UI for reordering books and bookshelves via drag-and-drop.
app/src/main/kotlin/indi/dmzz_yyhyy/lightnovelreader/ui/home/bookshelf/reorder/BookshelfReorderNavigation.kt Adds navigation destinations for reorder screens.
app/src/main/kotlin/indi/dmzz_yyhyy/lightnovelreader/ui/home/bookshelf/home/BookshelfUIComponents.kt Minor formatting cleanup.
app/src/main/kotlin/indi/dmzz_yyhyy/lightnovelreader/ui/home/bookshelf/home/BookshelfHomeViewModel.kt Adds sort/reverse/reorder behaviors and persists bookshelf order.
app/src/main/kotlin/indi/dmzz_yyhyy/lightnovelreader/ui/home/bookshelf/home/BookshelfHomeUiState.kt Extends UI state to include reorder-mode flags and reorder lists.
app/src/main/kotlin/indi/dmzz_yyhyy/lightnovelreader/ui/home/bookshelf/home/BookshelfHomeTopBar.kt New top bar with sort controls and entrypoints to reorder flows.
app/src/main/kotlin/indi/dmzz_yyhyy/lightnovelreader/ui/home/bookshelf/home/BookshelfHomeScreen.kt Refactors screen into actions/data sources and delegates UI to new components.
app/src/main/kotlin/indi/dmzz_yyhyy/lightnovelreader/ui/home/bookshelf/home/BookshelfHomeNavigation.kt Refactors navigation wiring to use a shared parent ViewModel + new actions/routes.
app/src/main/kotlin/indi/dmzz_yyhyy/lightnovelreader/ui/home/bookshelf/home/BookshelfHomeContent.kt New content composable implementing sorting logic (incl. Pinyin key for CN titles).
app/src/main/kotlin/indi/dmzz_yyhyy/lightnovelreader/ui/home/bookshelf/home/BookShelfHomeActions.kt Introduces action bundle used by the refactored bookshelf UI.
app/src/main/kotlin/indi/dmzz_yyhyy/lightnovelreader/ui/home/bookshelf/edit/EditBookshelfViewModel.kt Adds sortReversed support and sort-type change handler.
app/src/main/kotlin/indi/dmzz_yyhyy/lightnovelreader/ui/home/bookshelf/edit/EditBookshelfScreen.kt Updates edit UI to use shared settings components and adds sort-type selection.
app/src/main/kotlin/indi/dmzz_yyhyy/lightnovelreader/ui/home/bookshelf/edit/BookshelfEditNavigation.kt Wires sort-type change callback into edit screen.
app/src/main/kotlin/indi/dmzz_yyhyy/lightnovelreader/ui/home/bookshelf/BookshelNavigation.kt Registers reorder navigation graph under bookshelf navigation.
app/src/main/kotlin/indi/dmzz_yyhyy/lightnovelreader/MainActivity.kt Initializes default bookshelf with sortReversed.
app/src/main/kotlin/indi/dmzz_yyhyy/lightnovelreader/data/local/room/LightNovelReaderDatabase.kt Bumps DB version and adds migration for sort_reversed column.
app/src/main/kotlin/indi/dmzz_yyhyy/lightnovelreader/data/local/room/entity/BookshelfEntity.kt Adds sortReversed field to Room entity mapping.
app/src/main/kotlin/indi/dmzz_yyhyy/lightnovelreader/data/bookshelf/BookshelfRepository.kt Maps sortReversed through repository and updates create/update persistence.
app/build.gradle.kts Adds new UI deps (reorderable + tinypinyin) and bumps versionCode.
api/src/main/kotlin/io/nightfish/lightnovelreader/api/userdata/UserDataPath.kt Adds BookshelfOrder user-data path.
api/src/main/kotlin/io/nightfish/lightnovelreader/api/Route.kt Adds routes for reorder screens.
api/src/main/kotlin/io/nightfish/lightnovelreader/api/bookshelf/BookshelfSortType.kt Adds new sort types and makes map() resilient (fallback to Default).
api/src/main/kotlin/io/nightfish/lightnovelreader/api/bookshelf/BookshelfRepositoryApi.kt Extends bookshelf creation API with sortReversed.
api/src/main/kotlin/io/nightfish/lightnovelreader/api/bookshelf/Bookshelf.kt Adds sortReversed to bookshelf model interfaces.
api/src/main/kotlin/io/nightfish/lightnovelreader/api/ApiCompat.kt Updates API compatibility grouping to include API v4.

💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.

Comment thread settings.gradle.kts
Comment on lines 14 to 17
google()
mavenCentral()
maven { setUrl("https://maven.aliyun.com/repository/public") }
maven { setUrl("https://jitpack.io") }
Comment thread gradle/libs.versions.toml
Comment on lines 1 to 20
[versions]
androidGradlePlugin = "9.0.1"
apksig = "9.1.0"
cxhttp = "1.2.5"
dom4j = "2.2.0"
jaxen = "2.0.0"
javet = "5.0.4"
kotlin = "2.3.10"
kotlinComposeCompilerPlugin = "2.1.20"
kotlinResult = "2.3.1"
ksp = "2.3.5"
loggingInterceptor = "5.3.2"
materialIconsCore = "1.7.8"
matomoSdkAndroid = "4.4"
okhttp = "5.3.2"
profileinstaller = "1.4.1"
re2j = "1.8"
reorderable = "3.1.0"
runtime = "1.10.6"
vico = "3.0.3"
Comment thread app/build.gradle.kts Outdated
Comment on lines +210 to +213
// Reorderable
implementation(libs.reorderable)
// Source: https://mvnrepository.com/artifact/com.github.promeg/tinypinyin
implementation("com.github.promeg:tinypinyin:2.0.3")}
Comment on lines +115 to 126
oldMutableBookshelf.updatedBookIds.forEach { bookId ->
viewModelScope.launch(Dispatchers.IO) {
bookRepository.getBookVolumesFlow(bookId).collect {
if (it.volumes.isNotEmpty()) {
viewModelScope.launch(Dispatchers.Main) {
_uiState.bookLastChapterTitleMap[bookId] =
"${it.volumes.last().volumeTitle} ${it.volumes.last().chapters.last().title}"
}
}
}
}
}
Comment on lines +132 to +157
onClick = {
actions.changeSortType(BookshelfSortTypeOptions.getOptionWithValue(item.key).value)
}
)
}
DropdownMenuItem(
enabled = uiState.selectedBookshelf.sortType != BookshelfSortType.Default,
text = {
Text(
text = stringResource(R.string.bookshelf_sort_reverse),
style = MaterialTheme.typography.bodyLarge
)
},
leadingIcon = {
Checkbox(
checked = uiState.selectedBookshelf.sortType != BookshelfSortType.Default &&
uiState.selectedBookshelf.sortReversed,
enabled = uiState.selectedBookshelf.sortType != BookshelfSortType.Default,
onCheckedChange = null
)
},
onClick = {
if (uiState.selectedBookshelf.sortType == BookshelfSortType.Default) return@DropdownMenuItem
actions.changeSortReversed(!uiState.selectedBookshelf.sortReversed)
}
)
Comment on lines +233 to +241
DropdownMenuItem(
text = {
Text(
text = stringResource(R.string.share_bookshelf),
style = MaterialTheme.typography.bodyLarge
)
},
onClick = onShareBookshelf
)
Comment on lines +440 to +444
val stableIndexMap = allBookIds.withIndex().associate { it.value to it.index }
val locale = Locale.getDefault()
val collator = Collator.getInstance(locale)
val sortedIds = when (sortType) {
BookshelfSortType.Default -> allBookIds.filter(sourceIds::contains)
Comment on lines +128 to +142
val allBookIds = remember(uiState.selectedBookshelf.allBookIds) {
uiState.selectedBookshelf.allBookIds.toList()
}
val bookInfoMap = linkedMapOf<String, BookInformation>()
allBookIds.forEach { id ->
val infoFlow = remember(id) { dataSources.getBookInfoFlow(id) }
val info by infoFlow.collectAsStateWithLifecycle()
bookInfoMap[id] = info
}
val bookMetadataMap = linkedMapOf<String, BookshelfBookMetadata?>()
allBookIds.forEach { id ->
val metadataFlow = remember(id) { dataSources.getBookMetadataFlow(id) }
val metadata by metadataFlow.collectAsStateWithLifecycle()
bookMetadataMap[id] = metadata
}
Comment thread gradle/libs.versions.toml
Comment on lines 64 to 72
kotlin-result = { module = "com.michael-bull.kotlin-result:kotlin-result", version.ref = "kotlinResult" }
kotlin-result-coroutines = { module = "com.michael-bull.kotlin-result:kotlin-result-coroutines", version.ref = "kotlinResult" }
matomo-sdk-android = { module = "com.github.matomo-org:matomo-sdk-android", version.ref = "matomoSdkAndroid" }
okhttp = { module = "com.squareup.okhttp3:okhttp", version.ref = "okhttp" }
okhttp3-logging-interceptor = { module = "com.squareup.okhttp3:logging-interceptor", version.ref = "loggingInterceptor" }
re2j = { module = "com.google.re2j:re2j", version.ref = "re2j" }
reorderable = { module = "sh.calvin.reorderable:reorderable", version.ref = "reorderable" }
vico-compose-m3 = { group = "com.patrykandpatrick.vico", name = "compose-m3", version.ref = "vico" }
hilt-android = { module = "com.google.dagger:hilt-android", version.ref = "hilt" }
@dmzz-yyhyy

Copy link
Copy Markdown
Owner

你倒是把构建错误修了啊。。。

@yukonisen yukonisen marked this pull request as draft May 25, 2026 15:31
/** 当前正在阅读的书籍列表路径 @since Api 2 */
data object ReadingBooks : UserDataPath("reading_books")
/** 书架排序路径 @since Api 4 */
data object BookshelfOrder : UserDataPath("bookshelf_order")

Copy link
Copy Markdown
Owner

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

什么叫做排序路径啊

private val groups: List<Set<Int>> = listOf(
setOf(1),
setOf(2, 3)
setOf(2, 3, 4)

Copy link
Copy Markdown
Owner

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

api 4存在编译行为大改,无法向下兼容

Copy link
Copy Markdown
Owner

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

可以提取这种东西,但其实可以放到UiState里去

@yukonisen yukonisen requested a review from dmzz-yyhyy May 30, 2026 10:22
@yukonisen yukonisen marked this pull request as ready for review May 30, 2026 10:25
@dmzz-yyhyy dmzz-yyhyy merged commit eb90c17 into refactoring May 31, 2026
6 checks passed
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

[Bug] 探索页面没有保存状态 [Feature] 增加书架分类的移动排序功能

3 participants