TheGlasses
TheGlasses

Reputation: 63

chartjs 4.4 : not able to plot 2 time series in 1 graph

I have an issue with plotting 2 lines in 1 graph using chartjs: I get 2 graphs with 1 line in stead of 1 graph with 2 lines, and I think I made a very simpe error, but I can't find it. I have spend hours on it.

When I align the timestamps (with the same intervals), all works fine. But the timestamps have different intervals.

Here is the code:

<html>
<div>
  <canvas id="myChart"></canvas>
</div>

<script src="https://cdn.jsdelivr.net/npm/chart.js"></script>

<script>

new Chart("myChart", {
    type: 'line',
    data: {
        datasets: [{
            data: [{x:'2021-11-06 23:39:30',y:1900},{x:'2022-11-07 01:00:28',y:2000},{x:'2023-11-08 09:00:28',y:1800}],
            borderColor: "red",
            label:"John",
            fill: false
        },{
            data: [{x:'2021-11-06 21:39:30',y:1800},{x:'2022-11-07 00:10:28',y:1650},{x:'2023-11-08 12:00:28',y:1900}],
            borderColor: "blue",
            label:"Laura",
            fill: false         
        }],
    },

    options: {
        scales: {
            x: {    
            },
            y: {
                min: 1000,      
                max: 2400, 
            }
        }
    }   
});
</script>
</html>

This is what I get

2 graphs

This is what I want:

Desired graph

Upvotes: 2

Views: 54

Answers (1)

winner_joiner
winner_joiner

Reputation: 14870

Well the easy / fast solution for me would be to use the "date-module / adapter", since your x- values are dates. Just add the needed libs and set the type for x to for example time, and your string x-values should be all converted to correct "datetimes" and be displayed on the same axis / points. (first config in the demo below)

A short demo:

the demo also includes an alternative solution the x - values are stripped from the time part and than match with the help of the labels properties. The later is not very "nice" from a technical standpoint, but it works and doesn't need some fancy library. (It was just included, as an alternative solution/approach )

const config = {
  type: 'line',
  data: {
    datasets: [
      {
        data: [
          { x: '2021-11-06 23:39:30', y: 1900 },
          { x: '2022-11-07 01:00:28', y: 2000 },
          { x: '2023-11-08 09:00:28', y: 1800 },
        ],
        borderColor: 'red',
        label: 'John',
        fill: false,
      },
      {
        data: [
          { x: '2021-11-06 21:39:30', y: 1800 },
          { x: '2022-11-07 00:10:28', y: 1650 },
          { x: '2023-11-08 12:00:28', y: 1900 },
        ],
        borderColor: 'blue',
        label: 'Laura',
        fill: false,
      },
    ],
  },

  options: {
    scales: {
      x: { type: 'time' },
      y: {
        min: 1000,
        max: 2400,
      },
    },
  },
};

var data1 = [
  { x: '2021-11-06 23:39:30', y: 1900 },
  { x: '2022-11-07 01:00:28', y: 2000 },
  { x: '2023-11-08 09:00:28', y: 1800 },
].map( entry => {
  entry.x = entry.x.split(' ')[0]
  return entry;
});

var data2 =  [
  { x: '2021-11-06 21:39:30', y: 1800 },
  { x: '2022-11-07 00:10:28', y: 1650 },
  { x: '2023-11-08 12:00:28', y: 1900 },
].map( entry => {
  entry.x = entry.x.split(' ')[0]
  return entry;
});

var labels = Array.from(new Set(data1.concat(data2).map( entry => entry.x).sort()))

const config2 = {
  type: 'line',
  data: {
  labels: labels,
    datasets: [
      {
        data: data1,
        borderColor: 'red',
        label: 'John',
                 parsing: {
        yAxisKey: 'y'
      }
      },
      {
        data: data2,
        borderColor: 'blue',
        label: 'Laura',
         parsing: {
        yAxisKey: 'y'
      }
      },
    ],
  },
  options: {
    scales: {
        y: {
        min: 1000,
        max: 2400,
      },
    },
  },
};

var myChart = new Chart(document.getElementById('chart'), config);

var myChart2 = new Chart(document.getElementById('chart2'), config2);
<script src="https://cdn.jsdelivr.net/npm/chart.js"></script>
<script src="https://cdn.jsdelivr.net/npm/moment@^2"></script>
<script src="https://cdn.jsdelivr.net/npm/chartjs-adapter-moment@^1"></script>

<div class="chart" style="height:184px; width:350px;">
    <canvas  id="chart" ></canvas>
</div>

<div class="chart" style="height:184px; width:350px;">
    <canvas  id="chart2" ></canvas>
</div>

Info: Just for clarity, the chartjs lib doesn't recognize string-datetime values without an external library / adapter (link to documentation)

Upvotes: 1

Related Questions