根据访问路径设置Material-UI选项卡

时间:2016-09-17 05:52:49

标签: reactjs react-router react-redux material-ui

在我的新react-redux应用程序中(我是新手做出反应),我正在使用Material-UI并在我的网络应用程序中添加了材料-ui标签。选项卡用于在使用以下代码完成选择时更改URL。

function handleActive(tab) {
    browserHistory.push(tab.props['data-route']);
}

当我手动访问路径而不是单击选项卡时,我希望我的选项卡显示选定的选项卡指示符。我现在无法弄明白。任何人都可以建议我通过react或redux来做到这一点吗?让我知道,如果我不清楚我的问题。

更新

我的组件render()中的代码。组件中没有其他内容。

render() {
    function handleActive(tab) {
        browserHistory.push(tab.props['data-route']);
    }

    return (
        <Paper>
            <Toolbar className="navbar">
                <ToolbarGroup>
                    <Link to="/" style={{ textDecoration: 'none' }}>
                        <ToolbarTitle style={this.styles.title} text="Test App" />
                    </Link>
                </ToolbarGroup>
                <ToolbarGroup className="tab-container">
                    <Tabs className="tabs">
                        <Tab data-route="/" onActive={handleActive} className="tab" label="Route A" />
                        <Tab data-route="/routeB" onActive={handleActive} className="tab" label="Route B" />
                        <Tab data-route="/routeC" onActive={handleActive} className="tab" label="Route C" />
                        <Tab data-route="/routeD" onActive={handleActive} className="tab" label="Route D" />
                    </Tabs>
                </ToolbarGroup>
            </Toolbar>
        </Paper>
    );
}

3 个答案:

答案 0 :(得分:5)

我怀疑解析网址是个好主意。也许最好从onEnter <Route>道具中的路由器调度操作控制选项卡索引?

假设您有2条路线:

<Route path='sign_in' component={AuthenticationWrapper} onEnter={() => { store.dispatch(changeTab(0)) }} />
<Route path='sign_up' component={AuthenticationWrapper} onEnter={() => { store.dispatch(changeTab(1)) }} />

行动创作者:

changeTab = (index) => {
  return { type: AUTH_TAB_CHANGE, index }
}

减速机:

authTab = (state = 0, action = {}) => {
  switch (action.type) {
    case AUTH_TAB_CHANGE:
      return action.index
    default:
      return state
  }
}

组件:

class AuthenticationWrapper extends Component {
  constructor(props) {
    super(props)

    this.handleSignIn = this.handleActive.bind(this, '/sign_in')
    this.handleSignUp = this.handleActive.bind(this, '/sign_up')
  }

  handleActive(url) {
    browserHistory.push(url)
  }

  render() {
    const { authTab, changeTab } = this.props

    return (
      <Tabs index={authTab} onChange={changeTab}>
        <Tab label='Sign In' onActive={this.handleSignIn}>
          <SignInForm />
        </Tab>
        <Tab label='Sign Up' onActive={this.handleSignUp}>
          <SignUpForm />
        </Tab>
      </Tabs>
    )
  }
}

const mapStateToProps = ({ authTab }) => {
  return {
    authTab
  }
}

export default connect(mapStateToProps, {
  changeTab,
})(AuthenticationWrapper)

这种方法既适用于访问不同的网址,也可以通过点击它们来更改标签,而无需刷新页面。

答案 1 :(得分:3)

虽然很少有方法可以做到,但由于您使用的是React Component Class, 您可以添加componentWillMount

componentWillMount() {

  let urlPath = window.location.pathname;
  let currentTab = urlPath.split('/').pop();
  // you can add more validations here
  this.setState({ activeTab: currentTab || 'default' });

}

render方法中,将<Tabs className="tabs">更改为

<Tabs
  className="tabs"
  value={this.state.activeTab}
  >
    <Tab value="default" data-route="/" onActive={handleActive} className="tab" label="Route A" />
    <Tab value="routeC" data-route="/routeC" onActive={handleActive} className="tab" label="Route C" />
    ...

我不知道这是否是我们应该为value设置Tab的方式..但是要玩弄它。

它应该有用。

我在这里使用了setState而不是redux,因为只要这是唯一需要知道哪个标签当前处于活动状态的组件,就没有任何错误。 ,您可以轻松地将其更改为使用redux

答案 2 :(得分:1)

要实现这一目标,您需要做一些事情以确保您可以在标签所在的页面中捕获网址。这是您应该做的:

  • 渲染最高分量时,请确保在索引html的div id中呈现<Router history={browserHistory} routes={routes} />。看来你正在这样做,因为你有browserHistory工作。
  • 在您的路由中,请确保您具有嵌套路由,以便在父组件中传递this.props.children,以便在URL中反映的子项中包含/ path / to / comp。同样,你可能也有这个设置。
  • 现在,您需要按照此处http://www.material-ui.com/#/components/tabs中的说明为您的标签和标签组件添加值。值将指定哪个Tab处于活动状态,具体取决于为Tabs选择的那个<Tabs className="tabs" value={this is where your this.props.params.name_of_changing_route}>,或者如果你有react-router 2.4.0,你可以使用withRouter包装你的组件,然后你就可以访问params,location和route