Mormoran
Mormoran

Reputation: 791

Chart.js get array of currently visible points on graph

Using Chart.js with zoom/pan enabled, I am trying to write a function to export only what is visible on the canvas to CSV.

But I cannot figure out how to get only the visible datapoints after the user zooms/pans.

I know I can just look at myChart.data.datasets but that would fetch all the points in the chart, not just the currently visible ones.

var config = {
    type: 'line',
    data: {
        // data is from API call
    }
        pan: {
            enabled: true,
            mode: 'xy'
        },
        zoom: {
            enabled: true,
            mode: 'xy'
        },
        bezierCurve : false
    }
};

var ctx = document.getElementById('myChart').getContext('2d');
window.myChart = new Chart(ctx, config);

$('#exportTheseRunsToCSV').on('click', function() {
    // something like myChart.getVisibleDataPoints() ???
    console.log(chart)
    console.log(chart.data.datasets)
});

There has to be some internal API call to get the visible points, as I also have a function to export the current visible points to PNG and that only grabs what is currently drawn on the canvas:

<a id="exportTheseRuns" class="text-white" href="#" download="image.png" download><i class="fas fa-download"></i> Export to PNG</a>

$('#exportTheseRuns').on('click', function() {
    $('#exportTheseRuns').attr('href', myChart.toBase64Image());
})

The function .toBase64Image() seems like it internally does what I am looking for, as it will only capture visible points, but then it returns a Base64 URI which I can't use for my arrayToCSV function.

Upvotes: 6

Views: 2469

Answers (3)

Alfredo M F
Alfredo M F

Reputation: 1

In the last versions of ChartJS, minIndex and maxIndex are not linked to the visible points, they are linked to the visible X axis position, I found the same problem. But I found 2 properties that I used to solve it:

chart._metasets[0].controller._drawStart
chart._metasets[0].controller._drawCount

that show the first point visible Index and the number of visible points, both needs some corrections, but if you are here, you will fix it.

PS: I use Zoom in my code and it still works.

Upvotes: 0

timclutton
timclutton

Reputation: 13004

The chart object contains minIndex and maxIndex properties that can be used to slice the dataset for the visible values.

Here's a snippet showing how to use the plugin-provided functions onPanComplete and onZoomComplete to output the visible values after panning or zooming the chart:

function getVisibleValues({
  chart
}) {
  let x = chart.scales["x-axis-0"];

  document.getElementById("vv").innerText = JSON.stringify(chart.data.datasets[0].data.slice(x.minIndex, x.maxIndex + 1));
}

new Chart(document.getElementById("chart"), {
  type: "line",
  data: {
    labels: ['a', 'b', 'c', 'd', 'e', 'f', 'g', 'h', 'i', 'j'],
    datasets: [{
      data: [0, 1, 2, 4, 8, 16, 32, 64, 128, 256]
    }]
  },
  options: {
    maintainAspectRatio: false,
    scales: {
      xAxes: [{
        ticks: {
          min: 'c',
          max: 'h'
        }
      }]
    },
    plugins: {
      zoom: {
        pan: {
          enabled: true,
          mode: 'x',
          onPanComplete: getVisibleValues
        },
        zoom: {
          enabled: true,
          mode: 'x',
          onZoomComplete: getVisibleValues
        }
      }
    }
  }
});
<script src="https://cdn.jsdelivr.net/npm/[email protected]"></script>
<script src="https://cdn.jsdelivr.net/npm/[email protected]"></script>
<script src="https://cdn.jsdelivr.net/npm/[email protected]"></script>
<canvas id="chart" style="max-height:125px"></canvas>
<p>
  Visible values: <span id="vv"></span>
</p>

Upvotes: 4

Vl4dimyr
Vl4dimyr

Reputation: 916

The toBase64Image function does not what you want, it just gets the data URL from the canvas.

toBase64Image on github.com/chartjs

toBase64Image: function() {
  return this.canvas.toDataURL.apply(this.canvas, arguments);
},

You can get the updated chart data with onZoomComplete and onPanComplete, they both get an object that contains chart from this you might get more information about the current zoom, but as far as I can see you will need to do some calculations/work to get the visible points...

Upvotes: 0

Related Questions