如何使用 React Navigation 5.x 在不同的选项卡中重置堆栈

Posted

技术标签:

【中文标题】如何使用 React Navigation 5.x 在不同的选项卡中重置堆栈【英文标题】:How to reset a Stack in a different Tab using React Navigation 5.x 【发布时间】:2020-07-20 04:31:57 【问题描述】:

我的应用程序有一个 TabNavigator,每个选项卡中都有一个 StackNavigator。通过单击不同的选项卡在它们之间导航时,我不会重置堆栈,因此当您更改选项卡时,堆栈包含以前的状态。但是,偶尔从一个选项卡中的屏幕中,我想导航到不同选项卡中的特定屏幕,在这种情况下,我想重置目标选项卡中的堆栈。

TabNavigator
    Tab1 
      StackNavigator
         - ScreenA
         - ScreenB
    Tab2
      StackNavigator
         - Screen1
         - Screen2

我希望能够在 Screen2 上放置一个按钮,以重置 Tab1 上的堆栈。

我想知道此处文档中提到的“目标”参数是否有帮助,但没有关于如何使用它的示例。 https://reactnavigation.org/docs/navigation-actions/

(我在这里搜索过,但为 4.x 建议的答案似乎不再适用)。 谢谢!

【问题讨论】:

还没有回答,嘿?阅读使用此reactnavigation.org/docs/navigation-actions/#reset 可能是正确的,但我找不到解决方案 这里有同样的问题。你找到解决办法了吗? @VictorMolina 我已经在下面发布了一个答案 - 现在已经有一段时间了,但这大致是我采取的方法 【参考方案1】:

谢谢@anorakgirl。它完美无缺! 我想添加一些人们可能想知道的其他案例。因为应用程序通常包含 4-5 个标签。

下面的代码用于重置多个标签。

TabNavigator
    Tab1: 'tab1_name' 
      StackNavigator
         - ScreenA
         - ScreenB

    Tab2: 'tabs_name'
      StackNavigator
         - ScreenC
         - ScreenD

    Tab3: 'tab3_name'
      StackNavigator
         - ScreenE
         - ScreenF
navigation.dispatch(
  CommonActions.reset(
    routes: [
      
        name: 'tab1_name',
        state: 
          routes: [
             name: 'ScreenA' ,
             name: 'ScreenB' ,
          ]
        
      ,
      
        name: 'tab2_name',
        state: 
          routes: [
             name: 'ScreenC' ,
          ]
        
      ,
      
        name: 'tab3_name',
        state: 
          routes: [
             name: 'ScreenE' ,
             name: 'ScreenF' ,
          ]
        
      ,
    ]
  )
)

使用此代码,您看到的第一页是tab1_name 选项卡的ScreenB 屏幕。

所以,如果你想在运行调度函数后首先看到tab3_name标签的ScreenF屏幕,代码应该是这样的:

navigation.dispatch(
  CommonActions.reset(
    routes: [
      
        name: 'tab3_name',
        state: 
          routes: [
             name: 'ScreenE' ,
             name: 'ScreenF' ,
          ]
        
      ,
      
        name: 'tab1_name',
        state: 
          routes: [
             name: 'ScreenA' ,
             name: 'ScreenB' ,
          ]
        
      ,
      
        name: 'tab2_name',
        state: 
          routes: [
             name: 'ScreenC' ,
          ]
        
      ,
    ]
  )
)

顺便说一句,当你写下标签的stateroutes 时,它应该遵循页面堆栈的顺序。这样它就可以按您的预期工作。

navigation.dispatch(
  CommonActions.reset(
    routes: [
      
        name: 'tab3_name',
        state: 
          routes: [
            //  name: 'ScreenE' ,   // removed
             name: 'ScreenF' ,
          ]
        
      ,

如果你省略上面的第一个堆栈页面,ScreenE 是不可访问的,而在运行调度函数后只能访问 ScreenF

希望这对你有用。

【讨论】:

【参考方案2】:

最后我能够使用reset 操作来执行此操作。我为要重置的选项卡发送了嵌套状态:

navigation.dispatch(
  CommonActions.reset(
    routes: [
      
        name: 'tab-route-name',
        state: 
          routes: [
             name: 'stack-route-1' ,
             name: 'stack-route-2' ,
             name: 'stack-route-3' 
          ]
        
      
    ]
  )
)

它似乎很聪明,只要选项卡导航器是当前路由的父级,它就会找到并重置它。

【讨论】:

以上是关于如何使用 React Navigation 5.x 在不同的选项卡中重置堆栈的主要内容,如果未能解决你的问题,请参考以下文章

React Navigation 路由导航库升级 5.x

如何在打字稿中使用 react-navigation 的 withNavigation?

使用 react-navigation 重构 - 使用分支时如何提升静态导航标题?

使用`react-navigation`导航时如何触发render()方法?

如何使用 react-navigation 推送新场景?

如何在 react-native 中结合使用 Drawer Navigation 和 Stack Navigator?