2016-06-22 14 views
0

Невозможно сделать круговую диаграмму из набора данных

<!DOCTYPE html> 
 
    <html> 
 
     <head> 
 
     <meta charset="utf-8"> 
 
     <title>Testing Pie Chart</title> 
 
     <script src="d3.v3.min.js" charset="utf-8"></script> 
 
     <style type="text/css"> 
 
     #chart { 
 
      margin-top: 100px;            
 
      position: absolute; 
 
      margin-right: 50px; 
 
      margin-left: 50px;           
 
      }                 
 
      .tooltip {               
 
      background: #eee;            
 
      box-shadow: 0 0 5px #999999;          
 
      color: #900C3F;              
 
      display: inline-block;             
 
      font-size: 12px;             
 
      left: 600px;              
 
      padding: 10px;             
 
      position: absolute;            
 
      text-align: center;            
 
      top: 95px;              
 
      width: 150px;              
 
      z-index: 10; 
 
      opacity: 1;             
 
     }                 
 
     rect { 
 
      stroke-width: 2; 
 
     } 
 
     path { 
 
      stroke: #ffffff; 
 
      stroke-width: 0.5; 
 
     } 
 
     div.tooltip { 
 
     position: absolute; 
 
     z-index: 999; 
 
     padding: 10px; 
 
     background: #f4f4f4; 
 
     border: 0px; 
 
     border-radius: 3px; 
 
     pointer-events: none; 
 
     font-size: 11px; 
 
     color: #000; 
 
     line-height: 16px; 
 
     border: 1px solid #d4d4d4; 
 
     } 
 

 
     .legend{ 
 
     margin-left: 300px; 
 
     } 
 
     </style> 
 
     </head> 
 
     <body> 
 
     <div id="chart"></div> 
 
     <div id="toolTip" class="tooltip" style="opacity: 0;"></div> 
 
     <script type="text/javascript"> 
 

 
    var div = d3.select("#toolTip"); 
 

 
      var data = [ ["IP", "count"] 
 
      ["192.168.12.1", "20"], 
 
      ["76.09.45.34", "40"], 
 
      ["34.91.23.76", "80"], 
 
      ["192.168.19.32", "16"], 
 
      ["192.168.10.89", "50"], 
 
      ["192.178.34.07", "18"], 
 
      ["192.168.12.98", "30"]]; 
 

 
    var width = 300, 
 
     height = 300; 
 
    var margin = {top: 15, right: 15, bottom: 20, left: 40}, 
 
     radius = Math.min(width, height)/2 - 10; 
 
    var legendRectSize = 18, 
 
     legendSpacing = 4; 
 
      
 

 
     var color = d3.scale.category20b(); 
 

 
     var arc = d3.svg.arc() 
 
      .outerRadius(radius); 
 
      
 
      var arcOver = d3.svg.arc() 
 
       .outerRadius(radius + 10); 
 

 
     var pie = d3.layout.pie() 
 
      .sort(null) 
 
      .value(function(d) { return d.data.count; }); 
 

 
      var labelArc = d3.svg.arc() 
 
      .outerRadius(radius - 40) 
 
      .innerRadius(radius - 40); 
 
      
 
     var svg = d3.select("#chart").append("svg") 
 
      .datum(data) 
 
      .attr("width", width) 
 
      .attr("height", height) 
 
      .append("g") 
 
      .attr("transform", "translate(" + width/2 + "," + height/2 + ")"); 
 

 
     var arcs = svg.selectAll(".arc") 
 
      .data(pie) 
 
      .enter().append("g") 
 
      .attr("class", "arc"); 
 
      
 
     var arcs2 = svg.selectAll(".arc2") 
 
      .data(pie) 
 
      .enter().append("g") 
 
      .attr("class", "arc2"); 
 

 
      
 
     arcs.append("path") 
 
      .attr("fill", function(d, i) { return color(i); }) 
 
      .on("mouseover", function(d) { 
 
      var htmlMsg=""; 
 
       div.transition()  
 
        .style("opacity",0.9); 
 
        var total = d3.sum(data.map(function(d) {     
 
         return d.count;           
 
        })); 
 
      var percent = Math.round(1000 * d.data.count/total)/10;  
 
       div.html(
 
       "IP :"+ d.data.IP +""+"<br/>"+ 
 
       "Count : " + d.data.count +"<br/>" + 
 
       "Percent: " + percent + '%'+ htmlMsg) 
 
       .style("left", (d3.event.pageX) + "px") 
 
        .style("top", (d3.event.pageY) + "px"); 
 

 
       svg.selectAll("path").sort(function (a, b) { 
 
        if (a != d) return -1;    
 
       else return 1;        
 
       }); 
 
      
 
      var endAngle = d.endAngle + 0.1; 
 
      var startAngle = d.startAngle - 0.1; 
 
      var arcOver = d3.svg.arc() 
 
        .outerRadius(radius + 10).endAngle(endAngle).startAngle(startAngle); 
 
         d3.select(this) 
 
         .attr("stroke","white") 
 
         .transition() 
 
         .ease("bounce") 
 
         .duration(1000) 
 
         .attr("d", arcOver)    
 
         .attr("stroke-width",6); 
 
        }) 
 

 
      .on("mouseout", function(d) { 
 
        div.transition()   
 
        .duration(500)  
 
        .style("opacity", 0); 
 
        d3.select(this).transition()    
 
         .attr("d", arc) 
 
         .attr("stroke","none"); 
 
       }) 
 
       .transition() 
 
       .ease("bounce") 
 
       .duration(2000) 
 
       .attrTween("d", tweenPie); 
 

 
     function tweenPie(b) { 
 
      b.innerRadius = 0; 
 
      var i = d3.interpolate({startAngle: 0, endAngle: 0}, b); 
 
      return function(t) { return arc(i(t)); }; 
 
     } 
 

 
      var k=0; 
 
     arcs2.append("text") 
 
     .transition() 
 
      .ease("elastic") 
 
      .duration(2000) 
 
      .delay(function (d, i) { 
 
      return i * 250; 
 
      }) 
 
       .attr("x","6") 
 
       .attr("dy", ".35em") 
 
       .text(function(d) { if(d.data.count >0){ k = k+1; return d.data.count;} }) 
 
       .attr("transform", function(d) { if (k >1){return "translate(" + labelArc.centroid(d) + ") rotate(" + angle(d) + ")";} else{return "rotate(-360)";} }) 
 
       .attr("font-size", "10px"); 
 
      
 

 
     function type(d) { 
 
      d.count = +d.count; 
 
      return d; 
 
     } 
 
     function angle(d) { 
 
       var a = (d.startAngle + d.endAngle) * 90/Math.PI - 90; 
 
       return a > 90 ? a - 180 : a; 
 
     } 
 

 
    var legend = d3.select("#chart") 
 
     .append("svg") 
 
     .attr("class", "legend") 
 
     .attr("width", radius+50) 
 
     .attr("height", radius * 2) 
 
     .selectAll("g") 
 
     .data(color.domain()) 
 
     .enter() 
 
     .append("g") 
 
     .attr("transform", function(d, i) { return "translate(0," + i * 20 + ")"; }); 
 

 
    legend.append('rect') 
 
     .attr('width', legendRectSize) 
 
     .attr('height', legendRectSize)         
 
     .style('fill', color) 
 
     .style('stroke', color); 
 
     
 
     legend.append('text') 
 
     .attr('x', legendRectSize + legendSpacing) 
 
     .attr('y', legendRectSize - legendSpacing) 
 
     .data(data) 
 
     .text(function(d,i) { return d.IP; }); 
 
     
 
     
 
     </script> 
 
     </body> 
 
    </html>

