我想通过厚度来区分d3.js力图的链接

时间:2014-07-11 07:11:40

标签: javascript svg d3.js force-layout

我想通过厚度来区分链接。

我有数据。

变量“value”表示“thickness”。

“值”的范围是0~1。

    {"nodes":[{"name":"A", "group":1},
              {"name":"B", "group":1},
              {"name":"C", "group":1},
              {"name":"D", "group":1},
              {"name":"E", "group":1}],
     "links":[{"source":0,"target":1,"value":0.9},
              {"source":0,"target":2,"value":0.8},
              {"source":0,"target":3,"value":0.7},
              {"source":1,"target":2,"value":0.7},
              {"source":2,"target":4,"value":0.2},
              {"source":0,"target":4,"value":0.5}]}

我的d3.js图代码是

    <!DOCTYPE html>
    <meta charset="utf-8">

    <body><script src="../d3-master/d3.min.js"></script>
    <head><link rel="stylesheet" type="text/css" href="../D3css/D3css.css"></head>

    <script>

    var width = 960,
        height = 500

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

    var force = d3.layout.force()
        .gravity(.05)
        .distance(100)
        .charge(-100)
        .size([width, height]);

    d3.json("../data/cor_test.json", function(error, json) {

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

      var link = svg.selectAll(".link")
          .data(json.links)
        .enter().append("line")
          .attr("class", "link");

      var node = svg.selectAll(".node")
          .data(json.nodes)
        .enter().append("g")
          .attr("class", "node")
          .call(force.drag);

      node.append("circle")
          .attr("r", 5);

      node.append("text")
          .attr("dx", 12)
          .attr("dy", ".35em")
          .text(function(d) { return d.name });

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

        node.attr("transform", function(d) { return "translate(" + d.x + "," + d.y + ")"; });
      });
    });

    </script>

我改变了这样的代码。

但它不起作用。

      var link = svg.selectAll(".link")
          .data(json.links)
        .enter().append("line")
          .attr("class", "link")
          .attr("stroke-width", function(d) { return d.value; });

更简单的更改:.attr("stroke-width", "5px");也不起作用。

该链接未显示。

我该怎么办?

3 个答案:

答案 0 :(得分:5)

您需要先指定'stroke'属性,因为:

  

笔划属性的默认值为,这意味着永远不会绘制轮廓。

请参阅documentation for stroke。以下是如何完成的示例:

selection
    .attr('stroke', 'red')
    .attr('stroke-width', 5);

这里有一个jsfiddle,展示了它是如何运作的。

答案 1 :(得分:1)

我相信@Oleg的答案是完整的,但是,我只是想提请你注意一个广泛使用链接厚度和其他相关svg属性的例子:

2013 Budget Visualization

enter image description here

相关代码在这里:

        // Enter any new links at the parent's previous position.
    link.enter().insert("svg:path", "g")
            .attr("class", "link")
            .attr("d", function(d) {
                if (Number(d.target[spendField]) > 0) {
                    var o = {x: source.x0, y: source.y0};
                    return diagonal({source: o, target: o});
                }
                else {
                    null;
                }
            })
            .style("stroke",function (d,i) {
                if (d.source.depth==0) {
                    rootCounter++;
                    return (d.source.children[rootCounter-1].linkColor);
                }
                else {
                    return (d.source) ? d.source.linkColor : d.linkColor;
                }
            })
            .style("stroke-width", function (d,i) {

                if (d.source.depth==0) {
                    var ret = level1Radius(d.target[spendField]) * 2;
                    return (isNaN(ret) ? 4 : ret);
                }
                else if (d.source.depth==1) {
                    var ret = level2Radius(d.target[spendField]) * 2;
                    return (isNaN(ret) ? 4 : ret);
                }
                else if (d.source.depth==2) {
                    var ret = level3Radius(d.target[spendField]) * 2;
                    return (isNaN(ret) ? 4 : ret);
                }
                else if (d.source.depth==3) {
                    var ret = level4Radius(d.target[spendField]) * 2;
                    return (isNaN(ret) ? 4 : ret);
                }
             })
            .style("stroke-opacity", function(d){
                var ret = ((d.source.depth+1)/4.5)
                if (d.target[spendField] <= 0) ret=.1;
                return ret;
            })
            .style("stroke-linecap","round")
            .transition()
            .duration(duration);
      //      .attr("d", diagonal);


    // Transition links to their new position.
     var linkUpdate = link.transition()
            .duration(duration)
            .attr("d", diagonal);

     linkUpdate
             .style("stroke-width", function (d,i) {
                 if (d.source.depth==0) {
                     var ret = level1Radius(Number(d.target[spendField])) * 2;
                     return (isNaN(ret) ? 4 : ret);
                 }
                 else if (d.source.depth==1) {
                     var ret = level2Radius(Number(d.target[spendField])) * 2;
                     return (isNaN(ret) ? 4 : ret);
                 }
                 else if (d.source.depth==2) {
                     var ret = level3Radius(Number(d.target[spendField])) * 2;
                     return (isNaN(ret) ? 4 : ret);
                 }
                 else if (d.source.depth==3) {
                     var ret = level4Radius(Number(d.target[spendField])) * 2;
                     return (isNaN(ret) ? 4 : ret);
                 }
            })
         //    .style("stroke-dasharray", function(d) {
         //       var ret=(d.target[spendField] > 0) ? "" : "5,8";
         //       return ret;
         //    })
             .style("stroke-opacity", function(d){
                 var ret = ((d.source.depth+1)/4.5)
                 if (d.target[spendField] <= 0) ret=.1;
                 return ret;
             })


    // Transition exiting nodes to the parent's new position.
    link.exit().transition()
            .duration(duration)
            .attr("d", diagonal)
            .remove();

除了使用strokestroke-width之外,您还可以注意到stroke-opacitystroke-linecap和一般输入/更新/退出模式的使用情况。

希望这有帮助。

答案 2 :(得分:0)

我认为这更多地与style("stroke.width", 5)而非attr("stroke.width", 5)有关,但我不确定,我是d3的新手。