多线有序d3图表 [英] Multi Line Ordinal d3 chart

查看:148
本文介绍了多线有序d3图表的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

如果这看起来像一个重复的D3问题,表示歉意。我花了2天试图找出如何做到这一点。



我试图创建一个多轴线图,其中x轴作为序数刻度,y轴作为正常线性刻度。我看到的一切都涉及到使用时间和线性尺度组合,我似乎不能转换的例子,使他们的工作,我想要什么。



以下是我的示例JSON数据:

  var data = 
[
{Supplier:Supplier1,Half:2013 2H,Value:99.86047786},
{Supplier:Supplier1 2013,价值:93.86047786},
{Supplier:Supplier1,Half:2012 2H,Value:98.86047786} Supplier,Half:2012 1H,Value:96.86047786},
{Supplier:Supplier2,Half:2013 2H,Value:97.86047786} $ b {Supplier:Supplier2,Half:2013 1H,Value:91.86047786},
{Supplier:Supplier2 Value:93.86047786},
{Supplier:Supplier2,Half:2012 1H,Value:94.86047786},
{Supplier:Supplier3 :2013 2H,Value:92.86047786},
{Supplier:Supplier3,Half:2013 1H,Value:91.86047786} :Supplier3,Half:2012 2H,Value:88.86047786},
{Supplier:Supplier3,Half:2012 1H,Value:87.86047786} ,
{Supplier:Supplier4,Half:2013 2H,Value:88.86047786},
{Supplier:Supplier4,Half: ,Value:86.86047786},
{Supplier:Supplier4,Half:2012 2H,Value:83.86047786} ,Half:2012 1H,Value:81.86047786},
];

这里是我试图创建图表的地方:

  //宽度和高度
var margin = {top:20,right:20,bottom:30,left:40}
var width = 600 - margin.left - margin.right;
var height = 500-margin.top -margin.bottom;
var w = width;
var h = height;

var xScale = d3.scale.ordinal()
.domain(data.map(function(d){return d.Half;}))
.rangeRoundBands margin.left,width],0.05);

var xAxis = d3.svg.axis()。scale(xScale).orient(bottom)。tickSize(height - margin.bottom);

var yScale = d3.scale.linear()
.domain([0,d3.max(data,function(d){return d.Value;})]) $ b .range([h,0]);


//创建SVG元素
var svg = d3.select(body)
.append(svg)
.attr width,w)
.attr(height,h);


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

data = d3.nest()。key(function(d){return d.Supplier;})。

我不知道的是如何创建4个不同的供应商 半日期桶作为X坐标,值作为Y坐标。理想情况下,我会在图表上有4条线,每个供应商一个,每个都有不同的颜色。



任何帮助/指导将非常感谢。

解决方案

这应该让你开始: http: //jsfiddle.net/hU6r6/



正确设置xScale的域



  //查找所有唯一的x轴值
//幸运的是,按字母顺序排序的值也会产生
//正确的顺序
var xValues = d3.set(data.map(function(d){return d.Half;}))。values()。sort();

//仅使用xAxis的唯一值设置域
var xScale = d3.scale.ordinal()
.domain(xValues)
/ /设置rangePoints而不是rangeBands
.rangePoints([0,width],0.5);



附加与数据绑定的DOM元素



  //这是你创建的数据
var supplierData = d3.nest()。key(function(d){return d .Supplier;})。entries(data);

//创建一个线对象,它将为路径设置'd'属性
var line = d3.svg.line()
.interpolate(linear)
.x(function(d){return xScale(d.Half);})
.y(function(d){return yScale(d.Value);});

//选择不同的颜色
var colors = d3.scale.category10();

//图表容器
var gLines = svg.selectAll('g.chart-area')。data([supplierData]);

gLines.enter()
.append('g')
.classed('chart-area',true)
.attr 'translate('+ margin.left +','+ margin.top +));

//我们的'路径'是行
var lines = gLines.selectAll('path.supplier')。data(function(d){return d;});

//我们的'路径'是行
lines.enter()
.append('path')
.classed('supplier',true )
//数据格式为{key:'SupplierX',values:[...]}
.attr('d',function(d){return line(d.values );})
.attr('fill','none')
.attr('stroke',function(d,i){return colors(i);})



后续步骤



如果您遵循教程,那么您将看到jsFiddle仅实现了 enter 阶段的数据。也许这足够你的目的和更新退出阶段不需要。



除此之外,这个图形仍然是裸眼的,缺少适当的y轴和颜色的标签等。 / p>

Apologies if this seems like a duplicate D3 question. I've spent 2 days trying to figure out how to do this.

I'm trying to create a multi-line chart with the x-axis as an ordinal scale, and the y axis as a normal linear scale. Everything I've seen involves using time and linear scales combined and I can't seem to convert the examples to make them work how I want.

