1. 程式人生 > >D3.js實現節點摺疊+閃爍+葉節點形狀改變的demo

D3.js實現節點摺疊+閃爍+葉節點形狀改變的demo

var treeData = [ { "name": "Top Level", "parent": "null", "value": 10, "children": [ { "name": "Level 2: A", "parent": "Top Level", "value": 10, "children": [ { "name": "Son of A", "parent": "Level 2: A", "value"
: 5 }, { "name": "Daughter of A", "parent": "Level 2: A", "value": 5 }, ] }, { "name": "Level 2: B", "parent": "Top Level", "value": 5 }, { "name": "Level 2: C", "parent"
: "Top Level", "value": 5 }, ] } ]; // ************** Generate the tree diagram ***************** //定義樹圖的全域性屬性(寬高) var margin = {top: 20, right: 120, bottom: 20, left: 120}, width = 960 - margin.right - margin.left, height = 500 - margin.top - margin.bottom; var i = 0, duration = 750
,//過渡延遲時間 root; var tree = d3.layout.tree()//建立一個樹佈局 .size([height, width]); var diagonal = d3.svg.diagonal() .projection(function(d) { return [d.y, d.x]; });//建立新的斜線生成器 //宣告與定義畫布屬性 var svg = d3.select("body").append("svg") .attr("width", width + margin.right + margin.left) .attr("height", height + margin.top + margin.bottom) .append("g") .attr("transform", "translate(" + margin.left + "," + margin.top + ")"); root = treeData[0];//treeData為上邊定義的節點屬性 root.x0 = height / 2; root.y0 = 0; update(root); d3.select(self.frameElement).style("height", "500px"); function update(source) { // Compute the new tree layout.計算新樹圖的佈局 var nodes = tree.nodes(root).reverse(), links = tree.links(nodes); // Normalize for fixed-depth.設定y座標點,每層佔180px nodes.forEach(function(d) { d.y = d.depth * 180; }); // Update the nodes…每個node對應一個group var node = svg.selectAll("g.node") .data(nodes, function(d) { return d.id || (d.id = ++i); });//data():繫結一個數組到選擇集上,陣列的各項值分別與選擇集的各元素繫結 // Enter any new nodes at the parent's previous position.新增節點資料集,設定位置 var nodeEnter = node.enter().append("g") //在 svg 中新增一個g,g是 svg 中的一個屬性,是 group 的意思,它表示一組什麼東西,如一組 lines , rects ,circles 其實座標軸就是由這些東西構成的。 .attr("class", "node") //attr設定html屬性,style設定css屬性 .attr("transform", function(d) { return "translate(" + source.y0 + "," + source.x0 + ")"; }) .on("click", click); //新增連線點---此處設定的是圓圈過渡時候的效果(顏色) // nodeEnter.append("circle") // .attr("r", 1e-6);//d 代表資料,也就是與某元素繫結的資料。 nodeEnter.append("path") .style("stroke-width", "2px") .style("stroke", "#4682b4") .style("fill", "white") .attr("d", d3.svg.symbol() .size(function(d){ if (d.value <= 9) { return "400"; } else if (d.value >= 9) { return "400";} }) .type(function(d) { if (d.value <= 9) { return "triangle-up"; } else if (d.value >= 9) { return "circle";} })) .attr('class',function(d){ if(d.value <= 9 ){ return 'bling'; }else{ return 'fill_normal'; } }); //新增標籤 nodeEnter.append("text") .attr("x", function(d) { return d.children || d._children ? -13 : 13; }) .attr("dy", ".35em") .attr("text-anchor", function(d) { return d.children || d._children ? "end" : "start"; }) .text(function(d) { return d.name; }) .style("fill-opacity", 1e-6); // Transition nodes to their new position.將節點過渡到一個新的位置-----主要是針對節點過渡過程中的過渡效果 //node就是保留的資料集,為原來資料的圖形新增過渡動畫。首先是整個組的位置 var nodeUpdate = node.transition() //開始一個動畫過渡 .duration(duration) //過渡延遲時間,此處主要設定的是圓圈節點隨斜線的過渡延遲 .attr("r", 10) .attr("transform", function(d) { return "translate(" + d.y + "," + d.x + ")"; }); //更新連線點的填充色 // nodeUpdate.select("circle") // .attr("r", 10) // .attr('class',function(d){ // if(d.value <= 9){ // return 'bling'; // }else{ // return 'fill_normal'; // } // }); nodeUpdate.select("path") .style("stroke-width", "2px") .style("stroke", "#4682b4") .style("fill", "white") .attr("d", d3.svg.symbol() .size(function(d){ if (d.value <= 9) { return "400"; } else if (d.value >= 9) { return "400";} }) .type(function(d) { if (d.value <= 9) { return "triangle-up"; } else if (d.value >= 9) { return "circle";} })) .attr('class',function(d){ if(d.value <= 9 ){ return 'bling'; }else{ return 'fill_normal'; } }); nodeUpdate.select("text") .style("fill-opacity", 1); // Transition exiting nodes to the parent's new position.過渡現有的節點到父母的新位置。 //最後處理消失的資料,新增消失動畫 var nodeExit = node.exit().transition() .duration(duration) .attr("transform", function(d) { return "translate(" + source.y + "," + source.x + ")"; }) .remove(); nodeExit.select("circle") .attr("r", 1e-6); nodeExit.select("text") .style("fill-opacity", 1e-6); // Update the links…線操作相關 //再處理連線集合 var link = svg.selectAll("path.link") .data(links, function(d) { return d.target.id; }); // Enter any new links at the parent's previous position. //新增新的連線 link.enter().insert("path", "g") .attr("class", "link") .attr("d", function(d) { var o = {x: source.x0, y: source.y0}; return diagonal({source: o, target: o}); //diagonal - 生成一個二維貝塞爾聯結器, 用於節點連線圖. }) .style("stroke",function(d){ //d包含當前的屬性console.log(d) return '#ccc'; }); // Transition links to their new position.將斜線過渡到新的位置 //保留的連線新增過渡動畫 link.transition() .duration(duration) .attr("d", diagonal); // Transition exiting nodes to the parent's new position.過渡現有的斜線到父母的新位置。 //消失的連線新增過渡動畫 link.exit().transition() .duration(duration) .attr("d", function(d) { var o = {x: source.x, y: source.y}; return diagonal({source: o, target: o}); }) .remove(); // Stash the old positions for transition.將舊的斜線過渡效果隱藏 nodes.forEach(function(d) { d.x0 = d.x; d.y0 = d.y; }); } //定義一個將某節點摺疊的函式 // Toggle children on click.切換子節點事件 function click(d) { if (d.children) { d._children = d.children; d.children = null; } else { d.children = d._children; d._children = null; } update(d); }