D3.js时间刻度刻度线 - 仅限年份和月份 - 自定义时间格式

时间:2015-12-11 19:41:42

标签: javascript d3.js scale axis

我正在尝试在x轴上创建一个带有时间刻度的 zoomable 图表。





默认行为
 with像这样的xScale:




  var x = d3.time.scale()
 .domain([getDate(minDate),getDate(maxDate)])
 .range([0,width]);
  




和xAx是这样的:


&#xA ;
  var xAxis = d3.svg.axis()
 .scale(x);
  




几乎就是我所追求的。

&#xA;&#xA; <但是我希望有一个显示年份的自定义时间格式,而不是显示月份的名称,只显示一个刻度线,没有文本(并且可能在这些刻度上添加一个类),同时仍然保留轴上缩放的默认行为。

&#xA;&#xA;

非常感谢任何帮助。

&#xA;&#xA;

请参阅JSfiddle

&#xA;&#xA;

编辑:我想 Lars'在这里回答将是一个很好的方法,只要它可以应用于可缩放的图表。有什么新鲜的想法吗?

&#xA;

2 个答案:

答案 0 :(得分:3)

这可能有用。要显示年份,而不是显示月份的名称,只显示一个刻度线,而不显示文本:

var timeAxis = d3.svg.axis()
        .scale(timeScale)
        .orient('bottom')
        .ticks(d3.time.years, 1)//should display 1 year intervals
        .tickFormat(d3.time.format('%Y'))//%Y-for year boundaries, such as 2011
        .tickSubdivide(12);//subdivide 12 months in a year

资源:

  1. d3.js主要次要标记样式(http://bl.ocks.org/vjpgo/4689130
  2. scale.ticks和scale.tickFormat() (https://github.com/mbostock/d3/wiki/Time-Intervals#year
  3. 示例代码,每两个小时显示一次勾号,并将其格式化为仅显示小时和上午/下午:

    var timeAxis = d3.svg.axis()
            .scale(timeScale)
            .orient('bottom')
            .ticks(d3.time.hours, 2)
            .tickFormat(d3.time.format('%I%p'));
    

答案 1 :(得分:0)

我最终写了一个小功能来检查缩放级别并相应地设置轴的刻度数。

function calcTickAmount() {
  if (d3.event.scale > 15) {
    return 3
  } else {
    return 10;
  }
}

然后将在更新函数中调用此函数

function draw() {
  xAxis.ticks(calcTickAmount());
  axes.call(xAxis);
}

// Config SVG
var width = 500,
  height = 300,
  minDate = '1860',
  maxDate = '1958';

// Draw SVG element
var svgSelect = d3.select('div.tl').append('svg');

// Translate SVG G to accomodate margin
var translateGroupSelect = svgSelect
  .attr('width', width)
  .attr('height', height)
  .append('g');

// Define d3 xScale
var x = d3.time.scale()
  .domain([new Date(minDate), new Date(maxDate)])
  .range([0, width]);

// Define main d3 xAxis
var xAxis = d3.svg.axis()
  .scale(x)
  .ticks(10);

// Draw axes
var axes = translateGroupSelect.append("g")
  .attr("class", "x axis")
  .attr("transform", "translate(0," + 0 + ")")
  .call(xAxis);

// Define zoom
var zoom = d3.behavior.zoom()
  .x(x)
  .scaleExtent([1, 32])
  .center([width / 2, height / 2])
  .size([width, height])
  .on("zoom", draw);


// Apply zoom behavior to SVG element
svgSelect.call(zoom);


// Repetitive drawing stuff on every zoom event
function draw() {
  xAxis.ticks(calcTickAmount());
  axes.call(xAxis);
}

function calcTickAmount() {
  if (d3.event.scale > 15) {
    return 3
  } else {
    return 10;
  }
}
<script src="https://cdnjs.cloudflare.com/ajax/libs/d3/3.5.17/d3.min.js"></script>
<div class="tl">
</div>

Updated Fiddle