victory icon indicating copy to clipboard operation
victory copied to clipboard

Avoiding crowding of labels in VictoryLine chart

Open BhargaviAnnadevara opened this issue 10 months ago • 3 comments

Describe the bug When a large dataset is plotted as a line chart, noticing that the tick labels for the data on the chart are overlapping with each other causing it to become obscure. Is there a way to avoid this issue? Can the library decide which labels to display without overlapping? Or, can we provide a set of labels to be displayed, like tickValues maybe?

Victory version Which npm version are you using? N/A

Code This issue can be reproduced in the editable source present in VictoryLine chart with the below snippet:

<VictoryChart
  theme={VictoryTheme.material}
>
  <VictoryLine
    style={{
      data: { stroke: "#c43a31" },
      parent: { border: "1px solid #ccc"}
    }}
    data={[
{
        x: new Date(2023, 6, 1),
        y: 0
    },
    {
        x: new Date(2023, 7, 31),
        y: 17.97
    },
    {
        x: new Date(2023, 8, 1),
        y: 20.55
    },
    {
        x: new Date(2023, 8, 2),
        y: 28.27
    },
    {
        x: new Date(2023, 8, 3),
        y: 9.78
    },
    {
        x: new Date(2023, 8, 4),
        y: 0
    },
    {
        x: new Date(2023, 8, 5),
        y: 9.48
    },
    {
        x: new Date(2023, 8, 6),
        y: 11.38
    },
    {
        x: new Date(2023, 8, 7),
        y: 6.95
    },
    {
        x: new Date(2023, 8, 8),
        y: 21.64
    },
    {
        x: new Date(2023, 8, 9),
        y: 22.3
    },
    {
        x: new Date(2023, 8, 10),
        y: 24.42
    },
    {
        x: new Date(2023, 8, 11),
        y: 6.59
    },
    {
        x: new Date(2023, 8, 12),
        y: 17.09
    },
    {
        x: new Date(2023, 8, 13),
        y: 0
    },
    {
        x: new Date(2023, 8, 14),
        y: 0
    },
    {
        x: new Date(2023, 8, 15),
        y: 7.41
    },
    {
        x: new Date(2023, 8, 16),
        y: 17.5
    },
    {
        x: new Date(2023, 8, 17),
        y: 15.97
    }, {
        x: new Date(2023, 8, 18),
        y: 0.91
    },
    {
        x: new Date(2023, 8, 19),
        y: 8.75
    },
    {
        x: new Date(2023, 8, 20),
        y: 7.39
    },
    {
        x: new Date(2023, 8, 21),
        y: 10.43
    },
    {
        x: new Date(2023, 8, 22),
        y: 16.81
    },
    {
        x: new Date(2023, 8, 23),
        y: 9.26
    },
    {
        x: new Date(2023, 8, 24),
        y: 12.98
    },
    {
        x: new Date(2023, 8, 25),
        y: 0
    },
    {
        x: new Date(2023, 8, 26),
        y: 0
    },
    {
        x: new Date(2023, 8, 27),
        y: 9.26
    },
    {
        x: new Date(2023, 8, 28),
        y: 22.25
    },
    {
        x: new Date(2023, 8, 29),
        y: 19.02
    },
    {
        x: new Date(2023, 8, 30),
        y: 23.65
    },
    {
        x: new Date(2023, 9, 6),
        y: 62.25
    }
    ]}
    labels={({ datum }) => `${datum.y}k`}
  />
</VictoryChart>

Expected behavior Victory should automatically and selectively render a limited set of labels that helps render the chart neatly, or, should accept it as a prop similar to tickValues.

Screenshots image

Additional context Another observation from this example is that some labels like 0k are overlapping with the y-axis line, which shouldn't happen. Although the position of the labels can be adjusted manually, I feel this should be taken care of automatically by the library. image

Any inputs are appreciated!

BhargaviAnnadevara avatar Oct 18 '23 04:10 BhargaviAnnadevara

Is there any approach we can use in the interim? And really this can affect many of the charts, from box plots to scatter charts-

chriszrc avatar May 29 '24 10:05 chriszrc

I can't think of any easy way for Victory to determine which labels to display. A naive implementation that measures for overlap would bias to the first set of labels and end up skipping labels at uneven intervals.

I think we need to see a mockup of what a solution would look like, along with a set of rules for determining the display logic. Or if there is another charting library that offers a similar implementation we can explore how they do it.

carbonrobot avatar May 29 '24 18:05 carbonrobot

As a start, I think just support for a user supplied naive thinning function (maybe which perhaps could also receive the zoom level so thinning could be turned down or off as well) would at least be something. True overlap detection would take more work 😞

chriszrc avatar May 29 '24 18:05 chriszrc