2016-02-28 2 views
49

У меня возникли проблемы с дизайном, используя реактивный маршрутизатор и реакцию-бутстрап. ниже - код кодаReact-Bootstrap ссылка ссылка в navitem

import { Route, RouteHandler, Link } from 'react-router'; 
import AuthService from '../services/AuthService' 
import { Button, Nav, Navbar, NavDropdown, MenuItem, NavItem } from 'react-bootstrap'; 

    <Nav pullRight> 
     <NavItem eventKey={1}> 
     <Link to="home">Home</Link> 
     </NavItem> 
     <NavItem eventKey={2}> 
     <Link to="book">Book Inv</Link> 
     </NavItem> 
     <NavDropdown eventKey={3} title="Authorization" id="basic-nav-dropdown"> 
     <MenuItem eventKey="3.1"> 
      <a href="" onClick={this.logout}>Logout</a> 
     </MenuItem>   
     </NavDropdown> 
    </Nav> 

Это то, на что похоже, когда оно оказывает.

enter image description here

Я знаю, что <Link></Link> является причиной этого, но я не знаю, почему? Я хотел бы, чтобы это было в строке.

ответ

4

Вы не должны ставить якорь внутри NavItem. Делая это, вы увидите предупреждение в консоли:

Warning: validateDOMNesting(...): <a> cannot appear as a descendant of <a>. See Header > NavItem > SafeAnchor > a > ... > Link > a.

Это потому, что когда NavItem оказывается якорь (прямой потомок NavItem) уже есть.

Из-за предупреждения выше, реакция будет вынуждена рассматривать два якоря в качестве родственного брата, что вызвало проблему стиля.

+2

Мне пришлось закончить использование [linkcontainer] (https://www.npmjs.com/package/react-router-bootstrap). –

+2

Не могли бы вы привести пример? –

+2

Я единственный, чья проблема решена не принятым ответом, а вторым ответом. –

186

Использование LinkContainer от react-router-bootstrap - это путь. Следующий код должен работать.

import { Route, RouteHandler, Link } from 'react-router'; 
import AuthService from '../services/AuthService' 
import { Button, Nav, Navbar, NavDropdown, MenuItem, NavItem } from 'react-bootstrap'; 
import { LinkContainer } from 'react-router-bootstrap'; 

/// In the render() method 
<Nav pullRight> 
    <LinkContainer to="/home"> 
    <NavItem eventKey={1}>Home</NavItem> 
    </LinkContainer> 
    <LinkContainer to="/book"> 
    <NavItem eventKey={2}>Book Inv</NavItem> 
    </LinkContainer> 
    <NavDropdown eventKey={3} title="Authorization" id="basic-nav-dropdown"> 
    <LinkContainer to="/logout"> 
     <MenuItem eventKey={3.1}>Logout</MenuItem>  
    </LinkContainer>  
    </NavDropdown> 
</Nav> 

Это в основном примечание к будущему «я», когда речь идет о проблеме в этой проблеме. Я надеюсь, что кто-то другой может воспользоваться ответом.

+22

+1: [официальная рекомендация от реактивного бутстрапа и реактивного маршрутизатора] (https://github.com/reactjs/react-router/issues/83#issuecomment-214794477) заключается в использовании [response-router- самонастройки] (https://github.com/react-bootstrap/react-router-bootstrap). –

+3

Как насчет переключения activeClassName? –

+0

Если вы не можете сделать эту работу, просто убедитесь, что ваш путь включен в React Router. –

5

Вот решение для использования с реагировать-маршрутизатор 4:

import * as React from 'react'; 

import { MenuItem as OriginalMenuItem, NavItem as OriginalNavItem } from 'react-bootstrap'; 

export const MenuItem = ({ href, ...props }, { router }) => (
    <OriginalMenuItem onClick={e => {e.preventDefault();router.transitionTo(href)}} href={href} {...props}/> 
); 

MenuItem.contextTypes = { 
    router: React.PropTypes.any 
}; 

export const NavItem = ({ href, ...props }, { router }) => (
    <OriginalNavItem onClick={e => {e.preventDefault();router.transitionTo(href)}} href={href} {...props}/> 
); 

NavItem.contextTypes = { 
    router: React.PropTypes.any 
}; 
+0

Вместо использования 'router.transitionTo (href)' use 'router.history.push (href)' – user3129262

2

Вы можете использовать history, просто убедитесь, что для создания компонента with router:

в App.js:

// other imports 
import {withRouter} from 'react-router'; 

const NavigationWithRouter = withRouter(Navigation); 

//in render() 
    <NavigationWithRouter /> 

в Navigation.js:

//same code as you used before, just make an onClick event for the NavItems instead of using Link 

<Nav pullRight> 
    <NavItem eventKey={1} onClick={ e => this.props.history.push("/home") } > 
    Home 
    </NavItem> 
    <NavItem eventKey={2} onClick={ e => this.props.history.push("/book") } > 
    Book Inv 
    </NavItem> 
</Nav> 
1

IndexLinkContainer - лучший вариант, чем LinkContainer, если вы хотите, чтобы внутри NavItem отображался , какой из них активен на основе текущего выбора. Ни один ручной обработчик выбора не требуется

import { IndexLinkContainer } from 'react-router-bootstrap'; 
.... 

//Inside render 
<Nav bsStyle="tabs" > 
    <IndexLinkContainer to={`${this.props.match.url}`}> 
    <NavItem >Tab 1</NavItem> 
    </IndexLinkContainer> 
    <IndexLinkContainer to={`${this.props.match.url}/tab-2`}> 
    <NavItem >Tab 2</NavItem> 
    </IndexLinkContainer> 
    <IndexLinkContainer to={`${this.props.match.url}/tab-3`}> 
    <NavItem >Tab 3</NavItem> 
    </IndexLinkContainer> 
</Nav> 
+0

Я не использую вкладки, но хочу, чтобы ссылка в моей навигационной панели была выделена как активная. Я попытался использовать IndexLinkContainer, и он не работает, как вы указали. Если я перейду непосредственно к маршруту, он выделит правильный, но не, если я просто нажму ссылку. –

+0

это спасло мой день! Спасибо! –

+0

btw just curios, как вы нашли '' 'IndexLinkContainer'''? не мог найти его нигде в документах ... –

1

Вы попробуйте реагировать-самозагрузки-х componentClass?

import { Link } from 'react-router'; 
// ... 
<Nav pullRight> 
    <NavItem componentClass={Link} href="/" to="/">Home</NavItem> 
    <NavItem componentClass={Link} href="/book" to="/book">Book Inv</NavItem> 
</Nav> 
+0

Это хорошо работает! Нет проблем с дизайном и намного проще, чем другие ответы, требующие переопределения, вы также можете переопределить HoC, чтобы избежать повторения href/to. –