如何在 Compose NavGraph 内的两个或多个 Jetpack 可组合项之间共享视图模型?

2024-02-19

考虑这个例子。

对于身份验证,我们将使用 2 个屏幕 - 一个屏幕用于输入电话号码,另一个屏幕用于输入 OTP。

这两个屏幕都是在 Jetpack Compose 中制作的,对于 NavGraph,我们使用组合导航。

另外我必须提到 DI 是由 Koin 处理的。

val navController = rememberNavController()

NavHost(navController) {
    navigation(
        startDestination = "phone_number_screen",
        route = "auth"
    ) {
        composable(route = "phone_number_screen") {
            // Get's a new instance of AuthViewModel
            PhoneNumberScreen(viewModel = getViewModel<AuthViewModel>())
        }

        composable(route = "otp_screen") {
            // Get's a new instance of AuthViewModel
            OTPScreen(viewModel = getViewModel<AuthViewModel>())
        }
    }
}

那么,我们如何在 Jetpack 组合 NavGraph 中的两个或多个可组合项之间共享相同的视图模型呢?


你可以通过你的顶部viewModelStoreOwner到每个目的地

  1. 直接传递到.viewModel() call, composable("first")在我的例子中
  2. 压倒性的LocalViewModelStoreOwner对于整个内容,所以里面的每个可组合项CompositionLocalProvider将有权访问相同的视图模型,composable("second")在我的例子中
val viewModelStoreOwner = checkNotNull(LocalViewModelStoreOwner.current) {
    "No ViewModelStoreOwner was provided via LocalViewModelStoreOwner"
}
val navController = rememberNavController()
NavHost(navController = navController, startDestination = "first") {
    composable("first") {
        val model = viewModel<SharedModel>(viewModelStoreOwner = viewModelStoreOwner)
    }
    composable("second") {
        CompositionLocalProvider(
            LocalViewModelStoreOwner provides viewModelStoreOwner
        ) {
            SecondScreen()
        }
    }
}

在第二种情况下,您可以在组合树的任何级别获取模型,该模型位于CompositionLocalProvider:

@Composable
fun SecondScreen() {
    val model = viewModel<SharedModel>()
    SomeView()
}

@Composable
fun SomeView() {
    val model = viewModel<SharedModel>()
}
本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)