Я пытаюсь сделать круговую диаграмму с помощью прилагаемого набора данных и я столкнулся ошибка. Как определить параметр d для извлечения данных из переменной «данные» и ее последующих значений «IP» и «count»? Я не знаю, какую ошибку я делаю в своих кодах. Что я должен изменить в своих текущих кодах, чтобы получить круговую диаграмму с текущим форматом данных? Пожалуйста, помогите мне. Я застрял. Условие заключается в том, что я не должен использовать какой-либо файл .csv или .tsv в этом коде для импорта. Спасибо за любую помощь.

+0

Не используйте круговые диаграммы, они являются слугой дьявола. –

ответ

1
  • Одна проблема с массивом данных ... Вы должны удалить первый элемент в нем [Кроме того, вам не хватает «» после пункта. но элемент сам по себе не требуется как его массив].

  • Второй с d.data.count внутри функции пирога ... вам нужно передать его как d [1], поскольку вам нужно построить второй элемент в массиве данных в вашей диаграмме.

Рабочий код ниже:

<!DOCTYPE html> 
 
    <html> 
 
     <head> 
 
     <meta charset="utf-8"> 
 
     <title>Testing Pie Chart</title> 
 
     <script src="https://d3js.org/d3.v3.min.js" charset="utf-8"></script> 
 
     <style type="text/css"> 
 
     #chart { 
 
      margin-top: 100px;            
 
      position: absolute; 
 
      margin-right: 50px; 
 
      margin-left: 50px;           
 
      }                 
 
      .tooltip {               
 
      background: #eee;            
 
      box-shadow: 0 0 5px #999999;          
 
      color: #900C3F;              
 
      display: inline-block;             
 
      font-size: 12px;             
 
      left: 600px;              
 
      padding: 10px;             
 
      position: absolute;            
 
      text-align: center;            
 
      top: 95px;              
 
      width: 150px;              
 
      z-index: 10; 
 
      opacity: 1;             
 
     }                 
 
     rect { 
 
      stroke-width: 2; 
 
     } 
 
     path { 
 
      stroke: #ffffff; 
 
      stroke-width: 0.5; 
 
     } 
 
     div.tooltip { 
 
     position: absolute; 
 
     z-index: 999; 
 
     padding: 10px; 
 
     background: #f4f4f4; 
 
     border: 0px; 
 
     border-radius: 3px; 
 
     pointer-events: none; 
 
     font-size: 11px; 
 
     color: #000; 
 
     line-height: 16px; 
 
     border: 1px solid #d4d4d4; 
 
     } 
 

 
     .legend{ 
 
     margin-left: 300px; 
 
     } 
 
     </style> 
 
     </head> 
 
     <body> 
 
     <div id="chart"></div> 
 
     <div id="toolTip" class="tooltip" style="opacity: 0;"></div> 
 
     <script type="text/javascript"> 
 

 
    var div = d3.select("#toolTip"); 
 

 
      var data = [ 
 
      ["192.168.12.1", "20"], 
 
      ["76.09.45.34", "40"], 
 
      ["34.91.23.76", "80"], 
 
      ["192.168.19.32", "16"], 
 
      ["192.168.10.89", "50"], 
 
      ["192.178.34.07", "18"], 
 
      ["192.168.12.98", "30"]]; 
 

 
    var width = 300, 
 
     height = 300; 
 
    var margin = {top: 15, right: 15, bottom: 20, left: 40}, 
 
     radius = Math.min(width, height)/2 - 10; 
 
    var legendRectSize = 18, 
 
     legendSpacing = 4; 
 
      
 

 
     var color = d3.scale.category20b(); 
 

 
     var arc = d3.svg.arc() 
 
      .outerRadius(radius); 
 
      
 
      var arcOver = d3.svg.arc() 
 
       .outerRadius(radius + 10); 
 

 
     var pie = d3.layout.pie() 
 
      .sort(null) 
 
      .value(function(d) { return d[1]; }); 
 

 
      var labelArc = d3.svg.arc() 
 
      .outerRadius(radius - 40) 
 
      .innerRadius(radius - 40); 
 
      
 
     var svg = d3.select("#chart").append("svg") 
 
      .datum(data) 
 
      .attr("width", width) 
 
      .attr("height", height) 
 
      .append("g") 
 
      .attr("transform", "translate(" + width/2 + "," + height/2 + ")"); 
 

 
     var arcs = svg.selectAll(".arc") 
 
      .data(pie) 
 
      .enter().append("g") 
 
      .attr("class", "arc"); 
 
      
 
     var arcs2 = svg.selectAll(".arc2") 
 
      .data(pie) 
 
      .enter().append("g") 
 
      .attr("class", "arc2"); 
 

 
      
 
     arcs.append("path") 
 
      .attr("fill", function(d, i) { return color(i); }) 
 
      .on("mouseover", function(d) { 
 
      var htmlMsg=""; 
 
       div.transition()  
 
        .style("opacity",0.9); 
 
        var total = d3.sum(data.map(function(d) {     
 
         return d.count;           
 
        })); 
 
      var percent = Math.round(1000 * d.data.count/total)/10;  
 
       div.html(
 
       "IP :"+ d.data.IP +""+"<br/>"+ 
 
       "Count : " + d.data.count +"<br/>" + 
 
       "Percent: " + percent + '%'+ htmlMsg) 
 
       .style("left", (d3.event.pageX) + "px") 
 
        .style("top", (d3.event.pageY) + "px"); 
 

 
       svg.selectAll("path").sort(function (a, b) { 
 
        if (a != d) return -1;    
 
       else return 1;        
 
       }); 
 
      
 
      var endAngle = d.endAngle + 0.1; 
 
      var startAngle = d.startAngle - 0.1; 
 
      var arcOver = d3.svg.arc() 
 
        .outerRadius(radius + 10).endAngle(endAngle).startAngle(startAngle); 
 
         d3.select(this) 
 
         .attr("stroke","white") 
 
         .transition() 
 
         .ease("bounce") 
 
         .duration(1000) 
 
         .attr("d", arcOver)    
 
         .attr("stroke-width",6); 
 
        }) 
 

 
      .on("mouseout", function(d) { 
 
        div.transition()   
 
        .duration(500)  
 
        .style("opacity", 0); 
 
        d3.select(this).transition()    
 
         .attr("d", arc) 
 
         .attr("stroke","none"); 
 
       }) 
 
       .transition() 
 
       .ease("bounce") 
 
       .duration(2000) 
 
       .attrTween("d", tweenPie); 
 

 
     function tweenPie(b) { 
 
      b.innerRadius = 0; 
 
      var i = d3.interpolate({startAngle: 0, endAngle: 0}, b); 
 
      return function(t) { return arc(i(t)); }; 
 
     } 
 

 
      var k=0; 
 
     arcs2.append("text") 
 
     .transition() 
 
      .ease("elastic") 
 
      .duration(2000) 
 
      .delay(function (d, i) { 
 
      return i * 250; 
 
      }) 
 
       .attr("x","6") 
 
       .attr("dy", ".35em") 
 
       .text(function(d) { if(d.data.count >0){ k = k+1; return d.data.count;} }) 
 
       .attr("transform", function(d) { if (k >1){return "translate(" + labelArc.centroid(d) + ") rotate(" + angle(d) + ")";} else{return "rotate(-360)";} }) 
 
       .attr("font-size", "10px"); 
 
      
 

 
     function type(d) { 
 
      d.count = +d.count; 
 
      return d; 
 
     } 
 
     function angle(d) { 
 
       var a = (d.startAngle + d.endAngle) * 90/Math.PI - 90; 
 
       return a > 90 ? a - 180 : a; 
 
     } 
 

 
    var legend = d3.select("#chart") 
 
     .append("svg") 
 
     .attr("class", "legend") 
 
     .attr("width", radius+50) 
 
     .attr("height", radius * 2) 
 
     .selectAll("g") 
 
     .data(color.domain()) 
 
     .enter() 
 
     .append("g") 
 
     .attr("transform", function(d, i) { return "translate(0," + i * 20 + ")"; }); 
 

 
    legend.append('rect') 
 
     .attr('width', legendRectSize) 
 
     .attr('height', legendRectSize)         
 
     .style('fill', color) 
 
     .style('stroke', color); 
 
     
 
     legend.append('text') 
 
     .attr('x', legendRectSize + legendSpacing) 
 
     .attr('y', legendRectSize - legendSpacing) 
 
     .data(data) 
 
     .text(function(d,i) { return d.IP; }); 
 
     
 
     
 
     </script> 
 
     </body> 
 
    </html>

