如何监听 React Native 中的导航状态参数变化?

How to listen to navigation state params changes in React Native?

我正在使用 React Native 开发移动应用程序。在那里,我在导航到第二页时传递了一些东西。

所以,假设我的第一个屏幕有这样的东西。

export default function firstScreen(props) {
  return(
    //data is a custom object variable that may be changed.
    <Button onPress={() => props.navigation.navigate('SecondScreen', { data: data } )} /> 
  )
}

在我的第二个屏幕上,假设有这样的东西...

export default function secondScreen(props) {
  const { data } = props.navigation.state.params;

  useEffect(() => {
    console.log(data);
  }, [data])


  return(
    //content
  )
}

我的问题是,当 data 从第一个屏幕更改时,第二个屏幕不监听该更改并在控制台上打印 data 变量的内容。

所以,我想知道,如何在 React Native 中监听导航状态的变化。

您可以使用挂钩 'useNavigationState' 从第二个屏幕获取导航状态。

然后你又会遇到从第一个屏幕实际更新它的问题。 当您传递一个参数时,它是导航状态的一部分,并且您对对象所做的更改不会反映在那里。

更新导航状态的一种方法是分派一个动作,但这将是一个问题,因为您需要找到要更新的屏幕的键。 调度会是这样的

navigation.dispatch({ ...CommonActions.setParams({ 数据: {} }), 来源:route.key, });

由于您需要将对象更新到另一个屏幕,因此您应该考虑像 React 上下文这样的东西,或者如果您的应用程序中已经有 redux,则可以在需要时使用它。

最简单的方法是反应上下文,您可以从一个屏幕更新并从另一个屏幕接收。

使用上下文的版本如下所示。 这里使用了一个简单的堆栈导航器,上下文从主屏幕更新,值可以从设置屏幕读取。您可以使用相同的方式更新数据变量并从另一个屏幕获取数据。这里我们不使用导航状态,但我们为变量维护我们自己的上下文。

const Stack = createStackNavigator();
const CountContext = React.createContext({ count: 1, setCount: () => {} });

function HomeScreen({ navigation, route }) {
  const { count, setCount } = React.useContext(CountContext);
  React.useEffect(() => {
    const interval = setInterval(() => {
      setCount(count => count + 1);
    }, 1000);

    return () => {
      clearInterval(interval);
    };
  }, []);

  return (
    <View>
      <Text>Test{count}</Text>
      <Button
        title="Go to settings"
        onPress={() => navigation.navigate('Settings')}
      />
    </View>
  );
}

function SettingsScreen({ navigation, route }) {
  const { count, setCount } = React.useContext(CountContext);
  return (
    <View>
      <Text>Settings! {count}</Text>
      <Button title="Go back" onPress={() => navigation.goBack()} />
    </View>
  );
}

export default function App() {
  const [count, setCount] = React.useState(0);
  const value = { count, setCount };

  return (
    <CountContext.Provider value={value}>
      <NavigationContainer>
        <Stack.Navigator>
          <Stack.Screen name="Home" component={HomeScreen} />
          <Stack.Screen name="Settings" component={SettingsScreen} />
        </Stack.Navigator>
      </NavigationContainer>
    </CountContext.Provider>
  );
}

你可以看看这个小吃 https://snack.expo.io/@guruparan/stateparamschange

以下是我在 React Navigation V5 中使用 hooks 解决这个问题的方法:

import { useRoute } from '@react-navigation/native';
const route = useRoute();
useEffect(() => { //This will run whenever params change
     const {params = {}} = route;
    //your logic here
}, [route]);