Here's my sample JSON data:

var data = 
[
    { "Supplier": "Supplier1", "Half": "2013 2H", "Value": 99.86047786 },
    { "Supplier": "Supplier1", "Half": "2013 1H", "Value": 93.86047786 },
    { "Supplier": "Supplier1", "Half": "2012 2H", "Value": 98.86047786 },
    { "Supplier": "Supplier1", "Half": "2012 1H", "Value": 96.86047786 },
    { "Supplier": "Supplier2", "Half": "2013 2H", "Value": 97.86047786 },
    { "Supplier": "Supplier2", "Half": "2013 1H",  "Value": 91.86047786 },
    { "Supplier": "Supplier2", "Half": "2012 2H","Value": 93.86047786 },
    { "Supplier": "Supplier2", "Half": "2012 1H", "Value": 94.86047786 },
    { "Supplier": "Supplier3", "Half": "2013 2H", "Value": 92.86047786 },
    { "Supplier": "Supplier3", "Half": "2013 1H", "Value": 91.86047786 },
    { "Supplier": "Supplier3", "Half": "2012 2H", "Value": 88.86047786 },
    { "Supplier": "Supplier3", "Half": "2012 1H", "Value": 87.86047786 },   
    { "Supplier": "Supplier4", "Half": "2013 2H", "Value": 88.86047786 },
    { "Supplier": "Supplier4", "Half": "2013 1H", "Value": 86.86047786 },
    { "Supplier": "Supplier4", "Half": "2012 2H", "Value": 83.86047786 },
    { "Supplier": "Supplier4", "Half": "2012 1H", "Value": 81.86047786 },   
];

And here's where I've gotten so far in trying to create the chart:

//Width and height
var margin = {top: 20, right: 20, bottom: 30, left: 40};           
var width = 600 - margin.left - margin.right;
var height= 500-margin.top -margin.bottom;
var w = width;
var h = height;

var xScale = d3.scale.ordinal()
    .domain(data.map(function (d) {return d.Half; }))
    .rangeRoundBands([margin.left, width], 0.05);

var xAxis = d3.svg.axis().scale(xScale).orient("bottom").tickSize(height - margin.bottom);

var yScale = d3.scale.linear()
    .domain([0, d3.max(data, function(d) {return d.Value; })])
    .range([h,0]);


//Create SVG element
var svg = d3.select("body")
    .append("svg")
    .attr("width", w)
    .attr("height", h);


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

data = d3.nest().key(function(d) { return d.Supplier; }).entries(data); 

What I can't figure out is how to create the lines for the 4 different "suppliers" with the "Half" date buckets as the X coordinates and the "Value" as the Y coordinates. Ideally I would have 4 lines on the graph, one for each supplier, each with a different color.

Any help/direction would be greatly appreciated.

解决方案

This should get you started: http://jsfiddle.net/hU6r6/

Setting the domain of the xScale properly

// Find all the unique x-axis values
// Fortunately, alphabetical sorting of the values also yields
// the correct order
var xValues = d3.set(data.map(function (d) { return d.Half; })).values().sort();

// Set up the domain using only the unique values for the xAxis
var xScale = d3.scale.ordinal()
    .domain(xValues)
    // Setting the rangePoints instead of rangeBands
    .rangePoints([0, width], 0.5);

Append DOM elements tied to the data

// This is the same data as you have created
var supplierData = d3.nest().key(function(d) { return d.Supplier; }).entries(data); 

// Create a line object which will set the 'd' attributes for the paths
var line = d3.svg.line()
                  .interpolate("linear")
                  .x(function (d) { return xScale(d.Half); })
                  .y(function (d) { return yScale(d.Value); });

// To choose different colors
var colors = d3.scale.category10();

// The chart container
var gLines = svg.selectAll('g.chart-area').data([ supplierData ]);

gLines.enter()
  .append('g')
  .classed('chart-area', true)
  .attr('transform', 'translate(' + margin.left + ',' + margin.top + ")");

// Our 'paths' which are the lines
var lines = gLines.selectAll('path.supplier').data(function (d) { return d; });

// Our 'paths' which are the lines
lines.enter()
  .append('path')
  .classed('supplier', true)
  // The data is of the form { key: 'SupplierX', values: [ ... ] }
  .attr('d', function (d) { return line(d.values); })
  .attr('fill', 'none')
  .attr('stroke', function (d, i) { return colors(i); })

Next steps

If you followed the tutorial, then you will see that the jsFiddle only implements the enter phase of the data. Perhaps that is enough for your purposes and update and exit phases are not needed. Nevertheless, you should follow the tutorial completely.

Apart from that,this graph is still bare-bone and lacks proper y-axis and labels for the colors, etc.

这篇关于多线有序d3图表的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