ReactJS、d3JS、ES6を使用して組織図を作成しています。 チャートを作成して見ることができます。 ただし、ズームとドラッグの動作をグラフに追加したいので、 d3.behavior.zoomを使用しズームされたメソッドが呼び出されていることがわかりますが、
ズーム動作をdiv、svg、gにアタッチしてみましたが、何も役に立ちません。 ズームされた動作が呼び出されますが、イベントはnullです。
私のASP.NETプロジェクトでは、d3.eventがnullである理由に関連する問題として多くのスタックオーバーフローの回答が言及されているsystemJS構成以外に、d3.jsへの参照がないことを確認しました。
私のコードは、古いバージョンのReactJSを使用するhttps://github.com/Swizec/candidate-bucket-chart/blob/169779e110c8825f4545c71ae5845ff7bad4f1f4/src/BubbleChart.jsxのような例と非常によく似てい
これは私のsystemJS構成です:
<script>
System.defaultJSExtensions = true;
System.config({
map: {
'rx': "https://cdnjs.cloudflare.com/ajax/libs/rxjs/4.0.7/rx.all.min.js",
'react': 'https://cdnjs.cloudflare.com/ajax/libs/react/15.0.1/react.js',
'react-dom': 'https://cdnjs.cloudflare.com/ajax/libs/react/15.0.1/react-dom.js',
'd3': 'https://cdnjs.cloudflare.com/ajax/libs/d3/3.5.16/d3.js'
}
});
System.import('../app/app.js');
</script>
import React, { Component } from 'react';
import * as Rx from 'rx';
import * as d3 from 'd3';
import Person from './person';
class OrgChart extends Component {
constructor(props) {
super(props);
this.state = { persons: [] };
}
componentWillMount() {
// Just read a JSON file
var source = Rx.Observable.fromPromise($.getJSON("/js/org-persons.json"));
source.subscribe(
function(chart) {
var tree = d3.layout.tree()
.nodeSize([110, 50])
.separation(function() {
return 1;
});
var nodes = tree.nodes(chart[0]).reverse();
var links = tree.links(nodes);
var p = [];
nodes.forEach(function(node) {
fs.push((<Person x={node.x} y={node.y}></Person>));
}.bind(this));
this.setState({ person: p });
}.bind(this)
);
}
componentDidMount() {
var rootX = document.body.clientWidth / 4;
var rootY = 300;
// A standard setup with d3 to use it's zoom/drag behavior
var zoom = d3.behavior.zoom()
.scaleExtent([1, 10])
.on("zoom", this.zoomed)
.translate([rootX, rootY]);
// Attach zoom behavior to the first group in the svg.
d3.select("#viewport")
.call(zoom);
}
// When I drag the svg, this function gets called but the event is null. d3 is a global object.
zoomed() {
d3.select("#viewport").attr("transform", "translate(" + d3.event.translate + ")scale(" + d3.event.scale + ")");
}
// renders an org chart
render() {
return (
<div id='treeContainer'><svg id='fullTree' width='100%'>
<g id='viewport'>
{ this.state.persons }
</g>
</svg></div>
);
}
}
export default OrgChart;
参照するコードは一般的なd3javascriptのようであり、イベントはReactのイベントシステムを通過しません。 これは、Reactとは関係のないd3の質問のように見えます。 このため、この問題を解決します。
別の注意点として、IDで選択するのではなく、 ref
を使用してDOMノードを参照する必要があります。 d3.select("#viewport")
ようなものを使用すると、同じIDを選択する他のコンポーネントとの相互運用性の問題が発生し、コンポーネントが同じページで複数回使用されるのを防ぐことができます。 ref
を使用すると、これらの問題が解決します。
この問題を抱えている他の人はきっとここで終わるでしょう、それでここに私のために働いたアプローチがあります:
> window.theD3versionHostingTheEvent = d3;
listener.apply(this, argumentz);
まで前に進み、エラーをスローする場所に到達するまで[次の関数呼び出しにステップイン]を選択します。window.theD3versionHostingTheEvent == d3
結果がfalse
場合、間違いなくd3の2つのインスタンスを実行しています。 私の場合、使用していたライブラリの1つにd3がバンドルされていることがわかりました。
インポート/エクスポート構文を使用してd3から可変フィールドをインポートするのに問題があるBabelを使用している可能性が非常に高いです。
これを参照してください: https :
次のようにd3をインポートする方法を変更する必要があります。
import * as d3 from 'd3';
import {event as currentEvent} from 'd3';
そして、 d3.event
すべての出現をcurrentEvent
置き換えます。
これにより、d3.jsv3の問題が修正されます。
最も参考になるコメント
インポート/エクスポート構文を使用してd3から可変フィールドをインポートするのに問題があるBabelを使用している可能性が非常に高いです。
これを参照してください: https :
次のようにd3をインポートする方法を変更する必要があります。
そして、
d3.event
すべての出現をcurrentEvent
置き換えます。これにより、d3.jsv3の問題が修正されます。