Minor Gridlines

Hi,

Is it possible to include minor gridlines in a basic line graph? I need whole numbers as the major gridlines with minor lines every 0.2 but can’t see where or how this can be done.

Thanks

Hi @TDCT,

Have a look at the gridlines documentation: Grid lines | QuickChart and also the relevant Chart.js docs that are linked from this documentation.

The easiest way is to set stepSize manually, disable autoSkip, and conditionally display the tick label.

Here’s an example with Chart.js v3:

  options: {
    scales: {
      y: {
        ticks: {
          autoSkip: false,
          stepSize: 5,
          callback: function (val, index) {
            return val % 20 === 0 ? val : '';
          },
        },
      },
    },
  },

The Chart.js v2 implementation is quite similar:

  options: {
    scales: {
      yAxes: [{
        ticks: {
          autoSkip: false,
          stepSize: 5,
          callback: function (val, index) {
            return val % 20 === 0 ? val : '';
          },
        },
      }],
    },
  },

example in chart editor

Hi Ian,

Thank you for this. I have tried to include this under ‘ticks’ but all that is happening is my labels disappear. What have I done wrong?

      ticks: {
        display: true,
        max: 20,
        stepSize: 0.5,
        fontSize: 7,
        autoSkip: false,
        stepSize: 1,
        callback: function (val, index) {
          return val % 20 === 0 ? val : '';
        },
      },
        "distribution": "linear",
        "gridLines": {
        "display": true,
        "color": "rgba(0, 0, 0, 0.5)",
        "borderDash": [
          0,
          0
        ],
      },
    },
  ],

Apologies in advance for being a bit rubbish at this.

Try this :slight_smile:

Set stepSize to 0.2, and adjust callback to display only the whole numbers:

          ticks: {
            display: true,
            max: 20,
            stepSize: 0.2,
            fontSize: 7,
            autoSkip: false,
            callback: function (val, index) {
              return val % 1 === 0 ? val : '';
            },
          },
          gridLines: {
            display: true,
            color: 'rgba(0, 0, 0, 0.5)',
            borderDash: [0, 0],
          },

Here’s an example

Hi Ian,

Half way there :slight_smile:

The labels appear in whole numbers but still no minor grid lines. If I put this into any other graph it seems to work fine, but just not in the one I need to use. This is the whole thing…

{
  type: "line",
  data: {
    labels: [1, "", "", "", "", "", "", "", "", "", "", "", 2, "", "", "", "", "", "",3, "", "", "", "", 4, "", "", "", "", "", "", 6, "", "", "", "", 8, "", "", "", "", "", "",12, "", "", "", "", 16, "", "", "", "", "", "",24, "", "", "", "", 32, "", "", "", "", "", "", 48, "", "", "", "", 64, "", "", "", "", "", "", 96],
    datasets: [
      {
        label: "Change In Penetration Data Points",
        backgroundColor: "rgb(255, 99, 132, 0.5)",
        borderColor: "rgb(255, 99, 132, 0.5)",
        data: [', {{changeInPenetrationAnswers}}, '],
        fill: false,
        pointRadius: 5,
        showLine: false,
      }, {
        label: "5mm Green Line Marker",
        borderColor: "rgba(0, 255, 0, 0.3)",
        data: [5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5],
        fill: false,
        pointRadius: 0,
      }       
    ],
  },
  options: {
    title: {
      display: false,
      text: "            MCV Plot Exercise",
    },
    legend: {
      display: false,
    },
    elements: {
      point: {
        pointStyle: "crossRot",
      },
    },
scales: {
      xAxes: [
        {
          id: "x1",
          display: true,
          position: "top",
          scaleLabel: {
            display: true,
            labelString: "No of blows",
          },
          ticks: {
            display: true,
            fontSize: 7,
            stepSize: 1,
          },
            "gridLines": {
            "display": false,
            "color": "rgba(0, 0, 0, 0.3)",
            "borderDash": [
              0,
              0
            ],
          },
        }, {
          id: "x2",
          display: true,
          position: "bottom",
          labels: [0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18, 19, 20],
          scaleLabel: {
            display: true,
            labelString: "Moisture condition value",
          },
           ticks: {
            display: true,
            max: 20,
            stepSize: 0.2,
            fontSize: 7,
            autoSkip: false,
            callback: function (val, index) {
              return val % 1 === 0? val : '';
            },
          },
          gridLines: {
            display: true,
            color: 'rgba(0, 0, 0, 0.5)',
            borderDash: [0, 0],
          },
        },
      ],
      yAxes: [
        {
          display: true,
          scaleLabel: {
            display: true,
            labelString: "Change in penetration, mm",
          },
          ticks: {
            stepSize: 3,
            fontSize: 7,
          },
        },
      ],
    },    
  },
}

I know its a bit messy but it was the only way I could make the top scale resemble anywhere near what I needed (it’s supposed to be a logarithmic scale on the top!)

Any ideas why this is not working as expected?

Thanks

I think we’re getting there… your use case is a bit strange, so here’s what I did:

  1. Removed labels from the bottom X axis. This was overriding your other gridline settings.
  2. Adjusted the callback to compute the tick label based on index.
  3. Upgraded your chart to Chart.js v3 (make sure to set version=3 in your request)

You have a little under 80 datapoints in your data series, so at 0.2 per gridline you have just under 16 major ticks.

Link to modified example

Hi Ian,

How can I make the bottom scale go up to 20 without the labels?

My bottom scale needs to have 20 points, each of which need to line up with specific points on the top scale… hence all the forced blanks to get the correct spacings.

Thanks