D3.js:将时间轴添加到具有负值的条形图

时间:2016-09-28 01:51:04

标签: javascript d3.js

我有一个条形图,其中x轴是时间。条形图支持负值,下面有一个额外的轴用于显示x值。但是,正在显示数值而不是日期。

以下是代码:

data = [{"value": 10, "date": "20150824"},
        {"value": -21, "date": "20150924"},
        {"value": 7, "date": "20151024"},
        {"value": 12, "date": "20151124"},
        {"value": 33, "date": "20151224"},
        {"value": -10, "date": "20160124"},
        {"value": -10, "date": "20160224"},
        {"value": -2, "date": "20160324"},
        {"value": 17, "date": "20160424"},
        {"value": -4, "date": "20160524"},
        {"value": 6, "date": "20160864"},
        {"value": 23, "date": "20160724"},
        {"value": 13, "date": "20160824"},
        {"value": -19, "date": "20160924"},
        {"value": -8, "date": "20161024"},
        {"value": -2, "date": "20161124"},
        {"value": 12, "date": "20161224"}
    ]

var margin = {top: 30, right: 10, bottom: 10, left: 30},
    width = 960 - margin.left - margin.right,
    height = 600 - margin.top - margin.bottom;

var y0 = Math.max(Math.abs(d3.min(data, function(d) { return +d.value; })), Math.abs(d3.max(data, function(d) { return +d.value; })));

var parseDate = d3.time.format("%Y%m%d").parse;

 data.forEach(function(d) {
        d.date = parseDate(d.date);
  });


var y = d3.scale.linear()
    .domain([-y0, y0])
    .range([height,0])
    .nice();

var x = d3.scale.ordinal()
    .domain(d3.range(data.length))
    .rangeRoundBands([0, width], .2);


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

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

var svg = d3.select("body").append("svg")
    .attr("width", width + margin.left + margin.right)
    .attr("height", height + margin.top + margin.bottom + 100)
  .append("g")
    .attr("transform", "translate(" + margin.left + "," + margin.top + ")");

   bars = svg.selectAll(".bar")
    .data(data);

 bars.enter().append("rect")
    .attr("class", function(d) { return d.value < 0 ? "bar negative" : "bar positive"; })
    .attr("x", function(d, i) { return x(i); })
    .attr("width", x.rangeBand())
    .attr("fill", "#A9A9A9"});

 bars.transition()
      .duration(1000)
      .delay(function (d, i) {
        return i * 40;
      })
    .attr("y", function(d) { return y(Math.max(0, d.value)); })
    .attr("height", function(d) {return Math.abs(y(d.value) - y(0)); });

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



svg.append("g")
    .attr("class", "y axis")
  .append("line")
    .attr("y1", y(0))
    .attr("y2", y(0))
    .attr("x1", 0)
    .attr("x2", width);

svg.append("g")
      .attr("class", "xx axis")
      .attr("transform", "translate(0," + parseInt(height+ 30   ).toString() + ")")
      .call(xAxis)
    .selectAll("text")
      .style("text-anchor", "end")
      .attr("dx", "-.8em")
      .attr("dy", "-.55em")
      .attr("transform", "rotate(-90)" )

 bars
    .exit().remove();

这不起作用。我已经做了一些相当数量的谷歌搜索,但我仍然无法在这里解决问题。

如果有人可以解释代码有什么问题以及如何解决它,那就太好了。

1 个答案:

答案 0 :(得分:3)

将d3.time.scale()用于时间轴

var x =  d3.time.scale()  
       .domain(d3.extent(data, function(d){  
               return d.date;  
       }))  
       .range([0, width]);  

var xAxis = d3.svg.axis()  
          .scale(x)  
          .tickFormat(d3.time.format("%Y%m%d"))  
          .orient("bottom");