d3.js带标签的可折叠/可扩展力图表

时间:2014-11-07 12:29:47

标签: javascript d3.js

我正在使用d3.js应用程序,该应用程序正在使用具有可collaspable / expandable节点的强制图表库。我热衷于将标签集成到更新功能中。

http://jsfiddle.net/Qh9X5/3452/

这是完整的代码

$(document).ready(function () {

    var init = function (json) {

        var width = 960,
            height = 500,
            root;

        var force = d3.layout.force()
            .size([width, height])
            .on("tick", tick);

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

        var link = svg.selectAll(".link"),
            node = svg.selectAll(".node");

        //d3.json("readme.json", function(json) {
        root = json;
        update();
        //});

        function update() {
            var nodes = flatten(root),
                links = d3.layout.tree().links(nodes);

            // Restart the force layout.
            force.nodes(nodes)
                .links(links)
                .start();

            // Update the links…
            link = link.data(links, function (d) {
                return d.target.id;
            });

            // Exit any old links.
            link.exit().remove();

            // Enter any new links.
            link.enter().insert("line", ".node")
                .attr("class", "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;
            });

            // Update the nodes…
            node = node.data(nodes, function (d) {
                return d.id;
            }).style("fill", color);

            // Exit any old nodes.
            node.exit().remove();

            // Enter any new nodes.
            node.enter().append("circle")
                .attr("class", "node")
                .attr("cx", function (d) {
                return d.x;
            })
                .attr("cy", function (d) {
                return d.y;
            })
                .attr("r", function (d) {
                return Math.sqrt(d.size) / 10 || 4.5;
            })
                .style("fill", color)
                .on("click", click)
                .call(force.drag);


            /*
            var text = svg.append("svg:g")
                .selectAll("g")
                .data(force.nodes()).enter()
                .append("svg:g");

            text.append("svg:text")
                .attr("x", options.labelFontSize)
                .attr("y", ".31em")
                .attr("class", "shadow")
                .text(function (d) {
                return d[options.nodeLabel];
            });
            */


        }

        function tick() {
            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("cx", function (d) {
                return d.x;
            })
                .attr("cy", function (d) {
                return d.y;
            });
        }

        // Color leaf nodes orange, and packages white or blue.
        function color(d) {
            return d._children ? "#3182bd" : d.children ? "#c6dbef" : "#fd8d3c";
        }

        // Toggle children on click.
        function click(d) {
            if (!d3.event.defaultPrevented) {
                if (d.children) {
                    d._children = d.children;
                    d.children = null;
                } else {
                    d.children = d._children;
                    d._children = null;
                }
                update();
            }
        }

        // Returns a list of all nodes under the root.
        function flatten(root) {
            var nodes = [],
                i = 0;

            function recurse(node) {
                if (node.children) node.children.forEach(recurse);
                if (!node.id) node.id = ++i;
                nodes.push(node);
            }

            recurse(root);
            return nodes;
        }
    };



    var datajson = {
        "name": "parentnode",
            "children": [{
            "name": "equens",
                "children": [{
                "name": "Paul",
                    "size": 3938
            }, {
                "name": "John",
                    "size": 3812
            }, {
                "name": "Jack",
                    "size": 6714
            }]
        }, {
            "name": "test",
                "children": [{
                "name": "Jens",
                    "size": 3938
            }, {
                "name": "Robl",
                    "size": 3812
            }, {
                "name": "Mark",
                    "size": 6714
            }]
        }]
    };


    init(datajson);

});

1 个答案:

答案 0 :(得分:1)

文本元素的位置属性是x,y。不是cx和cy。

 var texts = labels.enter()
     .append("text")
     .attr("class", "labels")
     .attr("x", function (d) {
         return d.x;
      })
     .attr("y", function (d) {
         return d.y;
     })
     .attr("dx", 9)
     .attr("dy", ".31em")
     .text(function (d) {
         return d.name;
     });

还添加代码以更新tick函数中文本标签的位置。

function tick() {
    -------------------------
    --------------------------
   texts.attr("x", function (d) {
         return d.x;
     })
     .attr("y", function (d) {
         return d.y;
     });
} 

以下是更新后的JSFiddle