【问题标题】:Moving svg markers around a rectangular shape in d3js在d3js中围绕矩形移动svg标记
【发布时间】:2015-01-08 15:47:28
【问题描述】:

我正在使用 d3 使用固定的力导向布局来可视化基因网络。

图表包含矩形/椭圆/圆形矩形节点,这些节点之间的链接末端带有标记。到目前为止(据我所知),这些标记由 refX 和 refX 定位,因此沿着连接两个节点的路径末端周围的径向形状。有什么方法可以定义“路径”或标记,使标记沿着节点的形状移动,而不是围绕该节点移动,相对于路径末端有固定距离?

为了说明我的问题:

var graph = {
  "nodes": [{
    "name": "from",
    "fixed": true,
    x: 100,
    y: 100,
    w: 60,
    h: 20
  }, {
    "name": "to",
    "fixed": true,
    x: 250,
    y: 250,
    w: 60,
    h: 20
  }],
  "links": [{
    "source": 0,
    "target": 1
  }]
}
var width = 960,
  height = 500;

var force = d3.layout.force()
  .charge(-120)
  .linkDistance(300)
  .size([width, height]);

var svg = d3.select("body").append("svg")
  .attr("width", width)
  .attr("height", height);

force.nodes(graph.nodes)
  .links(graph.links)
  .start();

var defs = svg.append("svg:defs");
var marker = defs.selectAll("marker");

marker = marker.data([{
    "type": "arrow",
    "d": "M0,-5L10,0L0,5L2,0",
    "view": "0 -5 10 10",
    "color": "#000000"
  }])
  .enter()
  .append("svg:marker")
  .attr("id", function(d) {
    return d.type;
  })
  .attr("viewBox", function(d) {
    return d.view;
  })
  .attr("refX", 30)
  .attr("refY", 0)
  .attr("markerWidth", 5)
  .attr("markerHeight", 5)
  .attr("orient", "auto");

marker.append("svg:path")
  .attr("d", function(d) {
    return d.d;
  })
  .style("fill", function(d) {
    return d.color;
  });

var link = svg.selectAll(".link")
  .data(graph.links)
  .enter().append("line")
  .attr("class", "link")
  .style("stroke-width", "5")
  .attr("marker-end", "url(#arrow)");

var node = svg.selectAll(".node")
  .data(graph.nodes)
  .enter().append("rect")
  .attr("class", "node")
  .attr("width", function(d) {
    return d.w;
  })
  .attr("height", function(d) {
    return d.h;
  })
  .style("fill", "blue")
  .call(force.drag);

node.append("title")
  .text(function(d) {
    return d.name;
  });

force.on("tick", function() {
  link.attr("x1", function(d) {
      return d.source.x + d.source.w / 2;
    })
    .attr("y1", function(d) {
      return d.source.y + d.source.h / 2;
    })
    .attr("x2", function(d) {
      return d.target.x + d.target.w / 2;
    })
    .attr("y2", function(d) {
      return d.target.y + d.target.h / 2;
    })

  node.attr("x", function(d) {
      return d.x;
    })
    .attr("y", function(d) {
      return d.y;
    });
});
.node {
  stroke: #fff;
  stroke-width: 1.5px;
}
.link {
  stroke: #999;
  stroke-opacity: .6;
}
<script src="https://cdnjs.cloudflare.com/ajax/libs/d3/3.4.11/d3.min.js"></script>

JsFiddle 示例:

http://jsfiddle.net/millermaximilian/w3eq6ccc/

非常感谢您的任何建议!

最大

【问题讨论】:

    标签: svg d3.js markers


    【解决方案1】:

    没有内置的方式。您可以创建代码以根据形状的数学定义参数化标记的位置。从根本上说,当您设置一个标记以在该节点是一个圆时从该节点绘制 X px 时会发生什么,因为从数学上讲,它只是半径。对于更复杂的形状,它更难,当然正方形、矩形和椭圆形仍然相对容易计算。对于复杂的svg:path 形状,我想你可以使用path 的内置getPointAtLength 的某种组合并计算从一个节点到另一个节点的角度来做到这一点,但我不知道有任何任何早期示例的实现,更不用说类似的了。

    【讨论】:

      猜你喜欢
      • 2015-03-29
      • 1970-01-01
      • 1970-01-01
      • 2013-02-14
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2013-05-23
      • 1970-01-01
      相关资源
      最近更新 更多