2016-10-22 4 views
2

d3 v4를 사용하여 방사형 트리를 그립니다. 3 년 동안 데이터를로드하는 데 3 개의 버튼이 있습니다. 처음 단추를 클릭하면 루트가 미국에서 다른 값 (미국의 자식)으로 변경됩니다. 추가 클릭 (예 : 약 20 회 클릭) 후에 값이 다시 미국에서 다른 자식으로 변경됩니다.방사형 트리 - 루트 노드 문제

아무도 도와 줄 수 있습니까? 코드를 검색 :

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

.node { 
    cursor: pointer; 
} 

.node circle { 
    fill: #999; 
    stroke: steelblue; 
    stroke-width: 1.5px; 
} 

.node text { 
    font: 10px sans-serif; 
} 

.link { 
    fill: #e6f5c9;//#f03b20; //#c6dbef; 
    //stroke: #ccc; 
    stroke: #e6f5c9;//#f03b20; 
    //stroke-width: 5.5px; 

.ticks { 
    font: 10px sans-serif; 
} 

.track, 
.track-inset, 
.track-overlay { 
    stroke-linecap: round; 
} 

.track { 
    stroke: #000; 
    stroke-opacity: 0.3; 
    stroke-width: 10px; 
} 

.track-inset { 
    stroke: #ddd; 
    stroke-width: 8px; 
} 

.track-overlay { 
    pointer-events: stroke; 
    stroke-width: 50px; 
    cursor: crosshair; 
} 

.handle { 
    fill: #fff; 
    stroke: #000; 
    stroke-opacity: 0.5; 
    stroke-width: 1.25px; 
} 

</style> 
<body> 
<div id="collapseButton"> 
    <input name="collapseButton" 
      type="button" 
      value="Collapse All Nodes" 
      onclick="updateData()" /> 
</div> 
<div id="year_2013"> 
    <input name="2013Data" 
      type="button" 
      value="Wait times for 2013" 
      onclick="updateData2013()" /> 
</div> 
<div id="year_2014"> 
    <input name="2014Data" 
      type="button" 
      value="Wait times for 2014" 
      onclick="updateData2014()" /> 
</div> 
<div id="year_2015"> 
    <input name="2015Data" 
      type="button" 
      value="Wait times for 2015" 
      onclick="updateData2015()" /> 
</div> 
<script src="//d3js.org/d3.v4.min.js"></script> 
<script> 

    var duration=1500, delay = 3000; 


    var width = 960, 
    height = 1000, 
    margin = {top:20,bottom:20,right:20,left:20}; 
    duration = 750; 

    var buttonPressed = "2013"; 

    var nodes,links; 
    var i = 0; 


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

    var g = svg.append("g") 
       //.attr("transform","translate(100,400)"); 
      .attr("transform", "translate(" + width/2 + "," + height/2 + ")"); 
    createSvg2(); 
    //var g = svg.append("g").attr("transform", "translate(" + (width/2 + 40) + "," + (height/2 + 90) + ")"); 

    //var button = g.selectAll("button"); 
    //console.log(button); 

    //g.append("button"); 

    function connector(d) { 
      return "M" + project(d.x, d.y) 
       + "C" + project(d.x, (d.y + d.parent.y)/2) 
       + " " + project(d.parent.x, (d.y + d.parent.y)/2) 
       + " " + project(d.parent.x, d.parent.y); 
    } 

    var tree, 
     root; 

    var nodeSvg, linkSvg, nodeEnter, linkEnter; 
    //updateData2013(); 
    initialFunction(); 
    function initialFunction() 
    { 
     tree = d3.tree() 
     //.size([360,250]); 
     //.size([150,50]), 
     .size([150,100]); 

     function collapse(d) 
     { 
      if (d.children) { 
       d._children = d.children; 
       d._children.forEach(collapse); 
       d.children = null; 
      } 
     } 

    d3.json("treeData.json",function(error,treeData){ 
     if(error) throw error; 

     root = d3.hierarchy(treeData,function(d){ 
      return d.children; 
     }); 
     console.log("Data is: \n"); 
     root.each(function (d) { 
       d.name = d.data.name; //transferring name to a name variable 
       d.id = i; //Assigning numerical Ids 
       i += i; 
     }); 

     root.x0 = height/2; 
      root.y0 = 0; 

     //root.children.forEach(collapse); 
     update(root); 
    }); 
    } 



function update(source) { 

    nodes = tree(root).descendants(); 
    links = nodes.slice(1); 
    var nodeUpdate; 
    var nodeExit; 

// To maintain the depth of the tree always, comment for self arranging tree 
    nodes.forEach(function(d) { d.y = d.depth * 180; }); // 180 

    nodeSvg = g.selectAll(".node") 
       .data(nodes,function(d) { return d.id || (d.id = ++i); }); 


    var nodeEnter = nodeSvg.enter() 
        .append("g") 
        .attr("class", "node") 
        .attr("transform", function(d) { return "translate(" + project(d.x, d.y) + ")"; }) 
        .on("click",click); 
        //.on("mouseover", function(d) { return "minu"; }); 


    nodeEnter.append("circle") 
      .attr("r", function(d){ return 5;}) 
      .style("fill", color); 


    nodeEnter.append("text") 
      .attr("dy", ".31em") 
      .attr("x", function(d) { return d.children || d._children ? -10 : 10; }) 
      //.style("text-anchor", function(d) { return d.x < 180 === !d.children ? "start" : "end"; }) 
      .attr("text-anchor", function(d) { return d.children || d._children ? "start" : "start"; }) 
      //.attr("transform", function(d) { return "rotate(" + (d.x < 180 ? d.x - 40 : d.x + 40) + ")"; }) 
      .attr("transform",function(d) { return d.children || d._children ? ("translate(20,0)") : ("translate(0,0)"); }) // straight to right 
      //.attr("transform", function(d) { return "rotate(" + (d.x < 180 ? d.x - 90 : d.x + 90) + ")"; }) 
      //.attr("transform",function(d) { return d.children || d._children ? ("translate(20,0)") : ("translate(0,0)"); }) 
      .text(function(d) { return d.data.name; }); 

      // Transition nodes to their new position. 
    var nodeUpdate = nodeSvg.merge(nodeEnter).transition() 
     .duration(duration) 
     .attr("transform", function(d) { return "translate(" + project(d.x, d.y) + ")"; }); 


    nodeSvg.select("circle") 
     .style("fill", color); 


    nodeUpdate.select("text") 
     .style("fill-opacity", 1); 

     // Transition exiting nodes to the parent's new position. 
    var nodeExit = nodeSvg.exit().transition() 
     .duration(duration) 
     .attr("transform", function(d) { return "translate(" + source.y + "," + source.x + ")"; }) //for the animation to either go off there itself or come to centre 
     .remove(); 

    nodeExit.select("circle") 
     .attr("r", 1e-6); 

    nodeExit.select("text") 
     .style("fill-opacity", 1e-6); 

    nodes.forEach(function(d) { 
      d.x0 = d.x; 
      d.y0 = d.y; 
    }); 


    linkSvg = g.selectAll(".link") 
        .data(links, function(link) { var id = link.id + '->' + link.parent.id; return id; }); 


    // Transition links to their new position. 
    linkSvg.transition() 
      .duration(duration); 
      // .attr('d', connector); 

    // Enter any new links at the parent's previous position. 
    linkEnter = linkSvg.enter().insert('path', 'g') 
        .attr("class", "link") 
        .attr("d", function (d) { 
         var o = {x: source.x0, y: source.y0, parent: {x: source.x0, y: source.y0}}; 
         return connector(o); 
        }) 
        .style("fill",pathColor) 
        .style("stroke",pathColor) 
        .style("stroke-width","1.5px"); 



    // Transition links to their new position. 
    linkSvg.merge(linkEnter).transition() 
        .duration(duration) 
        .attr("d", connector); 


    // Transition exiting nodes to the parent's new position. 
    linkSvg.exit().transition() 
        .duration(duration) 
        .attr("d", function (d) { 
         var o = {x: source.x, y: source.y, parent: {x: source.x, y: source.y}}; 
         return connector(o); 
        }) 
        .remove(); 



} 
//timeSlider(); 
function showClock(d) 
{ 
    console.log("Show Clock"); 
    console.log(project(d.x,d.y)); 

} 

function click(d) { 

    if (d.children) { 
    d._children = d.children; 
    d.children = null; 
    } else { 

    d.children = d._children; 
    if(d.children == null) 
    { 
     showClock(d); 
    } 
    d._children = null; 


    } 
    update(d); 
} 

function updateData2013() 
{ 
    buttonPressed = "2013"; 
    initialFunction(); 
    console.log("2013 Data"); 
    //setTimeout(updateData2014, duration + delay); 

} 

function updateData2014() 
{ 
    buttonPressed = "2014"; 
    initialFunction(); 
    console.log("2014 Data"); 
    //setTimeout(updateData2015, duration + delay); 
} 

function updateData2015() 
{ 
    buttonPressed = "2015"; 
    initialFunction(); 
    console.log("2015 Data"); 
    //setTimeout(updateData2013, duration + delay); 
} 

function pathColor(d) 
{ 
//['#1b9e77','#d95f02','#7570b3','#e7298a','#66a61e','#e6ab02'] 
    if(buttonPressed == "2013") 
    { 
     if(d.data.time_2013 >= 5 && d.data.time_2013 <= 8) 
     { 
      return "#1b9e77"; 
     } 
     else if(d.data.time_2013 > 8 && d.data.time_2013 <= 11) 
     { 
      return "#d95f02"; 
     } 
     else if(d.data.time_2013 > 11 && d.data.time_2013 <= 14) 
     { 
      return "#7570b3"; 
     } 
     else if(d.data.time_2013 > 14 && d.data.time_2013 <= 17) 
     { 
      return "#e7298a"; 
     } 
     else if(d.data.time_2013 > 17 && d.data.time_2013 <= 21) 
     { 
      return "#66a61e"; 
     } 
     else if(d.data.time_2013 > 21 && d.data.time_2013 <= 24) 
     { 
      return "#e6ab02"; 
     } 
    } 
    else if(buttonPressed == "2014") 
    { 
     if(d.data.time_2014 >= 5 && d.data.time_2014 <= 8) 
     { 
      return "#1b9e77"; 
     } 
     else if(d.data.time_2014 > 8 && d.data.time_2014 <= 11) 
     { 
      return "#d95f02"; 
     } 
     else if(d.data.time_2014 > 11 && d.data.time_2014 <= 14) 
     { 
      return "#7570b3"; 
     } 
     else if(d.data.time_2014 > 14 && d.data.time_2014 <= 17) 
     { 
      return "#e7298a"; 
     } 
     else if(d.data.time_2014 > 17 && d.data.time_2014 <= 21) 
     { 
      return "#66a61e"; 
     } 
     else if(d.data.time_2014 > 21 && d.data.time_2014 <= 24) 
     { 
      return "#e6ab02"; 
     } 
    } 
    else 
    { 
     if(d.data.time_2015 >= 5 && d.data.time_2015 <= 8) 
     { 
      return "#1b9e77"; 
     } 
     else if(d.data.time_2015 > 8 && d.data.time_2015 <= 11) 
     { 
      return "#d95f02"; 
     } 
     else if(d.data.time_2015 > 11 && d.data.time_2015 <= 14) 
     { 
      return "#7570b3"; 
     } 
     else if(d.data.time_2015 > 14 && d.data.time_2015 <= 17) 
     { 
      return "#e7298a"; 
     } 
     else if(d.data.time_2015 > 17 && d.data.time_2015 <= 21) 
     { 
      return "#66a61e"; 
     } 
     else if(d.data.time_2015 > 21 && d.data.time_2015 <= 24) 
     { 
      return "#e6ab02"; 
     } 
    } 
} 

function color(d) { 
    return d._children ? "#3182bd" // collapsed package 
     : d.children ? "#c6dbef" // expanded package 
     : "#fd8d3c"; // leaf node 
} 

function project(x, y) { 
    var angle = (x - 90)/180 * Math.PI, radius = y; 
    return [radius * Math.cos(angle), radius * Math.sin(angle)]; 
} 

function updateData() 
{ 
    console.log("Button is clicked"); 
    //toggleAll(root.children); 
    root.children.forEach(toggleAll); 

} 

function toggleAll(d) { 
    if (d.children) { 
     d.children.forEach(toggleAll); 
     compressNodes(d); 
    } 
} 

function compressNodes(d) { 
    if(d==root) 
    { 
    } 
    else{ 
     console.log("inside d.children"); 
    d._children = d.children; 
    d.children = null; 
    update(d); 
    //simulation.restart(); 
    } 


} 
function createSvg2() 
{ 
    var width1 = 10, 
    height1 = 1000; 

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

    svg2.append("circle") 
    .attr("r",2.5) 
    .attr("transform","translate(" + width1/2 + "," + height1/4 + ")") 
    .attr("fill","red"); 
} 

</script> 
</body> 
</html> 

JSON을 :

가장 간단한 솔루션이로부터 data 기능의 주요 변화
{ 
    "name": "United States", 
    "children": [ 
    { 
     "name": "Ohio", 
     "children":[ 
     { "name" : "Cincinnati Northern Kentucky Intl", "code" : "CVG" , "time_2013": 15.01, "time_2014": 13.22, "time_2015": 13.81} 
     ] 
    }, 
    { 
     "name": "California", 
     "children":[ 
     {"name": "San Francisco", "code" : "" , "time_2013":15, "time_2014": 15.01, "time_2015": 15.01}, 
     {"name": "San Jose", "code" : "" , "time_2013":25, "time_2014": 15.01, "time_2015": 15.01}, 
     {"name": "Los Angeles", "code" : "" , "time_2013":17, "time_2014": 15.01, "time_2015": 15.01} 
     ] 
    }, 
    { 
     "name": "Illinois", 
     "children":[ 
     { "name" : "Chicago Ohare Intl", "code" : "ORD" , "time_2013": 18.58, "time_2014": 14.37, "time_2015": 14.32}, 
     { "name" : "Chicago Midway Intl", "code" : "MDW" , "time_2013": 11.19 , "time_2014": 14.37, "time_2015": 7.31} 
     ] 
    }, 
    { 
     "name": "Colorado", 
     "children" : [ 
     { "name": "Denver Intl", "code" : "DEN" , "time_2013": 13.31, "time_2014": 13.33, "time_2015": 12.51} 
     ] 
    }, 
    { 
     "name": "Florida", 
     "children" : [ 
     { "name": "Florida airport", "code" : "" , "time_2013": 13.31, "time_2014": 13.33, "time_2015": 12.51} 
     ] 
    }, 
    { 
     "name": "Georgia", 
     "children" : [ 
     { "name": "Hartsfield Jackson Atlanta Intl", "code" : "ATL" , "time_2013": 10.08, "time_2014": 10.00, "time_2015": 10.81} 
     ] 
    }, 
    { 
     "name": "Kentucky", 
     "children" : [ 
     { "name": "Kentucy airport", "code" : "KEN" , "time_2013": 13.31, "time_2014": 13.33, "time_2015": 12.51} 
     ] 
    }, 
    { 
     "name": "Massachussets", 
     "children" : [ 
     {"name": "General Edward Lawrence Logan Intl", "code" : "BOS" , "time_2013": 19.86, "time_2014": 19.24, "time_2015": 17.22} 
     ] 
    }, 
    { 
     "name": "Michigan", 
     "children" : [ 
     {"name" : "Detroit Metro Wayne Co", "code" : "DTW" , "time_2013":15.71, "time_2014": 15.55, "time_2015": 15.01} 
     ] 
    }, 
    { 
     "name": "Minnesota", 
     "children" : [ 
     { "name": "Minnesota airport", "code" : "DEN" , "time_2013": 13.31, "time_2014": 13.33, "time_2015": 12.51} 
     ] 
    }, 
    { 
     "name": "Missouri", 
     "children" : [ 
     { "name": "Missouri airport", "code" : "DEN" , "time_2013": 13.31, "time_2014": 13.33, "time_2015": 12.51} 
     ] 
    }, 
    { 
     "name": "North Carolina", 
     "children" : [ 
     {"name" : "Charlotte Douglas Intl","code" : "CLT" , "time_2013": 13.75 , "time_2014": 12.73, "time_2015": 9.21} 
     ] 
    }, 
    { 
     "name": "Nevada", 
     "children" : [ 
     { "name": "Nevada airport", "code" : "DEN" , "time_2013": 13.31, "time_2014": 13.33, "time_2015": 12.51} 
     ] 
    }, 
    { 
     "name": "Newyork", 
     "children" : [ 
     { "name": "Newyork airport", "code" : "DEN" , "time_2013": 13.31, "time_2014": 13.33, "time_2015": 12.51} 
     ] 
    }, 
    { 
     "name": "Oregon", 
     "children" : [ 
     { "name": "Oregon airprot", "code" : "OR" , "time_2013": 13.31, "time_2014": 13.33, "time_2015": 12.51} 
     ] 
    }, 
    { 
     "name": "Pennsylvania", 
     "children": [ 
     { "name" : "Pensylvania Airport", "code" : "PEN" , "time_2013" : 9.18, "time_2014": 7.7, "time_2015": 9.31} 
     ] 
    }, 
    { 
     "name": "Mary Land", 
     "children": [ 
     { "name" : "Baltimore Washington Intl", "code" : "BWI" , "time_2013" : 9.18, "time_2014": 7.7, "time_2015": 9.31} 
     ] 
    }, 
    { 
     "name": "Hawaii", 
     "children" : [ 
     { "name": "Hawaiiiiiii" , "code" : "HAW" , "time_2013": 21.33, "time_2014": 11.98, "time_2015": 13.47} 
     ] 
    }, 
    { 
     "name": "Texas", 
     "children" : [ 
     { "name": "Dallas Fort Worth Intl" , "code" : "DFW" , "time_2013": 21.33, "time_2014": 11.98, "time_2015": 13.47}, 
     { "name": "Houston" , "code" : "" , "time_2013": 13, "time_2014": 15.01, "time_2015": 15.01}, 
     { "name": "Austin Bergstrom Intl" , "code" : "AUS" , "time_2013": 13.52, "time_2014": 16.38, "time_2015": 13.29} 
     ] 
    }, 
    { 
     "name": "Utah", 
     "children" : [ 
     { "name": "Utah Airport", "code" : "DEN" , "time_2013": 13.31, "time_2014": 13.33, "time_2015": 12.51} 
     ] 
    }, 
    { 
     "name": "Virginia", 
     "children" : [ 
     { "name": "Virginia Airport", "code" : "DEN" , "time_2013": 13.31, "time_2014": 13.33, "time_2015": 12.51} 
     ] 
    } 
    ] 
} 

답변

0

: 여기에

nodeSvg = g.selectAll(".node") 
    .data(nodes,function(d) { return d.id || (d.id = ++i); }); 

:

nodeSvg = g.selectAll(".node") 
    .data(nodes,function(d) { return d.id; }); 

여기에 https://plnkr.co/edit/tMQBMyaWJEtEl9aPoDkQ?p=preview

+0

너무 많이 Gerardo 고맙습니다! – Minu