如何在 Compose NavGraph 内的两个或多个 Jetpack 可组合项之间共享视图模型? 的相关文章

  • Kotlin 反射不可用

    我试图从第一个例子中学习高阶函数video https www youtube com watch v a7QpoMj2uIA 这是我的代码和输出 Code fun lowercase value String value toLowerC
  • Kotlin:如何修改对中的值? [复制]

    这个问题在这里已经有答案了 为什么我无法更改该对中的值 var p Pair
  • 更改可组合项的布局方向

    我想将特定可组合项的方向设置为RTL Composable fun ViewToBeChanged Row Image Column Text Title Text Subtitle 是否可以 喷气背包组成布局文档 https develo
  • Jetpack Compose Navigation:直接导航到非 startDestination 的嵌套图中的路由

    我正在开发 Jetpack Compose Navigation 演示 并且有一个嵌套导航图 其中包含两个不同的嵌套路线以及每个嵌套路线的屏幕 登录图 主图 登录图具有三种路线 用于显示三个不同的屏幕 路由 登录 以显示登录屏幕 路由 re
  • Kotlin 等价于三元运算符 [重复]

    这个问题在这里已经有答案了 因此 在 java 中 我们有三元运算符 它有时对于简化 if else 内联计算的某些值很有用 例如 myAdapter setAdapterItems textToSearch length 0 noteLi
  • Android 导航 DeepLinks - 如何区分使用导航操作进行导航与深层链接

    我有导航操作和深层链接 根据您导航的位置 将您带到某个片段 我想确定是使用了深层链接还是仅使用了导航操作 这正是KEY DEEP LINK INTENT https developer android com reference andro
  • 如何在调用主构造函数之前运行代码?

    我正在编写一个包含两个不可变值的类 它们在主构造函数中设置 我想添加一个辅助构造函数 它接受一个字符串并解析它以获取这两个值 但是 我无法找到在 Kotlin 中实现此功能的方法 因为辅助构造函数在解析字符串之前立即调用主构造函数 在jav
  • 如何在 Kotlin 中将 List 转换为 Map?

    例如 我有一个字符串列表 例如 val list listOf a b c d 我想将其转换为地图 其中字符串是键 我知道我应该使用 toMap 函数 但我不知道如何实现 也没有看到任何例子 你有两个选择 第一个也是性能最高的是使用asso
  • ArgumentMatchers.any 不得为 null

    我正在尝试测试ViewModel以确保实时数据得到正确更新 然而使用时ArgumentMatchers any 它失败了IllegalStateException saying ArgumentMatchers any mViewModel
  • Spring webflux bean 验证不起作用

    我正在尝试在 Webflux 中使用 bean 验证 这是我到目前为止所拥有的 PostMapping contact fun create RequestBody Valid contact Mono
  • 如何将字节数组转换为图像 [kotlin]

    我想将字节数组转换为图像并在图像视图中显示它 但不知道该怎么做 有人可以指导我吗 我使用这个函数将位图转换为字节数组 private fun BitmapToByteArray ByteArray val stream ByteArrayO
  • 如何在 Jetpack compose 中制作 FlipCard 动画

    我有一个现有的应用程序 我在其中使用 XML 中的 Objectanimator 实现了 FlipCard 动画 如下所示 如果我点击一张卡片 它会水平翻转 但现在我想将其迁移到 jetpack compose 那么jetpack comp
  • 如何在 Jetpack Compose 中集成自动填充

    我想在我的应用程序中提供一些自动填充功能 电子邮件和密码 该功能完全使用 Jetpack compose 编写 我碰到这篇博文 https bryanherbst com 2021 04 13 compose autofill and 这个
  • 在粘贴时将 java 转换为 kotlin

    所以我检查了 下次不再显示此对话框 但事实证明它永远不会再次转换代码 我应该在哪里再次删除复选标记 以便在粘贴时可以返回将 java 代码转换为 kotlin 提前致谢 https developer android com kotlin
  • 如何在 Compose Image 中显示位图

    我有一个返回位图 其中 包含 QR 码 的函数 并且我想在Image 可组合函数 但我没有找到任何方法将位图转换为ImageBitmap或者只是显示该位图 基于这篇博文 https proandroiddev com display map
  • 错误:类 kotlin.reflect.jvm.internal.FunctionCaller$FieldSetter

    我已尝试一切方法来消除此错误 但它不断出现 Class kotlin reflect jvm internal FunctionCaller FieldSetter can not access a member of class com
  • 为什么我无法使用 HttpUrlConnection 上传第一个文件块?

    在我的项目中 我应该从一台服务器逐块下载文件 并将每个块立即上传到另一台服务器 我有一个应该下载的文件的 URL 我们就这样称呼它吧downloadUrl 因此 这就是我逐块下载文件的方式 val chunkSize 1024 1024 B
  • Jetpack Compose 中的图像裁剪器?

    我到处搜索 但没有找到有关在 Jetpack Compose 中裁剪图像的文档 如何在 Jetpack Compose 中裁剪图像 实际上 您可以使用那些较旧的 Android 库 没有问题 我用的是这个 https github com
  • 在 Android 中启用展开布局时,如何默认使用折叠布局显示自定义通知

    当用户折叠或展开通知时 我想通过支持小型和大型布局来显示我的自定义通知 如上面的屏幕截图所示 但结果它默认显示扩展通知 我想默认将其显示为折叠通知 并且仅在用户展开时显示展开通知 请检查我的代码如下 private fun initCust
  • 如何在 Jetpack Compose 中提供相对大小

    我有一个框布局 我想相对于父框的大小来布局子视图 这可以在 SwiftUI 中使用 Geometry Reader 来实现 如何在 Jetpack Compose 中实现类似的功能 您可以使用BoxWithConstraints代替Box

随机推荐