javascript - Hide unrelated parent nodes but child node in D3.js - Stack Overflow

I'm trying to do this thing in D3.js but unable to find a way to do it.What I want to do is, when

I'm trying to do this thing in D3.js but unable to find a way to do it.

What I want to do is, when a person clicks on the root node (level 0), it should show the child elements (level 1). When a person clicks on one of the child nodes (level 1) it should show its childrens (level 2) and the parent and parent-of-parent (level 1, this what the user clicked), but hide all the unrelated parents (from level 1).

Let me explain you this with pictures.

I'm trying to do this thing in D3.js but unable to find a way to do it.

What I want to do is, when a person clicks on the root node (level 0), it should show the child elements (level 1). When a person clicks on one of the child nodes (level 1) it should show its childrens (level 2) and the parent and parent-of-parent (level 1, this what the user clicked), but hide all the unrelated parents (from level 1).

Let me explain you this with pictures.

Share Improve this question edited Apr 26, 2015 at 6:22 asked Apr 26, 2015 at 4:59 user3418870user3418870 5
  • In jQuery you can hide the siblings of a node by calling $('selector').siblings().hide() – jwatts1980 Commented Apr 26, 2015 at 6:35
  • Are you trying to do this with d3.layout.tree(), or are you asking about a more general case with DOM elements? – davidhwang Commented Apr 26, 2015 at 15:15
  • Yeah! I'm trying to do it with d3.layout.tree(). – user3418870 Commented Apr 26, 2015 at 15:46
  • 1 What have you tried thus far? What is your setup? What exactly does not work? To get further help you need to provide some code. Please consider putting together a JSFiddle to play around with. – altocumulus Commented Apr 26, 2015 at 19:37
  • 1 Have you seen this example covering a collapsible tree layout? If not exactly what you are after, it lays out the basics pretty well. – altocumulus Commented Apr 26, 2015 at 19:38
Add a ment  | 

1 Answer 1

Reset to default 6

You could do something like http://bl.ocks/benlyall/4fea200ebebb273aa4df

I forked http://bl.ocks/mbostock/4339083 and made a few changes:

  1. Added a new property to each node .all_children which keeps track of all children. We need this, or something similar since .children contains the child nodes currently displayed, and ._children is used by the existing code to determine if a node contains children or not (and sets the style accordingly).

    Also added a .hidden property that helps to determine whether or not the node should be displayed.

    These are added after loading the data:

    d3.json("flare.json", function(error, flare) {
        root = flare;
        root.x0 = height / 2;
        root.y0 = 0;
    
        function collapse(d) {
            if (d.children) {
                d.all_children = d.children;
                d._children = d.children;
                d._children.forEach(collapse);
                d.children = null;
                d.hidden = true;
            }
        }
    
        root.all_children = root.children;
        root.children.forEach(collapse);
        root.children.forEach(function(d) { d.hidden = false; });
        root.hidden = false;
        update(root);
    });
    
  2. Updated the update function to reflect the new changes and only draw the nodes that are supposed to be drawn:

    function update(source) {
    
        // Compute the new tree layout.
        var nodes = tree.nodes(root).filter(function(d) { return !d.hidden; }).reverse(),
        links = tree.links(nodes);
    

    The nodes variable is set to only contain nodes that are NOT hidden.

  3. Updated the click handler to correctly set the state of the nodes in the display:

    // Toggle children on click.
    function click(d) {
        if (d.children) {
            d._children = d.children;
            d.children = null;
            if (d._children) {
                d._children.forEach(function(n) { n.hidden = true; });
    
                if (d.parent) {
                    d.parent.children = d.parent.all_children;
                    d.parent.children.forEach(function(n) {
                        n.hidden = false;
                    });
                }
            }
        } else {
            d.children = d._children;
            d._children = null;
            if (d.children) {
                d.children.forEach(function(n) { n.hidden = false; });
    
                if (d.parent) {
                    d.parent.children = [d,];
                    d.parent.children.filter(function(n) { return n !== d; }).forEach(function(n) {
                        n.hidden = true;
                    });
                }
            }
        }
        update(d);
    }
    

    The first part of the if statement is called when we're collapsing a node, in which case, we need to display all of the siblings of the clicked node by setting d.parent.children to d.parent.all_children and setting each of those nodes to .hidden = false. And we need to hide all the children of the clicked node by setting d.children = null and then setting each node in d._children to hidden.

    The second part of the if statement is called when we're expanding a node, in which case, we need to hide its siblings (set .hidden to true) and update the .children property of the clicked node's .parent node so that only the clicked node is listed as a child.

发布者:admin,转转请注明出处:http://www.yc00.com/questions/1745587765a4634646.html

相关推荐

发表回复

评论列表(0条)

  • 暂无评论

联系我们

400-800-8888

在线咨询: QQ交谈

邮件:admin@example.com

工作时间:周一至周五,9:30-18:30,节假日休息

关注微信