news 2026/4/23 11:39:28

Jetpack Compose Navigation 全面使用指南

作者头像

张小明

前端开发工程师

1.2k 24
文章封面图
Jetpack Compose Navigation 全面使用指南

🧭 一、为什么需要 Navigation?

在 Compose 中,你不再用Activity 跳转,而是用“声明式导航”

  • 页面 =Composable 函数
  • 跳转 =改变当前“目的地”(Destination)
  • 返回 =从导航栈弹出

Jetpack Compose Navigation 提供了一套统一、安全、带生命周期管理的导航方案。

🛠 二、快速上手:3 步实现页面跳转

第 1 步:添加依赖(build.gradle)

implementation"androidx.navigation:navigation-compose:2.8.0"

第 2 步:定义你的页面(Composable)

@ComposablefunHomeScreen(onNavigateToProfile:()->Unit){Column{Text("首页")Button(onClick=onNavigateToProfile){Text("去个人页")}}}@ComposablefunProfileScreen(){Text("个人中心")}

第 3 步:搭建导航图(NavGraph)

@ComposablefunMyApp(){valnavController=rememberNavController()NavHost(navController=navController,startDestination="home"){composable("home"){HomeScreen{navController.navigate("profile")}}composable("profile"){ProfileScreen()}}}

✅ 效果:点击按钮 → 跳转到个人页!

✅ 返回键自动生效(因为 NavHost 管理了返回栈)

🔑 三、核心概念解析

概念说明
NavController导航控制器,负责跳转、返回等操作
NavHost导航容器,定义所有页面(目的地)
composable(route)声明一个页面,route 是唯一标识(如 “profile”)
导航栈(Back Stack)记录用户访问路径,支持返回

💡 记住:

  • rememberNavController():在 Composable 中获取 NavController
  • 每个 composable 块对应一个页面

📦 四、页面传参(Arguments)

场景:从首页跳转到用户详情页,传userId

✅ 步骤 1:定义带参数的 route
// 使用 {id} 占位符composable("user/{userId}"){backStackEntry->// 从 backStackEntry 获取参数valuserId=backStackEntry.arguments?.getString("userId")?:"unknown"UserDetailScreen(userId=userId)}
✅ 步骤 2:跳转时传值
// 在 HomeScreen 中Button(onClick={navController.navigate("user/123")})

✅ 进阶:类型安全传参(推荐!)

使用 Navigation Safe Args(Compose 版) 或 自定义解析。

