リテレットマップを持つ再利用可能なMarkerCluster
コンポーネントをコンテキストinitから作成してから、ネストされたマップコンポーネントの更新を提供したいと考えています。 react-router
から動的アクションを実行するには、MyMap
コンポーネントに直接埋め込む必要はありませんが、MarkerCluster
にshouldComponentUpdate === false
がある場合、ネストされたマーカーは更新されません。この問題はissueに関連する可能性があることがわかりましたが、私の場合はこれを回避する方法が見つかりませんでした。私はまだshouldComponentUpdateをtrueに設定するよりも優れたソリューションがあると考えています。私の2つの例の間の行動の違いを説明できますか?それとも、再利用可能なMarkerCluster
コンポーネントを、リアクションの方法でコンテキストなしで構築する方がよいでしょうか?埋め込みコンポーネントの親からコンテキストを一度適用し、子を更新する方法は?
デモ:
const React = window.React;
const { Map, TileLayer, Marker, MapLayer, PropTypes } = window.ReactLeaflet;
const { markerClusterGroup } = window.L;
class MarkerCluster extends MapLayer {
static childContextTypes = {
layerContainer: PropTypes.layerContainer
};
getChildContext() {
return {
layerContainer: this.leafletElement
}
}
componentWillMount() {
super.componentWillMount()
this.leafletElement = markerClusterGroup()
}
shouldComponentUpdate() {
return false
}
render() {
console.log("update markers cluster")
return <div style={{display: 'none'}}>{this.props.children}</div>
}
}
class MapMarkers extends React.Component {
constructor() {
super()
\t const initialState = [
\t {position: [51.5, -0.1]},
\t {position: [51.51, -0.1]},
\t {position: [51.49, -0.05]},
\t ]
this.state = {markers: initialState};
}
componentDidMount() {
setInterval(this.addMarker.bind(this), 3000);
}
addMarker() {
const lat = (Math.random() * (51.49 - 51.51) + 51.51);
const lng = (Math.random() * (0.05 - 0.1) - 0.1);
const marker = {position: [lat, lng]};
this.setState({markers: this.state.markers.concat([marker])});
}
render() {
console.log("update markers")
const markers = this.state.markers.map((item, key) =>
<Marker position={item.position} key={key} />
);
return <MarkerCluster>{markers}</MarkerCluster>;
}
}
class MyMap extends React.Component {
render() {
return (
<Map center={[51.50, -0.1]} zoom={13}>
<TileLayer
attribution='© <a href="http://osm.org/copyright">OpenStreetMap</a> contributors'
url='http://{s}.tile.osm.org/{z}/{x}/{y}.png'
/>
{this.props.children}
</Map>
)
}
}
class MainLayout extends React.Component {
render() {
\t return (
<MyMap>
<MapMarkers />
</MyMap>
)
}
}
window.ReactDOM.render(<MainLayout />, document.getElementById('container'));
.leaflet-container {
height: 400px;
width: 100%;
}
<link href="https://rawgit.com/Leaflet/Leaflet.markercluster/leaflet-0.7/dist/MarkerCluster.Default.css" rel="stylesheet" />
<link href="https://cdnjs.cloudflare.com/ajax/libs/leaflet/0.7.7/leaflet.css" rel="stylesheet" />
<script src="https://cdnjs.cloudflare.com/ajax/libs/leaflet/0.7.7/leaflet.js"></script>
<script src="https://rawgit.com/Leaflet/Leaflet.markercluster/leaflet-0.7/dist/leaflet.markercluster.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/react/15.1.0/react.min.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/react/15.1.0/react-dom.min.js"></script>
<script src="https://npmcdn.com/[email protected]/dist/react-leaflet.js"></script>
<div id="container"></div>
以下の例は、作業及びこれ以上されていないのはなぜ?
const React = window.React;
const { Map, TileLayer, Marker, MapLayer, PropTypes } = window.ReactLeaflet;
const { markerClusterGroup } = window.L;
class MarkerCluster extends MapLayer {
static childContextTypes = {
layerContainer: PropTypes.layerContainer
};
getChildContext() {
return {
layerContainer: this.leafletElement
}
}
componentWillMount() {
super.componentWillMount()
this.leafletElement = markerClusterGroup()
}
shouldComponentUpdate() {
return false
}
render() {
console.log('update markers cluster')
return <div style={{display: 'none'}}>{this.props.children}</div>
}
}
class MapMarkers extends React.Component {
constructor() {
super()
\t const initialState = [
\t {position: [51.5, -0.1]},
\t {position: [51.51, -0.1]},
\t {position: [51.49, -0.05]},
\t ]
this.state = {markers: initialState};
}
componentDidMount() {
setInterval(this.addMarker.bind(this), 3000);
}
addMarker() {
const lat = (Math.random() * (51.49 - 51.51) + 51.51);
const lng = (Math.random() * (0.05 - 0.1) - 0.1);
const marker = {position: [lat, lng]};
this.setState({markers: this.state.markers.concat([marker])});
}
render() {
console.log('update markers')
const markers = this.state.markers.map((item, key) =>
<Marker position={item.position} key={key} />
);
return <div>{markers}</div>;
}
}
class MyMap extends React.Component {
render() {
return (
<Map center={[51.50, -0.1]} zoom={13}>
<TileLayer
attribution='© <a href="http://osm.org/copyright">OpenStreetMap</a> contributors'
url='http://{s}.tile.osm.org/{z}/{x}/{y}.png'
/>
<MarkerCluster><MapMarkers /></MarkerCluster>
</Map>
)
}
}
class MainLayout extends React.Component {
render() {
\t return (
<MyMap />
)
}
}
window.ReactDOM.render(<MainLayout />, document.getElementById('container'));
.leaflet-container {
height: 400px;
width: 100%;
}
<link href="https://rawgit.com/Leaflet/Leaflet.markercluster/leaflet-0.7/dist/MarkerCluster.Default.css" rel="stylesheet" />
<link href="https://cdnjs.cloudflare.com/ajax/libs/leaflet/0.7.7/leaflet.css" rel="stylesheet" />
<script src="https://cdnjs.cloudflare.com/ajax/libs/leaflet/0.7.7/leaflet.js"></script>
<script src="https://rawgit.com/Leaflet/Leaflet.markercluster/leaflet-0.7/dist/leaflet.markercluster.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/react/15.1.0/react.min.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/react/15.1.0/react-dom.min.js"></script>
<script src="https://npmcdn.com/[email protected]/dist/react-leaflet.js"></script>
<div id="container"></div>
これは、componentShouldUpdateが使用されるものではありません。あなたは更新しないように言いましたが、今は更新していません。それを更新したい場合は、そのようにフックを設定しないでください。 – gravityplanx
なぜ2番目の例が効果的なのですか? – luzny
**は**働いています。あなたは更新しないように指示し、更新していません。更新したい場合は、その関数を 'false'を返すように設定しないでください。 – gravityplanx