+0

Благодарим вас за ответ. Я нашел решение несколько следующим образом: var data = [ ["192.168.12.1", 20], ["76.09.45.34", 40], ["34.91.23.76", 80], ["192.168. 19,32 ", 16], [" 192.168.10.89 ", 50], [" 192.178.34.07 ", 18], [" 192.168.12.98 ", 30]]; вар данные = data.map (функция (г) { возврата { IP: д [0], Количество: д [1] }; }); –

+0

yea ,, Я предположил, что вы не сможете изменить структуру данных, поскольку вы упомянули о своих ограничениях ... поэтому предоставленное решение было встроено в существующую структуру ... Это может быть сделано с помощью еще дюжины других способов. –

0

Ваш формат ввода данных является неправильным.

Изменение от:

var data = [ ["IP", "count"] 
       ["192.168.12.1", "20"], 
       ["76.09.45.34", "40"], 
       ["34.91.23.76", "80"], 
       ["192.168.19.32", "16"], 
       ["192.168.10.89", "50"], 
       ["192.178.34.07", "18"], 
       ["192.168.12.98", "30"]]; 

в

var data = [ 
      {"IP":"192.168.12.1", "count":"20"}, 
      {"IP":"76.09.45.34", "count":"40"}, 
      {"IP":"34.91.23.76", "count":"80"}, 
      {"IP":"192.168.19.32", "count":"16"}, 
      {"IP":"192.168.10.89", "count":"50"}, 
      {"IP":"192.178.34.07", "count":"18"}, 
      {"IP":"192.168.12.98", "count":"30"} 
      ]; 
+0

Раньше мои данные были похожи на второй, который вы предложили –

+0

Да, данные должны выглядеть как позже, но если вы получаете данные как в quesion из источника, тогда вам нужно настроить и изменить данные, чтобы сделать их в формате как упоминалось ранее. – SiddP

+0

Спасибо SiddP за ваш ответ. Я изменил свой формат данных и смог получить к нему доступ через отображение: var data = [["192.168.12.1", 20], ["76.09.45.34", 40], ["34.91.23.76", 80], [" 192.168.19.32 ", 16], [" 192.168.10.89 ", 50], [" 192.178.34.07 ", 18], [" 192.168.12.98 ", 30]]; var data = data.map (function (d) {return {IP: d [0], count: d [1]};}); –

Смежные вопросы