d3 autospace overlapping tick labels

一曲冷凌霜 提交于 2020-01-01 04:35:08

问题


Is there a way in d3 to not draw overlapping tick labels? For example, if I have a bar chart, but the bars are only 5 pixels wide and the labels are 10 pixels wide, I end up with a cluttered mess. I'm currently working on an implementation to only draw the labels when they do not overlap. I can't find any existing way to do that, but wasn't sure if anyone else had dealt with this problem.


回答1:


There is no way of doing this automatically in D3. You can set the number of ticks or the tick values explicitly (see the documentation), but you'll have to figure out the respective numbers/values yourself. Another option would be to rotate the labels such that there is less chance of them overlapping.

Alternatively, like suggested in the other answer, you could try using a force layout to place the labels. To clarify, you would use the force layout on the labels only -- this is completely independent of the type of chart. I have done this in this example, which is slightly more relevant than the one linked in the other answer.

Note that if you go with the force layout solution, you don't have to animate the position of the labels. You could simply compute the force layout until it converges and then plot the labels.




回答2:


I've had a similar problem with multiple (sub-)axis, where the last tick overlaps my vertical axis in some situations (depending on the screen width), so I've just wrote a little function that compares the position of the end of the text label with the position of the next axis. This code is very specific to my use case, but could adapted easily to your needs:

var $svg = $('#svg');

// get the last tick of each of my sub-axis
$('.tick-axis').find('.tick:last-of-type').each(function() {

  // get position of the end of this text field
  var endOfTextField = $(this).offset().left + $(this).find('text').width();

  // get the next vertical axis
  var $nextAxis = $('line[data-axis="' + $(this).closest('.tick-axis').attr('data-axis') + '"]');

  // there is no axis on the very right, so just use the svg width
  var positionOfAxis = ($nextAxis.length > 0) ? $nextAxis.offset().left : $svg.offset().left + $svg.width();

  // hide the ugly ones!
  if (endOfTextField > positionOfAxis) {
    $(this).attr('class', 'tick hide');
  }

});

The ticks with color: aqua are the hidden ones:




回答3:


could you try something mentioned in this thread, specifically this example so that the labels are pushed up/down/out of the way so that they all may be fitted in. This requires using a seperate forces, one for the nodes and another for the labels themselves.



来源:https://stackoverflow.com/questions/17797437/d3-autospace-overlapping-tick-labels

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!