plouc / nivo

nivo provides a rich set of dataviz components, built on top of the awesome d3 and React libraries
https://nivo.rocks
MIT License
13.19k stars 1.03k forks source link

Bar chart X-axis is typed as a 'BandScale' and as such does not support custom ticks #1395

Closed jamesdh closed 3 years ago

jamesdh commented 3 years ago

Describe/explain the bug Bar charts have the typing indexScale: BandScale and use scaleBand() for generating their X-axis scale. Scale bands do not support ticks and as such, every bar must have a tick. This falls down for scenarios where we'd like to use a large number of bars on a timeline of days, but only want to show a tick for each week or month. Otherwise it looks obnoxious. This also means that configuring the x-axis doesn't follow the guidelines as shown at https://nivo.rocks/guides/axes

Screen Shot 2021-01-17 at 3 30 16 PM
jamesdh commented 3 years ago

It's also a bit confusing that the BandScale is wholly implemented within the Bars package, but it's typings are within the Scales package. Meanwhile, all the other scale types are defined within the Scales package. It appears this could use a bit of cleanup.

jamesdh commented 3 years ago

For anyone interested, a workaround is to define your own timescale, and then use a custom axis format function to only print the tick label if the value is contained within the timescale ticks, e.g.

const formatter = timeFormat('%d %b')
const timeScaleTicks: string[] = useMemo(() => {
    const scale = scaleTime().domain([from, to])
    const ticks = scale.ticks(10)
    return ticks.map(tick => (
      formatter(tick)
    ))
  }
})
axisBottom={{
  tickSize: 5,
  tickPadding: 5,
  tickRotation: 45,
  format: (val) => { 
      return timeScaleTicks.includes(formatter(new Date(val))) ? formatter(new Date(val)) : '' 
  } 
}}

It will still end up printing the tick lines, but it still looks much less cluttered:

Screen Shot 2021-01-18 at 9 47 15 AM
stale[bot] commented 3 years ago

This issue has been automatically marked as stale. If this issue is still affecting you, please leave any comment (for example, "bump"), and we'll keep it open. We are sorry that we haven't been able to prioritize it yet. If you have any new additional information, please include it with your comment!

stale[bot] commented 3 years ago

Closing this issue after a prolonged period of inactivity. If this issue is still present in the latest release, please create a new issue with up-to-date information. Thank you!

sebastienbarre commented 1 year ago

Thanks @jamesdh -- it's too bad the Bar chart still doesn't support time scale. Could you please clarify where timeFormat and scaleTime are coming/imported from? Thank you.

Nanak360 commented 1 year ago

timeFormat is being imported from d3-time-format, like import { timeFormat } from 'd3-time-format' and scaleTime like import { scaleTime } from 'd3-scale'