2015-11-17 109 views
0

我剛剛開始學習上週的d3.js,並試圖創建散點圖。我期待着y軸上的t1,t2,t3,t4,t5。而x-anxis是從1到質量的最大值。但是在運行下面的代碼後,看起來點的位置不正確。其中兩個甚至超出了y aixs的範圍。我無法弄清楚爲什麼。任何人都可以幫助修復代碼並解釋原因嗎?提前致謝!散點圖中點的位置d3.js

<!DOCTYPE html> 
<html> 
    <head> 
    <meta charset="utf-8"> 
    <title>Dot Plot</title> 
    <style> 
    .axis path, 
    .axis line{ 
     fill: none; 
     stroke: #000; 
     shape-rendering: crishpEdges; 
     }  
    .circles { opacity: .7; } 
    </style> 
    </head> 
    <body> 
    <h1 style = "text-align:center;">Dot Plot Example</h1>  
    </body> 

    <body> 

    <script src="http://d3js.org/d3.v3.min.js"></script> 
    <script> 
    var data = [ 
    {"custid": 1, "Type": "t1","quality": 7}, 
    {"custid": 2, "Type": "t2", "quality": 2}, 
    {"custid": 3, "Type": "t3", "quality": 3}, 
    {"custid": 4, "Type": "t4", "quality": 7}, 
    {"custid": 5, "Type": "t5", "quality": 2} 
    ]; 

     data.forEach(function(d){ 
     d.quality = +d.quality; 
     d.Type = d.Type; 
     return console.log(data); 
    }) 

    var margin = {t:30, r:20, b:40, l:40 }, 
     w = 600 - margin.l - margin.r, 
     h = 500 - margin.t - margin.b; 

    var color = d3.scale.category20c(); 

    var x = d3.scale.linear() 
     .range([0, w]) 
     .domain([0,d3.max(data, function(d){return d.quality})]); 

    var y = d3.scale.ordinal() 
     .range([h,0]) 
     .domain(data.map(function(d){return d.Type;}));  

    var xAxis = d3.svg.axis() 
     .scale(x) 
     .orient("bottom") 
     .ticks(8); 

    var yAxis = d3.svg.axis() 
     .scale(y) 
     .orient("left") 
     .ticks(6); 

    var svg = d3.select("body") 
     .append("svg") 
     .attr("width", w + margin.l + margin.r) 
     .attr("height", h + margin.t + margin.b) 
     .style("margin-left", "auto") 
     .style("margin-right", "auto") 
     .style("display", "block") 
     .append("g") 
     .attr("transform", "translate(" + margin.l + "," + margin.t + ")");  

    svg.selectAll("circle") 
     .data(data) 
     .enter() 
     .append("circle") 
     .attr("class", "circles") 
     .attr({ 
     cx: function(d) { return x(d.quality); }, 
     cy: function(d) { return y(d.Type); }, 
     r: 8 
     }) 
     .style("fill", function(d){return color(d.Type);}); 

    svg.append("g") 
     .attr("class", "x axis") 
     .attr("transform", "translate(" + margin.l + "," + (h - 20 + margin.t) + ")") 
     .call(xAxis); 

    svg.append("g") 
     .attr("class", "y axis") 
     .attr("transform", "translate(" + margin.l + "," + margin.t + ")") 
     .call(yAxis); 
    </script> 
    </body> 
</html> 
+1

位置不正確?你期望什麼? –

回答

1

有兩個問題。首先,按照您使用它的序號比例,預計域和範圍元素之間的1:1映射。也就是說,對於給出.range()的數組中的每個元素,在.domain()的數組中需要有一個相應的元素。在你的情況下,你有5個域值,但只有2個範圍值。在這樣的情況下,你應該使用.rangeRoundPoints(),它會自動細分區間取決於值的域數量:

var y = d3.scale.ordinal() 
    .rangeRoundPoints([h,0]) 
    .domain(data.map(function(d){return d.Type;})); 

其次,你與裕翻譯爲軸線的容器,但不要不包括那些積分。您只需要

svg.append("g") 
    .attr("class", "x axis") 
    .attr("transform", "translate(0," + h + ")") 
    .call(xAxis); 

svg.append("g") 
    .attr("class", "y axis") 
    .call(yAxis); 

完整示例here

+0

非常感謝!如何將t1的勾號在y軸上移動一點,因爲它位於x軸上。 – yxz122930

+0

您可以更改比例的範圍:https://jsfiddle.net/vny7p798/1/ –