在动画场景之外控制StackNavigator

时间:2017-05-10 19:52:17

标签: ios reactjs react-native react-navigation

编辑:我理解我的问题和解决方案所以我正在改写我的问题,然后回答。

普通StackNavigator和带导航的屏幕如下所示:

class ExampleScreen extends React.Component {
  render() {
    const { navigate, state } = this.props.navigation.navigate;
    const exampleTitle = state.params.title;

    return (
      <View>
        <Text>{exampleTitle}</Text>
        <Button
          title="Click"
          onPress={() => {
            navigate('Example', { exampleTitle: 'foo' })
          }}
        />
      </View>
    );
  }
}

const ExampleNavigator = StackNavigator({
  Example: { screen: ExampleScreen }
}, {
  initialRouteName: 'Example',
  initialRouteParams: { exampleTitle: 'bar' }
});

AppRegistry.registerComponent('Example', () => ExampleNavigator);

我想访问navigation之外的ExampleScreen#render对象,以便它不属于CardStack动画的一部分。

2 个答案:

答案 0 :(得分:1)

我通过添加另一个屏幕来渲染ExampleNavigator来解决我的问题 在ref上设置ExampleNavigator属性。 navigation对象和。{ 路径参数需要稍微不同地访问,但我将在整个代码中的注释中解释。

class ExampleScreen extends React.Component {
  render() {
    const { state } = this.props.navigation.navigate;
    const exampleTitle = state.params.title;

    return (
      <View>
        <Text>{exampleTitle}</Text>
      </View>
    );
  }
}

const ExampleNavigator = StackNavigator({
  Example: { screen: ExampleScreen }
}, {
  initialRouteName: 'Example',
  initialRouteParams: { exampleTitle: 'bar' }
});

// my solution
class RootScreen extends React.Component {
  constructor(props) {
    super(props);
    // makes sure _onPress has the correct context when clicked
    this._onPress = this._onPress.bind(this);
  }
  render() {
    // flex: 1 is set to make the navigator visible. you wont see the navigator
    // without this.
    return (
      <View style={{flex: 1}}>
        <ExampleNavigator ref='nav' />
        <Button title='Click' onPress={this._onPress} />
      </View>
    );
  }

  _onPress() {
    // read navigate and state from _navigation
    const { navigate, state } = this.refs.nav._navigation;
    const { routes, index } = state;
    // read scene params through the route of the index passed in state
    const params = routes[index].params;
    const exampleTitle = params.exampleTitle + ' clicked';

    // use the navigate method as your normally would
    navigate('Example', {exampleTitle});
  }
}

AppRegistry.registerComponent('Example', () => RootScreen);

答案 1 :(得分:0)

我相信我想做的事情与此非常相似,如果不相同的话。我不明白为什么这不常见(从组件中提取行为并允许更高级别的组件在一组组件中定义行为,并在这种情况下定义所有导航行为),以便不支持必须使用refs。

理想的解决方案似乎是:

class ExampleScreen extends React.Component {
  render() {
    const { navigate, state } = this.props.navigation.navigate;
    const exampleTitle = state.params.title;

    return (
      <View>
        <Text>{exampleTitle}</Text>
        <Button
          title="Click"
          onPress=state.params.onPress
        />
      </View>
    );
  }
}

const ExampleNavigator = StackNavigator({
  Example: { screen: ExampleScreen }
}, {
  initialRouteName: 'Example',
  initialRouteParams: {
    exampleTitle: 'bar',
    onPress: () => {XXX.navigate('Example', { exampleTitle: 'foo' })}
  }
});

AppRegistry.registerComponent('Example', () => ExampleNavigator);

在StackNavigator initialRouteParams中以某种方式提供导航。

我是否在这里错过了一些简单的解决方案,似乎是一种常见的设计模式?