Thread
#compose
    a

    allan.conda

    1 year ago
    My team raised me a question regarding compose navigation and deeplinks which I was not able to answer. Let’s say we have 2 independent feature modules, A and B. a screen from A can navigate to a screen from B. I call the nav graph of B from the top-level module so it has access to the B’s Screen composables, without having A depend directly on B. We would like a deep link navigation to B with a simulated backstack as if B was opened from a screen in A. Is this possible with this kind of setup?
    While writing this question I had the idea of doing two navigation calls something like
    navController.navigate("screen_in_A")
    navController.navigate("screen_in_B")
    Will this work? Edit: 🤦 forgot we’re talking deeplinks here, so this idea is stupid
    i

    Ian Lake

    1 year ago
    The synthetic back stack you get when deep linking is built from the start destination(s) of your graphs, as per the docs: https://developer.android.com/guide/navigation/navigation-deep-link#implicit
    So if A is the start destination of your graph, it will be on the back stack
    a

    allan.conda

    1 year ago
    Yes, it’s easy when working in a single module since I could do
    navigation("main") {
      composable("top") { TopScreen() }
    
      navigation("A") {
        composable("screen_in_a") { ScreenInA() }
    
        navigation("B") {
           composable("screen_in_b) {
              ScreenInB()
           }
        }
      }
    }
    If I understand this correctly.
    B got complex so we separated it out on its own feature module. Now the graph looks like
    navigation("main") {
      composable("top") { TopScreen() }
    
      navigationA() // defined in feature_a module
      
      navigationB() // defined in feature_b module
    }
    so from within A we can still call
    navController.navigate("screen_in_b")
    without coupling module A with B
    Maybe I could hoist the actual composable like this…
    navigation("main") {
      navigationA(
          screenInB = {
              ActualScreenInB()
          }
      )
    }
    
    // feature a
    fun NavGraphBuilder.navigationA(
      screenInB: () -> Unit,
    ) {
      navigation("A") {
         composable("screen_in_a") { ScreenInA()
         navigation("B") {
           screenInB()
         }
      }
    }
    i

    Ian Lake

    1 year ago
    Why wouldn't your
    navigationA()
    just take a
    embeddedGraph: NavGraphBuilder.() -> Unit
    ? Then you could do
    navigationA(navigationB())
    If
    navigation("B")
    really is a subgraph of
    navigation("A")
    , then your graph structure should represent that
    a

    allan.conda

    1 year ago
    Wow…
    I simply didn’t think of that 😓
    then your graph structure should represent that
    Yeah! I was thinking of this too, having two nav graphs at the same level doesn’t seem right, I use that kind of pattern more for global/shared navigations. I just never thought I could just pass the graph directly… Thanks Ian!