From 2b28b446eb66c478cc72b991a91a0965049da874 Mon Sep 17 00:00:00 2001 From: Super12138 <70494801+Super12138@users.noreply.github.com> Date: Mon, 26 Jan 2026 22:34:39 +0800 Subject: [PATCH] =?UTF-8?q?feat:=20=E4=BD=BF=E7=94=A8=E5=AF=BC=E8=88=AA?= =?UTF-8?q?=E6=96=B9=E5=BC=8F2=20&=20=E6=B7=BB=E5=8A=A0=E8=BD=AC=E5=9C=BA?= =?UTF-8?q?=E5=8A=A8=E7=94=BB?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- app/build.gradle.kts | 2 +- .../cn/super12138/todo/constants/Constants.kt | 3 +- .../cn/super12138/todo/logic/IRepository.kt | 18 ++ .../cn/super12138/todo/logic/Repository.kt | 14 +- .../todo/logic/model/ContrastLevel.kt | 2 +- .../super12138/todo/logic/model/DarkMode.kt | 4 +- .../todo/logic/model/PaletteStyle.kt | 2 +- .../super12138/todo/logic/model/Priority.kt | 2 +- .../todo/logic/model/SortingMethod.kt | 2 +- .../cn/super12138/todo/ui/TodoDefaults.kt | 2 +- .../todo/ui/activities/MainActivity.kt | 36 ++-- .../todo/ui/navigation/SettingsNavigation.kt | 103 +++++++++++ .../todo/ui/navigation/TodoDestinations.kt | 8 +- .../todo/ui/navigation/TodoNavigation.kt | 175 ------------------ .../todo/ui/navigation/TodoScreen.kt | 65 ++++--- .../todo/ui/navigation/TopNavigation.kt | 122 ++++++++++++ .../todo/ui/pages/editor/TodoEditorPage.kt | 65 ++++--- .../todo/ui/pages/overview/OverviewPage.kt | 6 +- .../settings/components/SettingsCategory.kt | 8 +- .../settings/components/SettingsContainer.kt | 4 +- .../pages/{main => tasks}/ProgressFragment.kt | 2 +- .../ui/pages/{main => tasks}/TasksPage.kt | 52 +++--- .../{main => tasks}/components/TodoCard.kt | 17 +- .../components/TodoTopAppBar.kt | 2 +- .../todo/ui/viewmodels/MainViewModel.kt | 4 +- 25 files changed, 413 insertions(+), 307 deletions(-) create mode 100644 app/src/main/kotlin/cn/super12138/todo/logic/IRepository.kt delete mode 100644 app/src/main/kotlin/cn/super12138/todo/ui/navigation/TodoNavigation.kt create mode 100644 app/src/main/kotlin/cn/super12138/todo/ui/navigation/TopNavigation.kt rename app/src/main/kotlin/cn/super12138/todo/ui/pages/{main => tasks}/ProgressFragment.kt (99%) rename app/src/main/kotlin/cn/super12138/todo/ui/pages/{main => tasks}/TasksPage.kt (81%) rename app/src/main/kotlin/cn/super12138/todo/ui/pages/{main => tasks}/components/TodoCard.kt (93%) rename app/src/main/kotlin/cn/super12138/todo/ui/pages/{main => tasks}/components/TodoTopAppBar.kt (99%) diff --git a/app/build.gradle.kts b/app/build.gradle.kts index eb1594a..c291fdc 100644 --- a/app/build.gradle.kts +++ b/app/build.gradle.kts @@ -38,7 +38,7 @@ android { applicationId = "cn.super12138.todo" minSdk = 24 targetSdk = 36 - versionCode = 941 + versionCode = 950 versionName = "2.3.3" testInstrumentationRunner = "androidx.test.runner.AndroidJUnitRunner" diff --git a/app/src/main/kotlin/cn/super12138/todo/constants/Constants.kt b/app/src/main/kotlin/cn/super12138/todo/constants/Constants.kt index 8745294..1b7d8ee 100644 --- a/app/src/main/kotlin/cn/super12138/todo/constants/Constants.kt +++ b/app/src/main/kotlin/cn/super12138/todo/constants/Constants.kt @@ -5,8 +5,7 @@ object Constants { const val GITHUB_REPO = "https://github.com/Super12138/ToDo/" const val KEY_TODO_FAB_TRANSITION = "todo_fab" - // const val KEY_TODO_CONTENT_TRANSITION = "todo_content" - // const val KEY_TODO_CATEGORY_TRANSITION = "todo_category" + const val KEY_TODO_ITEM_TRANSITION = "todo_item_id" const val DB_NAME = "todo" const val DB_TABLE_NAME = "todo" diff --git a/app/src/main/kotlin/cn/super12138/todo/logic/IRepository.kt b/app/src/main/kotlin/cn/super12138/todo/logic/IRepository.kt new file mode 100644 index 0000000..ab6bfd4 --- /dev/null +++ b/app/src/main/kotlin/cn/super12138/todo/logic/IRepository.kt @@ -0,0 +1,18 @@ +package cn.super12138.todo.logic + +import cn.super12138.todo.logic.database.TodoEntity +import kotlinx.coroutines.flow.Flow + +interface IRepository { + suspend fun insertTodo(toDo: TodoEntity) + + fun getAllTodos(): Flow> + + suspend fun updateTodo(toDo: TodoEntity) + + suspend fun deleteTodo(toDo: TodoEntity) + + suspend fun deleteTodoFromIds(toDoItems: List) + + // suspend fun deleteAllTodo() +} \ No newline at end of file diff --git a/app/src/main/kotlin/cn/super12138/todo/logic/Repository.kt b/app/src/main/kotlin/cn/super12138/todo/logic/Repository.kt index 034a5c2..2aa71cc 100644 --- a/app/src/main/kotlin/cn/super12138/todo/logic/Repository.kt +++ b/app/src/main/kotlin/cn/super12138/todo/logic/Repository.kt @@ -4,29 +4,29 @@ import cn.super12138.todo.TodoApp import cn.super12138.todo.logic.database.TodoEntity import kotlinx.coroutines.flow.Flow -object Repository { +object Repository : IRepository { private val db get() = TodoApp.db private val toDoDao = db.toDoDao() - suspend fun insertTodo(toDo: TodoEntity) { + override suspend fun insertTodo(toDo: TodoEntity) { toDoDao.insert(toDo) } - fun getAllTodos(): Flow> = toDoDao.getAll() + override fun getAllTodos(): Flow> = toDoDao.getAll() - suspend fun updateTodo(toDo: TodoEntity) { + override suspend fun updateTodo(toDo: TodoEntity) { toDoDao.update(toDo) } - suspend fun deleteTodo(toDo: TodoEntity) { + override suspend fun deleteTodo(toDo: TodoEntity) { toDoDao.delete(toDo) } - suspend fun deleteTodoFromIds(toDoItems: List) { + override suspend fun deleteTodoFromIds(toDoItems: List) { toDoDao.deleteFromIds(toDoItems.toSet()) } - /*suspend fun deleteAllTodo() { + /*override suspend fun deleteAllTodo() { toDoDao.deleteAllTodo() }*/ } \ No newline at end of file diff --git a/app/src/main/kotlin/cn/super12138/todo/logic/model/ContrastLevel.kt b/app/src/main/kotlin/cn/super12138/todo/logic/model/ContrastLevel.kt index eb6ae6c..4f65193 100644 --- a/app/src/main/kotlin/cn/super12138/todo/logic/model/ContrastLevel.kt +++ b/app/src/main/kotlin/cn/super12138/todo/logic/model/ContrastLevel.kt @@ -5,7 +5,7 @@ import cn.super12138.todo.R enum class ContrastLevel( val value: Float, - @StringRes val nameRes: Int + @param:StringRes val nameRes: Int ) { VeryLow(value = -1f, nameRes = R.string.contrast_very_low), Low(value = -0.5f, nameRes = R.string.contrast_low), diff --git a/app/src/main/kotlin/cn/super12138/todo/logic/model/DarkMode.kt b/app/src/main/kotlin/cn/super12138/todo/logic/model/DarkMode.kt index 55b5392..4df36dd 100644 --- a/app/src/main/kotlin/cn/super12138/todo/logic/model/DarkMode.kt +++ b/app/src/main/kotlin/cn/super12138/todo/logic/model/DarkMode.kt @@ -6,8 +6,8 @@ import cn.super12138.todo.R enum class DarkMode( val id: Int, - @DrawableRes val iconRes: Int, - @StringRes val nameRes: Int + @param:DrawableRes val iconRes: Int, + @param:StringRes val nameRes: Int ) { FollowSystem(id = -1, iconRes = R.drawable.ic_lightbulb_2, nameRes = R.string.dark_mode_system), Light(id = 1, iconRes = R.drawable.ic_light_mode, nameRes = R.string.dark_mode_light), diff --git a/app/src/main/kotlin/cn/super12138/todo/logic/model/PaletteStyle.kt b/app/src/main/kotlin/cn/super12138/todo/logic/model/PaletteStyle.kt index 8f0341b..d22fa38 100644 --- a/app/src/main/kotlin/cn/super12138/todo/logic/model/PaletteStyle.kt +++ b/app/src/main/kotlin/cn/super12138/todo/logic/model/PaletteStyle.kt @@ -5,7 +5,7 @@ import cn.super12138.todo.R enum class PaletteStyle( val id: Int, - @StringRes val nameRes: Int + @param:StringRes val nameRes: Int ) { TonalSpot(id = 1, nameRes = R.string.palette_tonal_spot), Neutral(id = 2, nameRes = R.string.palette_neutral), diff --git a/app/src/main/kotlin/cn/super12138/todo/logic/model/Priority.kt b/app/src/main/kotlin/cn/super12138/todo/logic/model/Priority.kt index 50378f2..ace33e9 100644 --- a/app/src/main/kotlin/cn/super12138/todo/logic/model/Priority.kt +++ b/app/src/main/kotlin/cn/super12138/todo/logic/model/Priority.kt @@ -5,7 +5,7 @@ import cn.super12138.todo.R enum class Priority( val value: Float, - @StringRes val nameRes: Int + @param:StringRes val nameRes: Int ) { Urgent(value = 2f, nameRes = R.string.priority_urgent), Important(value = 1f, nameRes = R.string.priority_important), diff --git a/app/src/main/kotlin/cn/super12138/todo/logic/model/SortingMethod.kt b/app/src/main/kotlin/cn/super12138/todo/logic/model/SortingMethod.kt index 81dadf0..d88614b 100644 --- a/app/src/main/kotlin/cn/super12138/todo/logic/model/SortingMethod.kt +++ b/app/src/main/kotlin/cn/super12138/todo/logic/model/SortingMethod.kt @@ -5,7 +5,7 @@ import cn.super12138.todo.R enum class SortingMethod( val id: Int, - @StringRes val nameRes: Int + @param:StringRes val nameRes: Int ) { // 按添加先后顺序 Sequential(id = 1, nameRes = R.string.sorting_sequential), diff --git a/app/src/main/kotlin/cn/super12138/todo/ui/TodoDefaults.kt b/app/src/main/kotlin/cn/super12138/todo/ui/TodoDefaults.kt index c326260..839f2ea 100644 --- a/app/src/main/kotlin/cn/super12138/todo/ui/TodoDefaults.kt +++ b/app/src/main/kotlin/cn/super12138/todo/ui/TodoDefaults.kt @@ -16,7 +16,7 @@ object TodoDefaults { /** * 屏幕上下预留边距(防止内容全部贴边显示过丑) */ - val screenVerticalPadding = 16.dp + val screenVerticalPadding = 8.dp /** * 待办卡片默认高度 diff --git a/app/src/main/kotlin/cn/super12138/todo/ui/activities/MainActivity.kt b/app/src/main/kotlin/cn/super12138/todo/ui/activities/MainActivity.kt index 32bd9dd..d63b6a4 100644 --- a/app/src/main/kotlin/cn/super12138/todo/ui/activities/MainActivity.kt +++ b/app/src/main/kotlin/cn/super12138/todo/ui/activities/MainActivity.kt @@ -4,6 +4,7 @@ import android.os.Bundle import android.view.WindowManager import androidx.activity.ComponentActivity import androidx.activity.compose.setContent +import androidx.compose.animation.Crossfade import androidx.compose.foundation.isSystemInDarkTheme import androidx.compose.foundation.layout.fillMaxSize import androidx.compose.material3.Icon @@ -26,7 +27,7 @@ import cn.super12138.todo.logic.model.PaletteStyle import cn.super12138.todo.ui.TodoDefaults import cn.super12138.todo.ui.components.Konfetti import cn.super12138.todo.ui.navigation.TodoDestinations -import cn.super12138.todo.ui.navigation.TodoNavigation +import cn.super12138.todo.ui.navigation.TopNavigation import cn.super12138.todo.ui.theme.ToDoTheme import cn.super12138.todo.ui.viewmodels.MainViewModel import cn.super12138.todo.utils.VibrationUtils @@ -39,7 +40,7 @@ class MainActivity : ComponentActivity() { super.onCreate(savedInstanceState) setContent { val mainViewModel: MainViewModel = viewModel() - val navigationBackStack = mainViewModel.topLevelBackStack + val mainBackStack = mainViewModel.mainBackStack val showConfetti = mainViewModel.showConfetti // 主题 val dynamicColor by DataStoreManager.dynamicColorFlow.collectAsState(initial = Constants.PREF_DYNAMIC_COLOR_DEFAULT) @@ -89,27 +90,34 @@ class MainActivity : ComponentActivity() { Surface(color = TodoDefaults.BackgroundColor) { NavigationSuiteScaffold( navigationSuiteItems = { - TodoDestinations.entries.forEach { - val selected = it.route == navigationBackStack.topLevelKey + TodoDestinations.entries.forEach { destination -> + val selected = destination.route == mainBackStack.topLevelKey item( icon = { - Icon( - painter = if (selected) painterResource(it.selectedIcon) else painterResource( - it.icon - ), - contentDescription = null - ) + Crossfade(selected) { + if (it) { + Icon( + painter = painterResource(destination.selectedIcon), + contentDescription = null + ) + } else { + Icon( + painter = painterResource(destination.icon), + contentDescription = null + ) + } + } }, - label = { Text(stringResource(it.label)) }, + label = { Text(stringResource(destination.label)) }, selected = selected, - onClick = { navigationBackStack.addTopLevel(it.route) } + onClick = { mainBackStack.addTopLevel(destination.route) } ) } }, containerColor = TodoDefaults.BackgroundColor ) { - TodoNavigation( - backStack = navigationBackStack, + TopNavigation( + backStack = mainBackStack, viewModel = mainViewModel, modifier = Modifier.fillMaxSize() ) diff --git a/app/src/main/kotlin/cn/super12138/todo/ui/navigation/SettingsNavigation.kt b/app/src/main/kotlin/cn/super12138/todo/ui/navigation/SettingsNavigation.kt index 0b31233..11c38c9 100644 --- a/app/src/main/kotlin/cn/super12138/todo/ui/navigation/SettingsNavigation.kt +++ b/app/src/main/kotlin/cn/super12138/todo/ui/navigation/SettingsNavigation.kt @@ -1,2 +1,105 @@ package cn.super12138.todo.ui.navigation +import androidx.compose.runtime.Composable +import androidx.compose.ui.Modifier +import androidx.navigation3.runtime.NavBackStack +import androidx.navigation3.runtime.NavKey +import androidx.navigation3.runtime.entryProvider +import androidx.navigation3.ui.NavDisplay +import cn.super12138.todo.ui.pages.settings.SettingsAbout +import cn.super12138.todo.ui.pages.settings.SettingsAboutLicence +import cn.super12138.todo.ui.pages.settings.SettingsAppearance +import cn.super12138.todo.ui.pages.settings.SettingsData +import cn.super12138.todo.ui.pages.settings.SettingsDataCategory +import cn.super12138.todo.ui.pages.settings.SettingsDeveloperOptions +import cn.super12138.todo.ui.pages.settings.SettingsDeveloperOptionsPadding +import cn.super12138.todo.ui.pages.settings.SettingsInterface +import cn.super12138.todo.ui.pages.settings.SettingsMain +import cn.super12138.todo.ui.theme.materialSharedAxisX +import cn.super12138.todo.ui.viewmodels.MainViewModel + +private const val INITIAL_OFFSET_FACTOR = 0.10f + +@Composable +fun SettingsNavigation( + backStack: NavBackStack, + viewModel: MainViewModel, + modifier: Modifier = Modifier +) { + fun onBack() { + backStack.removeLastOrNull() + } + + NavDisplay( + backStack = backStack, + onBack = ::onBack, + transitionSpec = { + materialSharedAxisX( + initialOffsetX = { (it * INITIAL_OFFSET_FACTOR).toInt() }, + targetOffsetX = { -(it * INITIAL_OFFSET_FACTOR).toInt() }) + }, + popTransitionSpec = { + materialSharedAxisX( + initialOffsetX = { -(it * INITIAL_OFFSET_FACTOR).toInt() }, + targetOffsetX = { (it * INITIAL_OFFSET_FACTOR).toInt() }) + }, + entryProvider = entryProvider { + entry { + SettingsMain( + toAppearancePage = { backStack.add(TodoScreen.Settings.Appearance) }, + toAboutPage = { backStack.add(TodoScreen.Settings.About) }, + toInterfacePage = { backStack.add(TodoScreen.Settings.Interface) }, + toDataPage = { backStack.add(TodoScreen.Settings.Data) }, + ) + } + + entry { + SettingsAppearance(onNavigateUp = ::onBack) + } + + entry { + SettingsInterface(onNavigateUp = ::onBack) + } + + entry { + SettingsData( + viewModel = viewModel, + toCategoryManager = { backStack.add(TodoScreen.Settings.DataCategory) }, + onNavigateUp = ::onBack + ) + } + + entry { + SettingsDataCategory(onNavigateUp = ::onBack) + } + + entry { + SettingsAbout( + //toSpecialPage = { backStack.add(TodoScreen.Settings.AboutSpecial) }, + toLicencePage = { backStack.add(TodoScreen.Settings.AboutLicence) }, + toDevPage = { backStack.add(TodoScreen.Settings.DeveloperOptions) }, + onNavigateUp = ::onBack, + ) + } + + /*entry { + SettingsAboutSpecial(viewModel = viewModel) + }*/ + + entry { + SettingsAboutLicence(onNavigateUp = ::onBack) + } + + entry { + SettingsDeveloperOptions( + toPaddingPage = { backStack.add(TodoScreen.Settings.DeveloperOptionsPadding) }, + onNavigateUp = ::onBack + ) + } + entry { + SettingsDeveloperOptionsPadding(onNavigateUp = ::onBack) + } + }, + modifier = modifier, + ) +} \ No newline at end of file diff --git a/app/src/main/kotlin/cn/super12138/todo/ui/navigation/TodoDestinations.kt b/app/src/main/kotlin/cn/super12138/todo/ui/navigation/TodoDestinations.kt index 732f77a..096f2eb 100644 --- a/app/src/main/kotlin/cn/super12138/todo/ui/navigation/TodoDestinations.kt +++ b/app/src/main/kotlin/cn/super12138/todo/ui/navigation/TodoDestinations.kt @@ -6,9 +6,9 @@ import androidx.navigation3.runtime.NavKey enum class TodoDestinations( val route: NavKey, - @StringRes val label: Int, - @DrawableRes val icon: Int, - @DrawableRes val selectedIcon: Int + @param:StringRes val label: Int, + @param:DrawableRes val icon: Int, + @param:DrawableRes val selectedIcon: Int ) { Overview( route = TodoScreen.Overview, @@ -23,7 +23,7 @@ enum class TodoDestinations( selectedIcon = cn.super12138.todo.R.drawable.ic_ballot_filled ), Settings( - route = TodoScreen.Settings, + route = TodoScreen.Settings.Main, label = cn.super12138.todo.R.string.page_settings, icon = cn.super12138.todo.R.drawable.ic_settings, selectedIcon = cn.super12138.todo.R.drawable.ic_settings_filled diff --git a/app/src/main/kotlin/cn/super12138/todo/ui/navigation/TodoNavigation.kt b/app/src/main/kotlin/cn/super12138/todo/ui/navigation/TodoNavigation.kt deleted file mode 100644 index fd8f2c6..0000000 --- a/app/src/main/kotlin/cn/super12138/todo/ui/navigation/TodoNavigation.kt +++ /dev/null @@ -1,175 +0,0 @@ -package cn.super12138.todo.ui.navigation - -import androidx.compose.animation.EnterTransition -import androidx.compose.animation.ExitTransition -import androidx.compose.animation.ExperimentalSharedTransitionApi -import androidx.compose.animation.SharedTransitionLayout -import androidx.compose.animation.core.tween -import androidx.compose.animation.fadeIn -import androidx.compose.animation.fadeOut -import androidx.compose.animation.slideInVertically -import androidx.compose.animation.slideOutVertically -import androidx.compose.animation.togetherWith -import androidx.compose.runtime.Composable -import androidx.compose.ui.Modifier -import androidx.navigation3.runtime.NavKey -import androidx.navigation3.runtime.entryProvider -import androidx.navigation3.ui.NavDisplay -import cn.super12138.todo.ui.pages.editor.TodoEditorPage -import cn.super12138.todo.ui.pages.main.MainPage -import cn.super12138.todo.ui.pages.overview.OverviewPage -import cn.super12138.todo.ui.pages.settings.SettingsAbout -import cn.super12138.todo.ui.pages.settings.SettingsAboutLicence -import cn.super12138.todo.ui.pages.settings.SettingsAppearance -import cn.super12138.todo.ui.pages.settings.SettingsData -import cn.super12138.todo.ui.pages.settings.SettingsDataCategory -import cn.super12138.todo.ui.pages.settings.SettingsDeveloperOptions -import cn.super12138.todo.ui.pages.settings.SettingsDeveloperOptionsPadding -import cn.super12138.todo.ui.pages.settings.SettingsInterface -import cn.super12138.todo.ui.pages.settings.SettingsMain -import cn.super12138.todo.ui.theme.materialSharedAxisX -import cn.super12138.todo.ui.viewmodels.MainViewModel - -private const val INITIAL_OFFSET_FACTOR = 0.10f - -@OptIn(ExperimentalSharedTransitionApi::class) -@Composable -fun TodoNavigation( - backStack: TopLevelBackStack, - modifier: Modifier = Modifier, - viewModel: MainViewModel -) { - fun onBack() { - backStack.removeLast() - } - - val anim = NavDisplay.transitionSpec { - // Slide new content up, keeping the old content in place underneath - slideInVertically( - initialOffsetY = { it / 5 }, - animationSpec = tween(200) - ) + fadeIn(tween(200)) togetherWith ExitTransition.KeepUntilTransitionsFinished - } + NavDisplay.popTransitionSpec { - // Slide old content down, revealing the new content in place underneath - EnterTransition.None togetherWith - slideOutVertically( - targetOffsetY = { it / 5 }, - animationSpec = tween(200) - ) + fadeOut(tween(200)) - } + NavDisplay.predictivePopTransitionSpec { - // Slide old content down, revealing the new content in place underneath - EnterTransition.None togetherWith - slideOutVertically( - targetOffsetY = { it / 5 }, - animationSpec = tween(200) - ) + fadeOut(tween(200)) - } - - SharedTransitionLayout { - NavDisplay( - backStack = backStack.backStack, - onBack = ::onBack, - transitionSpec = { - materialSharedAxisX( - initialOffsetX = { (it * INITIAL_OFFSET_FACTOR).toInt() }, - targetOffsetX = { -(it * INITIAL_OFFSET_FACTOR).toInt() }) - }, - popTransitionSpec = { - materialSharedAxisX( - initialOffsetX = { -(it * INITIAL_OFFSET_FACTOR).toInt() }, - targetOffsetX = { (it * INITIAL_OFFSET_FACTOR).toInt() }) - }, - entryProvider = entryProvider { - entry(metadata = anim) { - OverviewPage() - } - entry(metadata = anim) { - MainPage( - viewModel = viewModel, - toTodoEditPage = { backStack.add(TodoScreen.Editor(it)) }, - sharedTransitionScope = this@SharedTransitionLayout - ) - } - - entry(metadata = anim) { - SettingsMain( - toAppearancePage = { backStack.add(TodoScreen.SettingsAppearance) }, - toAboutPage = { backStack.add(TodoScreen.SettingsAbout) }, - toInterfacePage = { backStack.add(TodoScreen.SettingsInterface) }, - toDataPage = { backStack.add(TodoScreen.SettingsData) }, - ) - } - - entry { editorArgs -> - TodoEditorPage( - toDo = editorArgs.toDo, - onSave = { - viewModel.addTodo(it) - // 如果原来的待办状态为未完成并且修改后状态为完成 - if (editorArgs.toDo?.isCompleted != true && it.isCompleted) { - viewModel.playConfetti() - } - onBack() - }, - onDelete = { - if (editorArgs.toDo !== null) { - viewModel.deleteTodo(editorArgs.toDo) - } - onBack() - }, - onNavigateUp = ::onBack, - sharedTransitionScope = this@SharedTransitionLayout - ) - } - - entry { - SettingsAppearance(onNavigateUp = ::onBack) - } - - entry { - SettingsInterface(onNavigateUp = ::onBack) - } - - entry { - SettingsData( - viewModel = viewModel, - toCategoryManager = { backStack.add(TodoScreen.SettingsDataCategory) }, - onNavigateUp = ::onBack - ) - } - - entry { - SettingsDataCategory(onNavigateUp = ::onBack) - } - - entry { - SettingsAbout( - //toSpecialPage = { backStack.add(TodoScreen.SettingsAboutSpecial) }, - toLicencePage = { backStack.add(TodoScreen.SettingsAboutLicence) }, - toDevPage = { backStack.add(TodoScreen.SettingsDev) }, - onNavigateUp = ::onBack, - ) - } - - /*entry { - SettingsAboutSpecial(viewModel = viewModel) - }*/ - - entry { - SettingsAboutLicence(onNavigateUp = ::onBack) - } - - entry { - SettingsDeveloperOptions( - toPaddingPage = { backStack.add(TodoScreen.SettingsDevPadding) }, - onNavigateUp = ::onBack - ) - } - entry { - SettingsDeveloperOptionsPadding(onNavigateUp = ::onBack) - } - }, - modifier = modifier, - ) - } -} \ No newline at end of file diff --git a/app/src/main/kotlin/cn/super12138/todo/ui/navigation/TodoScreen.kt b/app/src/main/kotlin/cn/super12138/todo/ui/navigation/TodoScreen.kt index 298959c..701464d 100644 --- a/app/src/main/kotlin/cn/super12138/todo/ui/navigation/TodoScreen.kt +++ b/app/src/main/kotlin/cn/super12138/todo/ui/navigation/TodoScreen.kt @@ -13,35 +13,44 @@ sealed class TodoScreen : NavKey { data object Tasks : TodoScreen() @Serializable - data class Editor(val toDo: TodoEntity?) : TodoScreen() + sealed class Settings : TodoScreen() { + @Serializable + data object Main : Settings() + + @Serializable + data object Appearance : Settings() + + @Serializable + data object Interface : Settings() + + @Serializable + data object Data : Settings() + + @Serializable + data object DataCategory : Settings() + + @Serializable + data object About : Settings() + + // @Serializable + // data object AboutEasterEgg : Settings() + + @Serializable + data object AboutLicence : Settings() + + @Serializable + data object DeveloperOptions : Settings() + + @Serializable + data object DeveloperOptionsPadding : Settings() + } @Serializable - data object Settings : TodoScreen() + sealed class Editor : TodoScreen() { + @Serializable + data object Add : Editor() - @Serializable - data object SettingsAppearance : TodoScreen() - - @Serializable - data object SettingsInterface : TodoScreen() - - @Serializable - data object SettingsData : TodoScreen() - - @Serializable - data object SettingsDataCategory : TodoScreen() - - @Serializable - data object SettingsAbout : TodoScreen() - - // @Serializable - // data object SettingsAboutSpecial : TodoScreen() - - @Serializable - data object SettingsAboutLicence : TodoScreen() - - @Serializable - data object SettingsDev : TodoScreen() - - @Serializable - data object SettingsDevPadding : TodoScreen() + @Serializable + data class Edit(val toDo: TodoEntity) : Editor() + } } diff --git a/app/src/main/kotlin/cn/super12138/todo/ui/navigation/TopNavigation.kt b/app/src/main/kotlin/cn/super12138/todo/ui/navigation/TopNavigation.kt new file mode 100644 index 0000000..b71834e --- /dev/null +++ b/app/src/main/kotlin/cn/super12138/todo/ui/navigation/TopNavigation.kt @@ -0,0 +1,122 @@ +package cn.super12138.todo.ui.navigation + +import androidx.compose.animation.ExperimentalAnimationApi +import androidx.compose.animation.SharedTransitionLayout +import androidx.compose.animation.fadeIn +import androidx.compose.animation.fadeOut +import androidx.compose.animation.togetherWith +import androidx.compose.animation.unveilIn +import androidx.compose.animation.veilOut +import androidx.compose.material3.MaterialTheme +import androidx.compose.runtime.Composable +import androidx.compose.ui.Modifier +import androidx.navigation3.runtime.NavKey +import androidx.navigation3.runtime.entryProvider +import androidx.navigation3.ui.NavDisplay +import cn.super12138.todo.ui.pages.editor.TodoAddPage +import cn.super12138.todo.ui.pages.editor.TodoEditPage +import cn.super12138.todo.ui.pages.overview.OverviewPage +import cn.super12138.todo.ui.pages.tasks.TasksPage +import cn.super12138.todo.ui.viewmodels.MainViewModel + +@OptIn(ExperimentalAnimationApi::class) +@Composable +fun TopNavigation( + backStack: TopLevelBackStack, + modifier: Modifier = Modifier, + viewModel: MainViewModel +) { + fun onBack() { + backStack.removeLast() + } + /* + * NavDisplay.transitionSpec { + * // Slide new content up, keeping the old content in place underneath + * slideInVertically( + * initialOffsetY = { it / 5 }, + * animationSpec = tween(200) + * ) + fadeIn(tween(200)) togetherWith ExitTransition.KeepUntilTransitionsFinished + * } + NavDisplay.popTransitionSpec { + * // Slide old content down, revealing the new content in place underneath + * EnterTransition.None togetherWith + * slideOutVertically( + * targetOffsetY = { it / 5 }, + * animationSpec = tween(200) + * ) + fadeOut(tween(200)) + * } + NavDisplay.predictivePopTransitionSpec { + * // Slide old content down, revealing the new content in place underneath + * EnterTransition.None togetherWith + * slideOutVertically( + * targetOffsetY = { it / 5 }, + * animationSpec = tween(200) + * ) + fadeOut(tween(200)) + * } + */ + + val veilColor = MaterialTheme.colorScheme.surfaceDim + SharedTransitionLayout { + NavDisplay( + backStack = backStack.backStack, + onBack = ::onBack, + transitionSpec = { + fadeIn() togetherWith veilOut(targetColor = veilColor) + }, + popTransitionSpec = { + unveilIn(initialColor = veilColor) togetherWith fadeOut() + }, + predictivePopTransitionSpec = { + unveilIn(initialColor = veilColor) togetherWith fadeOut() + }, + entryProvider = entryProvider { + entry { + OverviewPage() + } + + entry { + TasksPage( + viewModel = viewModel, + toTodoAddPage = { backStack.add(TodoScreen.Editor.Add) }, + toTodoEditPage = { backStack.add(TodoScreen.Editor.Edit(it)) } + ) + } + + entry { + TodoAddPage( + onSave = { + viewModel.addTodo(it) + onBack() + }, + onNavigateUp = ::onBack + ) + } + + entry { editorArgs -> + TodoEditPage( + toDo = editorArgs.toDo, + onSave = { + viewModel.addTodo(it) + // 如果原来的待办状态为未完成并且修改后状态为完成 + if (!editorArgs.toDo.isCompleted && it.isCompleted) { + viewModel.playConfetti() + } + onBack() + }, + onDelete = { + viewModel.deleteTodo(editorArgs.toDo) + onBack() + }, + onNavigateUp = ::onBack + ) + } + + entry { + SettingsNavigation( + backStack = viewModel.settingsBackStack, + viewModel = viewModel + ) + } + }, + modifier = modifier, + ) + } +} \ No newline at end of file diff --git a/app/src/main/kotlin/cn/super12138/todo/ui/pages/editor/TodoEditorPage.kt b/app/src/main/kotlin/cn/super12138/todo/ui/pages/editor/TodoEditorPage.kt index fb1bbae..51ed747 100644 --- a/app/src/main/kotlin/cn/super12138/todo/ui/pages/editor/TodoEditorPage.kt +++ b/app/src/main/kotlin/cn/super12138/todo/ui/pages/editor/TodoEditorPage.kt @@ -2,7 +2,6 @@ package cn.super12138.todo.ui.pages.editor import androidx.activity.compose.BackHandler import androidx.compose.animation.AnimatedVisibility -import androidx.compose.animation.ExperimentalSharedTransitionApi import androidx.compose.animation.SharedTransitionScope import androidx.compose.animation.expandVertically import androidx.compose.animation.fadeIn @@ -17,12 +16,9 @@ import androidx.compose.foundation.layout.imePadding import androidx.compose.foundation.layout.padding import androidx.compose.foundation.layout.size import androidx.compose.foundation.lazy.LazyColumn -import androidx.compose.material3.ExperimentalMaterial3Api -import androidx.compose.material3.ExperimentalMaterial3ExpressiveApi import androidx.compose.material3.MaterialTheme import androidx.compose.material3.Switch import androidx.compose.material3.Text -import androidx.compose.material3.TopAppBarDefaults import androidx.compose.runtime.Composable import androidx.compose.runtime.LaunchedEffect import androidx.compose.runtime.collectAsState @@ -41,6 +37,7 @@ import cn.super12138.todo.R import cn.super12138.todo.constants.Constants import cn.super12138.todo.logic.database.TodoEntity import cn.super12138.todo.logic.datastore.DataStoreManager +import cn.super12138.todo.ui.TodoDefaults import cn.super12138.todo.ui.components.ChipItem import cn.super12138.todo.ui.components.ConfirmDialog import cn.super12138.todo.ui.components.TodoFloatingActionButton @@ -52,23 +49,50 @@ import cn.super12138.todo.ui.pages.editor.components.TodoPrioritySlider import cn.super12138.todo.ui.pages.editor.state.rememberEditorState import cn.super12138.todo.utils.VibrationUtils -@OptIn( - ExperimentalMaterial3Api::class, ExperimentalSharedTransitionApi::class, - ExperimentalMaterial3ExpressiveApi::class -) @Composable -fun TodoEditorPage( +fun SharedTransitionScope.TodoAddPage( + modifier: Modifier = Modifier, + onSave: (TodoEntity) -> Unit, + onNavigateUp: () -> Unit +) = TodoEditorPage( + toDo = null, + modifier = modifier.sharedBounds( + sharedContentState = rememberSharedContentState(key = Constants.KEY_TODO_FAB_TRANSITION), + animatedVisibilityScope = LocalNavAnimatedContentScope.current + ), + onSave = onSave, + onDelete = {}, + onNavigateUp = onNavigateUp +) + +@Composable +fun SharedTransitionScope.TodoEditPage( + modifier: Modifier = Modifier, + toDo: TodoEntity, + onSave: (TodoEntity) -> Unit, + onDelete: () -> Unit, + onNavigateUp: () -> Unit +) = TodoEditorPage( + toDo = toDo, + modifier = modifier.sharedBounds( + sharedContentState = rememberSharedContentState(key = "${Constants.KEY_TODO_ITEM_TRANSITION}_${toDo.id}"), + animatedVisibilityScope = LocalNavAnimatedContentScope.current + ), + onSave = onSave, + onDelete = onDelete, + onNavigateUp = onNavigateUp +) + +@Composable +private fun TodoEditorPage( modifier: Modifier = Modifier, toDo: TodoEntity? = null, onSave: (TodoEntity) -> Unit, onDelete: () -> Unit, - onNavigateUp: () -> Unit, - sharedTransitionScope: SharedTransitionScope + onNavigateUp: () -> Unit ) { // TODO: 本页及其相关组件重组性能检查优化 val view = LocalView.current - val animatedVisibilityScope = LocalNavAnimatedContentScope.current - TopAppBarDefaults.exitUntilCollapsedScrollBehavior() val uiState = rememberEditorState(initialTodo = toDo) @@ -114,7 +138,6 @@ fun TodoEditorPage( TopAppBarScaffold( title = stringResource(if (toDo != null) R.string.title_edit_task else R.string.action_add_task), floatingActionButton = { - with(sharedTransitionScope) { Row( horizontalArrangement = Arrangement.spacedBy(10.dp), modifier = Modifier.imePadding() @@ -146,15 +169,9 @@ fun TodoEditorPage( ) onSave(newTodo) } - }, - modifier = Modifier - .sharedElement( - sharedContentState = rememberSharedContentState(key = Constants.KEY_TODO_FAB_TRANSITION), - animatedVisibilityScope = animatedVisibilityScope - ) + } ) } - } }, onBack = ::checkModifiedBeforeBack, modifier = modifier @@ -163,6 +180,10 @@ fun TodoEditorPage( verticalArrangement = Arrangement.spacedBy(5.dp), modifier = Modifier.fillMaxSize() ) { + item { + Spacer(modifier = Modifier.size(TodoDefaults.screenVerticalPadding)) + } + item { TodoContentTextField( value = uiState.toDoContent, @@ -241,7 +262,7 @@ fun TodoEditorPage( } item { - Spacer(modifier = Modifier.size(80.dp)) + Spacer(modifier = Modifier.size(TodoDefaults.screenVerticalPadding)) } } diff --git a/app/src/main/kotlin/cn/super12138/todo/ui/pages/overview/OverviewPage.kt b/app/src/main/kotlin/cn/super12138/todo/ui/pages/overview/OverviewPage.kt index 106e7bb..65dfca8 100644 --- a/app/src/main/kotlin/cn/super12138/todo/ui/pages/overview/OverviewPage.kt +++ b/app/src/main/kotlin/cn/super12138/todo/ui/pages/overview/OverviewPage.kt @@ -1,6 +1,7 @@ package cn.super12138.todo.ui.pages.overview -import androidx.compose.foundation.layout.Row +import androidx.compose.animation.ExperimentalAnimationApi +import androidx.compose.foundation.layout.Column import androidx.compose.material3.Card import androidx.compose.material3.Icon import androidx.compose.material3.Text @@ -11,13 +12,14 @@ import androidx.compose.ui.res.stringResource import cn.super12138.todo.R import cn.super12138.todo.ui.components.TopAppBarScaffold +@OptIn(ExperimentalAnimationApi::class) @Composable fun OverviewPage(modifier: Modifier = Modifier) { TopAppBarScaffold( title = stringResource(R.string.page_overview), modifier = modifier ) { - Row { + Column { Card { Icon(painter = painterResource(R.drawable.ic_ballot), contentDescription = null) Text("总任务") diff --git a/app/src/main/kotlin/cn/super12138/todo/ui/pages/settings/components/SettingsCategory.kt b/app/src/main/kotlin/cn/super12138/todo/ui/pages/settings/components/SettingsCategory.kt index 099ec10..3d940e3 100644 --- a/app/src/main/kotlin/cn/super12138/todo/ui/pages/settings/components/SettingsCategory.kt +++ b/app/src/main/kotlin/cn/super12138/todo/ui/pages/settings/components/SettingsCategory.kt @@ -21,10 +21,10 @@ fun SettingsCategory( modifier = modifier .fillMaxWidth() .padding( - top = if (first) 0.dp else TodoDefaults.settingsItemVerticalPadding, - start = TodoDefaults.settingsItemHorizontalPadding / 2, - end = TodoDefaults.settingsItemHorizontalPadding / 2, - bottom = TodoDefaults.settingsItemVerticalPadding / 2 + top = if (first) 0.dp else TodoDefaults.screenVerticalPadding, + start = TodoDefaults.screenHorizontalPadding / 2, + end = TodoDefaults.screenHorizontalPadding / 2, + bottom = TodoDefaults.screenVerticalPadding ) ) { Text( diff --git a/app/src/main/kotlin/cn/super12138/todo/ui/pages/settings/components/SettingsContainer.kt b/app/src/main/kotlin/cn/super12138/todo/ui/pages/settings/components/SettingsContainer.kt index 5f4cce1..d14ee41 100644 --- a/app/src/main/kotlin/cn/super12138/todo/ui/pages/settings/components/SettingsContainer.kt +++ b/app/src/main/kotlin/cn/super12138/todo/ui/pages/settings/components/SettingsContainer.kt @@ -23,13 +23,13 @@ fun SettingsContainer( modifier = modifier ) { item { - Spacer(modifier = Modifier.size(TodoDefaults.settingsItemVerticalPadding)) + Spacer(modifier = Modifier.size(TodoDefaults.screenVerticalPadding)) } content() item { - Spacer(modifier = Modifier.size(TodoDefaults.settingsItemVerticalPadding)) + Spacer(modifier = Modifier.size(TodoDefaults.screenVerticalPadding)) } } } \ No newline at end of file diff --git a/app/src/main/kotlin/cn/super12138/todo/ui/pages/main/ProgressFragment.kt b/app/src/main/kotlin/cn/super12138/todo/ui/pages/tasks/ProgressFragment.kt similarity index 99% rename from app/src/main/kotlin/cn/super12138/todo/ui/pages/main/ProgressFragment.kt rename to app/src/main/kotlin/cn/super12138/todo/ui/pages/tasks/ProgressFragment.kt index 10f5d77..d38259b 100644 --- a/app/src/main/kotlin/cn/super12138/todo/ui/pages/main/ProgressFragment.kt +++ b/app/src/main/kotlin/cn/super12138/todo/ui/pages/tasks/ProgressFragment.kt @@ -1,4 +1,4 @@ -package cn.super12138.todo.ui.pages.main +package cn.super12138.todo.ui.pages.tasks import androidx.compose.animation.AnimatedVisibility import androidx.compose.animation.core.animateFloatAsState diff --git a/app/src/main/kotlin/cn/super12138/todo/ui/pages/main/TasksPage.kt b/app/src/main/kotlin/cn/super12138/todo/ui/pages/tasks/TasksPage.kt similarity index 81% rename from app/src/main/kotlin/cn/super12138/todo/ui/pages/main/TasksPage.kt rename to app/src/main/kotlin/cn/super12138/todo/ui/pages/tasks/TasksPage.kt index 2efff83..f750e16 100644 --- a/app/src/main/kotlin/cn/super12138/todo/ui/pages/main/TasksPage.kt +++ b/app/src/main/kotlin/cn/super12138/todo/ui/pages/tasks/TasksPage.kt @@ -1,4 +1,4 @@ -package cn.super12138.todo.ui.pages.main +package cn.super12138.todo.ui.pages.tasks import androidx.activity.compose.BackHandler import androidx.compose.animation.SharedTransitionScope @@ -38,17 +38,17 @@ import cn.super12138.todo.ui.TodoDefaults import cn.super12138.todo.ui.components.ConfirmDialog import cn.super12138.todo.ui.components.TodoFloatingActionButton import cn.super12138.todo.ui.components.TopAppBarScaffold -import cn.super12138.todo.ui.pages.main.components.TodoCard -import cn.super12138.todo.ui.pages.main.components.TodoTopAppBar +import cn.super12138.todo.ui.pages.tasks.components.TodoCard +import cn.super12138.todo.ui.pages.tasks.components.TodoTopAppBar import cn.super12138.todo.ui.viewmodels.MainViewModel @OptIn(ExperimentalMaterial3ExpressiveApi::class) @Composable -fun MainPage( +fun SharedTransitionScope.TasksPage( modifier: Modifier = Modifier, viewModel: MainViewModel, - toTodoEditPage: (TodoEntity?) -> Unit, - sharedTransitionScope: SharedTransitionScope, + toTodoAddPage: () -> Unit, + toTodoEditPage: (TodoEntity) -> Unit, ) { val animatedVisibilityScope = LocalNavAnimatedContentScope.current @@ -82,23 +82,21 @@ fun MainPage( ) }, floatingActionButton = { - with(sharedTransitionScope) { - TodoFloatingActionButton( - text = stringResource(R.string.action_add_task), - iconRes = R.drawable.ic_add, - expanded = expandedFab, - onClick = { toTodoEditPage(null) }, - modifier = Modifier - .sharedElement( - sharedContentState = rememberSharedContentState(key = Constants.KEY_TODO_FAB_TRANSITION), - animatedVisibilityScope = animatedVisibilityScope - ) - .animateFloatingActionButton( - visible = !inSelectedMode, - alignment = Alignment.BottomEnd, - ) - ) - } + TodoFloatingActionButton( + text = stringResource(R.string.action_add_task), + iconRes = R.drawable.ic_add, + expanded = expandedFab, + onClick = { toTodoAddPage() }, + modifier = Modifier + .sharedBounds( + sharedContentState = rememberSharedContentState(key = Constants.KEY_TODO_FAB_TRANSITION), + animatedVisibilityScope = animatedVisibilityScope + ) + .animateFloatingActionButton( + visible = !inSelectedMode, + alignment = Alignment.BottomEnd, + ) + ) }, contentWindowInsets = WindowInsets(0, 0, 0, 0), modifier = modifier @@ -109,7 +107,7 @@ fun MainPage( modifier = Modifier.fillMaxSize() ) { item { - Spacer(modifier = Modifier.size(TodoDefaults.settingsItemVerticalPadding)) + Spacer(modifier = Modifier.size(TodoDefaults.screenVerticalPadding)) } if (filteredTodoList.isEmpty()) { @@ -146,6 +144,10 @@ fun MainPage( viewModel.playConfetti() }, modifier = Modifier + .sharedBounds( + sharedContentState = rememberSharedContentState(key = "${Constants.KEY_TODO_ITEM_TRANSITION}_${it.id}"), + animatedVisibilityScope = LocalNavAnimatedContentScope.current + ) .animateItem( fadeInSpec = MaterialTheme.motionScheme.defaultEffectsSpec(), placementSpec = MaterialTheme.motionScheme.defaultSpatialSpec(), @@ -154,7 +156,7 @@ fun MainPage( ) } item { - Spacer(modifier = Modifier.size(TodoDefaults.settingsItemVerticalPadding)) + Spacer(modifier = Modifier.size(TodoDefaults.screenVerticalPadding)) } } } diff --git a/app/src/main/kotlin/cn/super12138/todo/ui/pages/main/components/TodoCard.kt b/app/src/main/kotlin/cn/super12138/todo/ui/pages/tasks/components/TodoCard.kt similarity index 93% rename from app/src/main/kotlin/cn/super12138/todo/ui/pages/main/components/TodoCard.kt rename to app/src/main/kotlin/cn/super12138/todo/ui/pages/tasks/components/TodoCard.kt index 57db1c5..9910509 100644 --- a/app/src/main/kotlin/cn/super12138/todo/ui/pages/main/components/TodoCard.kt +++ b/app/src/main/kotlin/cn/super12138/todo/ui/pages/tasks/components/TodoCard.kt @@ -1,12 +1,10 @@ -package cn.super12138.todo.ui.pages.main.components +package cn.super12138.todo.ui.pages.tasks.components import androidx.compose.animation.AnimatedVisibility -import androidx.compose.animation.ExperimentalSharedTransitionApi import androidx.compose.animation.expandHorizontally import androidx.compose.animation.fadeIn import androidx.compose.animation.fadeOut import androidx.compose.animation.shrinkHorizontally -import androidx.compose.foundation.ExperimentalFoundationApi import androidx.compose.foundation.background import androidx.compose.foundation.basicMarquee import androidx.compose.foundation.combinedClickable @@ -21,7 +19,8 @@ import androidx.compose.foundation.layout.padding import androidx.compose.foundation.shape.CircleShape import androidx.compose.material3.Badge import androidx.compose.material3.BadgedBox -import androidx.compose.material3.ElevatedCard +import androidx.compose.material3.Card +import androidx.compose.material3.CardDefaults import androidx.compose.material3.ExperimentalMaterial3ExpressiveApi import androidx.compose.material3.Icon import androidx.compose.material3.IconButton @@ -32,7 +31,6 @@ import androidx.compose.runtime.Composable import androidx.compose.ui.Alignment import androidx.compose.ui.Modifier import androidx.compose.ui.draw.clip -import androidx.compose.ui.platform.LocalContext import androidx.compose.ui.platform.LocalView import androidx.compose.ui.res.painterResource import androidx.compose.ui.res.stringResource @@ -45,10 +43,7 @@ import cn.super12138.todo.ui.TodoDefaults import cn.super12138.todo.utils.VibrationUtils import cn.super12138.todo.utils.containerColor -@OptIn( - ExperimentalFoundationApi::class, ExperimentalSharedTransitionApi::class, - ExperimentalMaterial3ExpressiveApi::class -) +@OptIn(ExperimentalMaterial3ExpressiveApi::class) @Composable fun TodoCard( modifier: Modifier = Modifier, @@ -63,8 +58,8 @@ fun TodoCard( onChecked: () -> Unit = {} ) { val view = LocalView.current - val context = LocalContext.current - ElevatedCard( + Card( + colors = CardDefaults.cardColors(containerColor = TodoDefaults.ContainerColor), modifier = modifier .fillMaxWidth() .height(TodoDefaults.toDoCardHeight) diff --git a/app/src/main/kotlin/cn/super12138/todo/ui/pages/main/components/TodoTopAppBar.kt b/app/src/main/kotlin/cn/super12138/todo/ui/pages/tasks/components/TodoTopAppBar.kt similarity index 99% rename from app/src/main/kotlin/cn/super12138/todo/ui/pages/main/components/TodoTopAppBar.kt rename to app/src/main/kotlin/cn/super12138/todo/ui/pages/tasks/components/TodoTopAppBar.kt index d570b0b..20d6c54 100644 --- a/app/src/main/kotlin/cn/super12138/todo/ui/pages/main/components/TodoTopAppBar.kt +++ b/app/src/main/kotlin/cn/super12138/todo/ui/pages/tasks/components/TodoTopAppBar.kt @@ -1,4 +1,4 @@ -package cn.super12138.todo.ui.pages.main.components +package cn.super12138.todo.ui.pages.tasks.components import androidx.compose.animation.AnimatedContent import androidx.compose.animation.AnimatedVisibility diff --git a/app/src/main/kotlin/cn/super12138/todo/ui/viewmodels/MainViewModel.kt b/app/src/main/kotlin/cn/super12138/todo/ui/viewmodels/MainViewModel.kt index c97ace1..76525c9 100644 --- a/app/src/main/kotlin/cn/super12138/todo/ui/viewmodels/MainViewModel.kt +++ b/app/src/main/kotlin/cn/super12138/todo/ui/viewmodels/MainViewModel.kt @@ -5,6 +5,7 @@ import android.net.Uri import androidx.compose.runtime.mutableStateOf import androidx.lifecycle.ViewModel import androidx.lifecycle.viewModelScope +import androidx.navigation3.runtime.NavBackStack import androidx.navigation3.runtime.NavKey import cn.super12138.todo.TodoApp import cn.super12138.todo.constants.Constants @@ -35,7 +36,8 @@ import java.util.zip.ZipOutputStream @OptIn(ExperimentalCoroutinesApi::class) class MainViewModel : ViewModel() { - val topLevelBackStack = TopLevelBackStack(startKey = TodoScreen.Overview) + val mainBackStack = TopLevelBackStack(TodoScreen.Overview) + val settingsBackStack = NavBackStack(TodoScreen.Settings.Main) // 待办 private val toDos: Flow> = Repository.getAllTodos()