方法 A:手动解析(简单场景)
composable("user/{userId}"){entry->valuserId=entry.pathSegments[1]// ["user", "123"]UserDetailScreen(userId)}
方法 B:使用 navArgs + Parcelable(更安全)
// 定义数据类@ParcelizedataclassUserArgs(valid:String,valname:String):Parcelable// 跳转valargs=UserArgs("123","Alice")navController.navigate("user?args=${Uri.encode(args.toString())}")// 不推荐,复杂// 更推荐:直接拼接基础类型navController.navigate("user/${userId}")

📌 官方建议:

对于简单参数(String/Int),直接用 {param};

复杂对象优先通过 ViewModel 共享,而非导航传参。

🔙 五、返回并传递结果(类似 startActivityForResult)

Compose Navigation 原生不支持返回结果,但我们可以用 ViewModel + Shared State 实现。
✅ 推荐方案:共享 ViewModel

// 共享 ViewModel@HiltViewModelclassSharedViewModel@Injectconstructor():ViewModel(){privateval_selectedItem=MutableStateFlow<String?>("")valselectedItem=_selectedItem.asStateFlow()funselectItem(item:String){_selectedItem.value=item}}// 主页@ComposablefunSelectHomeScreen(viewModel:SharedViewModel,onNavigateToSelectItem:()->Unit){valselectedItembyviewModel.selectedItem.collectAsState()Column{Text("选中数据:${selectedItem}")Button(onClick=onNavigateToSelectItem){Text("选项选择")}}}// 选择页@ComposablefunPickerScreen(viewModel:SharedViewModel,onNavigateBackHome:()->Unit){Column{Button(onClick={viewModel.selectItem("选项A")onNavigateBackHome()}){Text("选项A")}}}

✅ 优点:解耦、可测试、支持跨多层返回

💡 注:HiltViewModel 如果没有这个注解,需要引入依赖:

implementation("androidx.hilt:hilt-lifecycle-viewmodel:1.3.0")

🌐 六、深度链接(Deep Link)

让外部链接(如网页、通知)直接打开 App 内页面。

步骤 1:在 composable 中注册 deep link

composable("profile",deepLinks=listOf(navDeepLink{uriPattern="myapp://profile"})){ProfileScreen()}

步骤 2:在 AndroidManifest.xml 中声明

<activityandroid:name=".MainActivity"><intent-filter><actionandroid:name="android.intent.action.VIEW"/><categoryandroid:name="android.intent.category.DEFAULT"/><categoryandroid:name="android.intent.category.BROWSABLE"/><dataandroid:scheme="myapp"android:host="profile"/></intent-filter></activity>

效果:点击 myapp://profile → 直接打开个人页!

🧪 七、测试导航

使用 createAndroidComposeRule + navigate() 模拟跳转。

@TestfuntestNavigateToProfile(){composeTestRule.setContent{MyApp()}// 点击按钮composeTestRule.onNodeWithText("去个人页").performClick()// 验证是否显示个人页内容composeTestRule.onNodeWithText("个人中心").assertExists()}

⚙️ 八、高级技巧

1. 嵌套路由(Nested Graph)

//TODO main是外层的路由路径,home是嵌套内开始展示UI的路由路径navigation(startDestination="home",route="main"){composable("home"){HomeScreen()}composable("settings"){SettingsScreen()}}composable("login"){LoginScreen()}

2. 自定义过渡动画

composable("profile",enterTransition={slideInHorizontally(initialOffsetX={it})},exitTransition={slideOutHorizontally(targetOffsetX={-it})}){...}
3. 拦截返回键
BackHandler(enabled=canExit){navController.popBackStack()}

✅ 十、最佳实践总结

  • 导航图集中管理:所有 composable 定义在一个地方(如 NavGraph.kt)
  • 参数尽量简单:用 ID 代替完整对象
  • 返回结果用共享状态:避免 hack 式回调
  • 深度链接提前规划:方便运营和分享
  • 动画适度使用:提升体验但别过度

🎯 结语

Jetpack Compose Navigation 不只是“页面跳转”,而是一套完整的页面生命周期管理方案。

它帮你处理了:

  • 返回栈
  • 状态保存(配合 rememberSaveable)
  • 深度链接
  • 动画过渡
  • 测试支持

只要掌握NavController+NavHost+composable三件套,你就能构建任意复杂的 App 导航结构!

版权声明: 本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若内容造成侵权/违法违规/事实不符,请联系邮箱:809451989@qq.com进行投诉反馈,一经查实,立即删除!
网站建设 2026/4/23 10:11:17

2025语音交互革命:Step-Audio-AQAA端到端技术如何重构人机对话体验

导语 【免费下载链接】Step-Audio-AQAA 项目地址: https://ai.gitcode.com/StepFun/Step-Audio-AQAA StepFun团队推出的Step-Audio-AQAA模型以全链路音频直连技术将响应延迟压缩至500ms以下&#xff0c;重新定义智能语音交互标准&#xff0c;为智能座舱、远程医疗等实时…

作者头像 李华
网站建设 2026/4/23 10:09:37

Vite 环境变量配置详解及最佳实践

在现代前端工程化开发中&#xff0c;环境变量&#xff08;Environment Variables&#xff09; 是管理不同部署环境&#xff08;开发、测试、预发、生产&#xff09;配置的核心机制。Vite 作为新一代构建工具&#xff0c;对环境变量提供了简洁而强大的支持。 本文将深入讲解 Vit…

作者头像 李华
网站建设 2026/4/23 10:10:10

7步构建企业级Ansible自动化运维平台

7步构建企业级Ansible自动化运维平台 【免费下载链接】ansible Ansible: 是一款基于 Python 开发的自动化运维工具&#xff0c;可以帮助开发者简化 IT 任务的部署和管理过程。适合运维工程师和开发者管理和自动化 IT 系统。 项目地址: https://gitcode.com/GitHub_Trending/a…

作者头像 李华
网站建设 2026/4/23 10:10:14

电脑小白必看:5分钟搞定万能网卡驱动安装

快速体验 打开 InsCode(快马)平台 https://www.inscode.net输入框内输入如下内容&#xff1a; 创建一个极简的万能网卡驱动安装向导&#xff0c;要求&#xff1a;1. 三步完成驱动安装&#xff08;检测-下载-安装&#xff09;2. 全中文图形界面 3. 自动判断32/64位系统 4. 内置…

作者头像 李华