3

選択可能なリンク/ノード、ツールチップ、魚眼効果、そして-私の質問にとって重要な-ズームとパンなど、いくつかの追加機能を備えた力指向グラフレイアウトに取り組んでいます。

これで、ズームは次のように非常にうまく機能します。

d3 ... .append('svg:g').call(d3.behavior.zoom().on("zoom", redraw))... 

再描画関数は次のようになります...

function redraw() {
  trans = d3.event.translate;
  scale = d3.event.scale;
  vis.attr("transform", "translate(" + trans + ")" + " scale(" + scale + ")");
}

ただし、この方法では、フォントサイズ、グラフのエッジ、ノードを囲む線のストローク幅などを含むSVGグラフィック全体がズームされます。

特定の要素をズームしないことはどういうわけか可能ですか?私がこれまでに見た唯一の解決策は、このような行を置くことです(ここからそれを取りましたhttp://jsfiddle.net/56RDx/2/

node.attr("font-size", (nodeFontSize / d3.event.scale) + "px");

再描画メソッドでは、基本的に特定の要素のズームをオンザフライで反転します。ただし、私の問題は(これが醜いハックであることを除けば)、グラフ描画時にエッジ幅が動的に生成されるため(一部のグラフプロパティに従って...)、この「反転」メソッドが機能しないことです...

4

2 に答える 2

8
  1. ズームをトリガーする要素にクラスを追加できます。

    d3 ... .append('svg:g').classed("some_classname", true).call(d3.behavior.zoom().on("zoom", redraw))...
    

    次に行います:

    function redraw() {
      trans = d3.event.translate;
      scale = d3.event.scale;
      vis.selectAll("some_classname").attr("transform", "translate(" + trans + ")" + " scale(" + scale + ")");
    }
    

  2. または、ズームをトリガーしたくないすべての要素にクラスを追加してから、CSS3を使用することができます:疑似クラスではありません:

    function redraw() {
      trans = d3.event.translate;
      scale = d3.event.scale;
      vis.selectAll("*:not(.some_classname)").attr("transform", "translate(" + trans + ")" + " scale(" + scale + ")");
    }
    
于 2012-11-07T07:58:26.470 に答える
2

私が見つけた唯一の解決策は「醜いハック」です。たとえば、線をズームしないようにしようとしている場合は、以下を試してください。ズームインとズームアウトの両方で機能します。

デモ: http: //jsfiddle.net/SO_AMK/gJMTb/

JavaScript:

function redraw() {
  vis.attr("transform", "translate(" + d3.event.translate + ")" + " scale(" + d3.event.scale + ")");
  vis.attr("font-size", (nodeFontSize / d3.event.scale) + "px");
  vis.selectAll("line.link").style("stroke-width", getStrokeWidth); // Function so it runs for each element individually
}

function getStrokeWidth(){
    if (!this.__data__.stroke) { // Doesn't exist, so set it to the original stroke-width
        this.__data__.stroke = parseFloat(d3.select(this).style("stroke-width"));
        // I found __data__ to be easier than d3's .data()
    }
    return this.__data__.stroke / d3.event.scale + "px";
}

で関数を使用する方法の詳細については、ドキュメントを参照してくださいstyle()

于 2012-10-16T15:29:55.023 に答える