react-leaflet Popup 包含一个 react-route Link

react-leaflet's Popup contains a react-route's Link

我的应用程序使用 react-leaflet 生成带有标记和弹出窗口的地图。我需要通过 react-router.

<Link/> 组件从 Popup 给另一个页面一个 link
/* app.js */
import React from 'react';
import { render } from 'react-dom';
import { Router, Route, browserHistory } from 'react-router';
import App from './components/App';
import Map from './components/Map';

const Root = () =>
  <Router history={browserHistory}>
    <Route path='/' component={App}>
      <Route path='map' component={Map} />
    </Route>
  <Router>

render(<Root />, document.getElementById('root'));


/* components/Map/index.js */
import React from 'react';
import { Router, Route, browserHistory } from 'react-router';
import App from './components/App';
import Map from './components/Map';

const Map = () =>
  <Map>
    <Marker position={[10, 10]}>
      <Popup>
        <div>
          <Link to="/">Main page</Link>
        </div>
      </Popup>
    </Marker>
  <Map>

export default Map;

但是通过 link 我得到一个错误:

<Link>s rendered outside of a router context cannot navigate.

因为打开的Popup内容从router context中移除,放在了下面

我想,我可以将 router.push() 放入 Popup。但也许可以使用 <Link/>?

谢谢!

所以,我创建了 ContextProvider component-creator:

import React, { PureComponent, PropTypes } from 'react';

export default function createContextProvider(context) {
  class ContextProvider extends PureComponent {
    static propTypes = {
      children: PropTypes.node,
    };
    static childContextTypes = {};

    getChildContext() {
      return context;
    }

    render() {
      return this.props.children;
    }
  }

  Object.keys(context).forEach((key) => {
    ContextProvider.childContextTypes[key] = PropTypes.any.isRequired;
  });

  return ContextProvider;
}

并将其用于创建地图标记:

import React, { PureComponent, PropTypes } from 'react';
import { Marker, Popup } from 'react-leaflet';
import createContextProvider from '../ContextProvider';

export default class SomeComponent extends PureComponent {
  static contextTypes = {
    router: PropTypes.object,
    // Place here any other parameters from context
  };

  render() {
    const { position, children, ...props } = this.props;
    const ContextProvider = createContextProvider(this.context);

    return (
      <Marker {...props} position={position}>
        <Popup>
          <ContextProvider>
            <div>
              {children}
            </div>
          </ContextProvider>
        </Popup>
      </Marker>
    );
  }
}