Andres SK
Andres SK

Reputation: 10974

How to avoid positioning ChartJS's tooltip on specific datasets on a chart?

I'm using ChartJS to display stripes (ranges) and inside each stripe I'm display a line of the median value. I'm hiding the stripes' presence in both the legend and tooltip lists. That's done by adding this string in the dataset label: "HIDE!" and then just filtering out those items through the tooltip and legend options.

When I move the mouse over the chart, I've configured the tooltip to be positioned on the nearest vector, but that should only be hapenning on the line datasets, and not on the stripe datasets. Examples below:

Tooltip using a stripe as nearest vector (this is NOT ok):

problem

Tooltip using a line as nearest vector (this is ok):

tooltip on point

So the question is: How can I avoid positioning the tooltip tick on the stripes' vectors, and only use the lines' vectors for that? It seems that the filter option only hides the item from the legend list itself, but not from the graphic when it comes to position the tooltip div.

Here's my current code (you can check the jsfiddle as well):

<canvas id="rainbow"></canvas>
<script src="https://cdn.jsdelivr.net/npm/[email protected]/dist/chart.umd.min.js"></script>
<script>
var chart;
var aspectRatio = 2;
if(window.innerWidth < 600) {
    aspectRatio = 1;
}
var chartdata = {
    type: "line",
    data: {
        //months
        labels: ["0","1","2","3","4","5","6","7","8","9","10","11","12","13","14","15","16","17","18","19","20","21","22","23","24","25","26","27","28","29","30","31","32","33","34","35","36","37","38","39","40","41","42","43","44","45","46","47","48","49","50","51","52","53","54","55","56","57","58","59","60"],
        datasets : [

            //##################################################

            {
                //tracking (white dotted line)
                type: 'line',
                data: [50.9,54.6,,62,,,68.3,68.9,70.5,73,74.4,,,77.5,79.7,,,82.4,,,85.7,,,88.9,90.6,90.1,,92,93,,,95.6,96.4,,99.1,98.9,,,,,,103.4,104.2,,,,,108.7,,,110.7,111.3,,111.6,,,113.5,114.1,115.7,116.3,],
                label: "name",
                borderColor: "#ffffff",
                backgroundColor: "#ffffff",
                pointRadius: 0,
                pointHitRadius: 1,
                borderWidth: 3,
                spanGaps: true,
                borderDash: [10,5]
            },

            //##################################################

            {
                //3 SD line [7]
                data: [54.7,59.5,63.2,66.1,68.6,70.7,72.5,74.2,75.8,77.4,78.9,80.3,81.7,83.1,84.4,85.7,87.0,88.2,89.4,90.6,91.7,92.9,94.0,95.0,95.8,96.4,97.4,98.4,99.4,100.3,101.3,102.2,103.1,103.9,104.8,105.6,106.5,107.3,108.1,108.9,109.7,110.5,111.2,112.0,112.7,113.5,114.2,114.9,115.7,116.4,117.1,117.7,118.4,119.1,119.8,120.4,121.1,121.8,122.4,123.1,123.7],
                label: "3 SD",
                backgroundColor: "#8ac4e8",
                borderColor: "#8ac4e8",
                pointRadius: 0,
                pointHitRadius: 5,
                borderWidth: 2
            },
            {
                //2 SD line [6]
                data: [52.9,57.6,61.1,64.0,66.4,68.5,70.3,71.9,73.5,75.0,76.4,77.8,79.2,80.5,81.7,83.0,84.2,85.4,86.5,87.6,88.7,89.8,90.8,91.9,92.6,93.1,94.1,95.0,96.0,96.9,97.7,98.6,99.4,100.3,101.1,101.9,102.7,103.4,104.2,105.0,105.7,106.4,107.2,107.9,108.6,109.3,110.0,110.7,111.3,112.0,112.7,113.3,114.0,114.6,115.2,115.9,116.5,117.1,117.7,118.3,118.9],
                label: "2 SD",
                backgroundColor: "#80a3e6",
                borderColor: "#80a3e6",
                pointRadius: 0,
                pointHitRadius: 5,
                borderWidth: 2
            },
            {
                //1 SD line [5]
                data: [51.0,55.6,59.1,61.9,64.3,66.2,68.0,69.6,71.1,72.6,73.9,75.3,76.6,77.8,79.1,80.2,81.4,82.5,83.6,84.7,85.7,86.7,87.7,88.7,89.3,89.9,90.8,91.7,92.5,93.4,94.2,95.0,95.8,96.6,97.4,98.1,98.9,99.6,100.3,101.0,101.7,102.4,103.1,103.8,104.5,105.1,105.8,106.4,107.0,107.7,108.3,108.9,109.5,110.1,110.7,111.3,111.9,112.5,113.0,113.6,114.2],
                label: "1 SD",
                backgroundColor: "#7780e4",
                borderColor: "#7780e4",
                pointRadius: 0,
                pointHitRadius: 5,
                borderWidth: 2
            },
            {
                //Median [4]
                data: [49.1,53.7,57.1,59.8,62.1,64.0,65.7,67.3,68.7,70.1,71.5,72.8,74.0,75.2,76.4,77.5,78.6,79.7,80.7,81.7,82.7,83.7,84.6,85.5,86.1,86.6,87.4,88.3,89.1,89.9,90.7,91.4,92.2,92.9,93.6,94.4,95.1,95.7,96.4,97.1,97.7,98.4,99.0,99.7,100.3,100.9,101.5,102.1,102.7,103.3,103.9,104.5,105.0,105.6,106.2,106.7,107.3,107.8,108.4,108.9,109.4],
                label: "Median",
                backgroundColor: "#8c77e4",
                borderColor: "#8c77e4",
                pointRadius: 0,
                pointHitRadius: 5,
                borderWidth: 2
            },
            {
                //-1 SD line [3]
                data: [47.3,51.7,55.0,57.7,59.9,61.8,63.5,65.0,66.4,67.7,69.0,70.3,71.4,72.6,73.7,74.8,75.8,76.8,77.8,78.8,79.7,80.6,81.5,82.3,82.9,83.3,84.1,84.9,85.7,86.4,87.1,87.9,88.6,89.3,89.9,90.6,91.2,91.9,92.5,93.1,93.8,94.4,95.0,95.6,96.2,96.7,97.3,97.9,98.4,99.0,99.5,100.1,100.6,101.1,101.6,102.2,102.7,103.2,103.7,104.2,104.7],
                label: "-1 SD",
                backgroundColor: "#aa78e5",
                borderColor: "#aa78e5",
                pointRadius: 0,
                pointHitRadius: 5,
                borderWidth: 2
            },
            {
                //-2 SD line [2]
                data: [45.4,49.8,53.0,55.6,57.8,59.6,61.2,62.7,64.0,65.3,66.5,67.7,68.9,70.0,71.0,72.0,73.0,74.0,74.9,75.8,76.7,77.5,78.4,79.2,79.7,80.0,80.8,81.5,82.2,82.9,83.6,84.3,84.9,85.6,86.2,86.8,87.4,88.0,88.6,89.2,89.8,90.4,90.9,91.5,92.0,92.5,93.1,93.6,94.1,94.6,95.1,95.6,96.1,96.6,97.1,97.6,98.1,98.5,99.0,99.5,99.9],
                label: "-2 SD",
                backgroundColor: "#c97be5",
                borderColor: "#c97be5",
                pointRadius: 0,
                pointHitRadius: 5,
                borderWidth: 2
            },
            {
                //-3 SD line [1]
                data: [43.6,47.8,51.0,53.5,55.6,57.4,58.9,60.3,61.7,62.9,64.1,65.2,66.3,67.3,68.3,69.3,70.2,71.1,72.0,72.8,73.7,74.5,75.2,76.0,76.4,76.8,77.5,78.1,78.8,79.5,80.1,80.7,81.3,81.9,82.5,83.1,83.6,84.2,84.7,85.3,85.8,86.3,86.8,87.4,87.9,88.4,88.9,89.3,89.8,90.3,90.7,91.2,91.7,92.1,92.6,93.0,93.4,93.9,94.3,94.7,95.2],
                label: "-3 SD",
                backgroundColor: "#dc7db7",
                borderColor: "#dc7db7",
                pointRadius: 0,
                pointHitRadius: 5,
                borderWidth: 2
            },

            //##################################################

            {
                //3 SD stripe [7]
                data: [55.6,60.45,64.25,67.15,69.7,71.8,73.6,75.35,76.95,78.6,80.15,81.55,82.95,84.4,85.75,87.05,88.4,89.6,90.85,92.1,93.2,94.45,95.6,96.55,97.4,98.05,99.05,100.1,101.1,102,103.1,104,104.95,105.7,106.65,107.45,108.4,109.25,110.05,110.85,111.7,112.55,113.2,114.05,114.75,115.6,116.3,117,117.9,118.6,119.3,119.9,120.6,121.35,122.1,122.65,123.4,124.15,124.75,125.5,126.1],
                label: "HIDE!3 SD",
                borderColor: "#7bb5d9",
                backgroundColor: "#7bb5d9",
                pointRadius: 0,
                pointHitRadius: 0,
                pointHoverRadius: 0,
                borderWidth: 1,
                fill: 9
            },
            {
                //2 SD stripe [6]
                data: [53.8,58.55,62.15,65.05,67.5,69.6,71.4,73.05,74.65,76.2,77.65,79.05,80.45,81.8,83.05,84.35,85.6,86.8,87.95,89.1,90.2,91.35,92.4,93.45,94.2,94.75,95.75,96.7,97.7,98.6,99.5,100.4,101.25,102.1,102.95,103.75,104.6,105.35,106.15,106.95,107.7,108.45,109.2,109.95,110.65,111.4,112.1,112.8,113.5,114.2,114.9,115.5,116.2,116.85,117.5,118.15,118.8,119.45,120.05,120.7,121.3],
                label: "HIDE!2 SD",
                borderColor: "#7194d7",
                backgroundColor: "#7194d7",
                pointRadius: 0,
                pointHitRadius: 0,
                pointHoverRadius: 0,
                borderWidth: 1,
                fill: 10
            },
            {
                //1 SD stripe [5]
                data: [51.95,56.6,60.1,62.95,65.35,67.35,69.15,70.75,72.3,73.8,75.15,76.55,77.9,79.15,80.4,81.6,82.8,83.95,85.05,86.15,87.2,88.25,89.25,90.3,90.95,91.5,92.45,93.35,94.25,95.15,95.95,96.8,97.6,98.45,99.25,100,100.8,101.5,102.25,103,103.7,104.4,105.15,105.85,106.55,107.2,107.9,108.55,109.15,109.85,110.5,111.1,111.75,112.35,112.95,113.6,114.2,114.8,115.35,115.95,116.55],
                label: "HIDE!1 SD",
                borderColor: "#6871d5",
                backgroundColor: "#6871d5",
                pointRadius: 0,
                pointHitRadius: 0,
                pointHoverRadius: 0,
                borderWidth: 1,
                fill: 11
            },

            //##################################################

            {
                //Median stripe [4]
                data: [50.05,54.65,58.1,60.85,63.2,65.1,66.85,68.45,69.9,71.35,72.7,74.05,75.3,76.5,77.75,78.85,80,81.1,82.15,83.2,84.2,85.2,86.15,87.1,87.7,88.25,89.1,90,90.8,91.65,92.45,93.2,94,94.75,95.5,96.25,97,97.65,98.35,99.05,99.7,100.4,101.05,101.75,102.4,103,103.65,104.25,104.85,105.5,106.1,106.7,107.25,107.85,108.45,109,109.6,110.15,110.7,111.25,111.8],
                label: "HIDE!Median",
                borderColor: "#7d68d5",
                backgroundColor: "#7d68d5",
                pointRadius: 0,
                pointHitRadius: 0,
                pointHoverRadius: 0,
                borderWidth: 1,
                fill: 12
            },

            //##################################################

            {
                //-1 SD stripe [3]
                data: [48.2,52.7,56.05,58.75,61,62.9,64.6,66.15,67.55,68.9,70.25,71.55,72.7,73.9,75.05,76.15,77.2,78.25,79.25,80.25,81.2,82.15,83.05,83.9,84.5,84.95,85.75,86.6,87.4,88.15,88.9,89.65,90.4,91.1,91.75,92.5,93.15,93.8,94.45,95.1,95.75,96.4,97,97.65,98.25,98.8,99.4,100,100.55,101.15,101.7,102.3,102.8,103.35,103.9,104.45,105,105.5,106.05,106.55,107.05],
                label: "HIDE!-1 SD",
                borderColor: "#9b69d6",
                backgroundColor: "#9b69d6",
                pointRadius: 0,
                pointHitRadius: 0,
                pointHoverRadius: 0,
                borderWidth: 1,
                fill: 13
            },
            {
                //-2 SD stripe [2]
                data: [46.35,50.75,54,56.65,58.85,60.7,62.35,63.85,65.2,66.5,67.75,69,70.15,71.3,72.35,73.4,74.4,75.4,76.35,77.3,78.2,79.05,79.95,80.75,81.3,81.65,82.45,83.2,83.95,84.65,85.35,86.1,86.75,87.45,88.05,88.7,89.3,89.95,90.55,91.15,91.8,92.4,92.95,93.55,94.1,94.6,95.2,95.75,96.25,96.8,97.3,97.85,98.35,98.85,99.35,99.9,100.4,100.85,101.35,101.85,102.3],
                label: "HIDE!-2 SD",
                borderColor: "#ba6cd6",
                backgroundColor: "#ba6cd6",
                pointRadius: 0,
                pointHitRadius: 0,
                pointHoverRadius: 0,
                borderWidth: 1,
                fill: 14
            },
            {
                //-3 SD stripe [1]
                data: [44.5,48.8,52,54.55,56.7,58.5,60.05,61.5,62.85,64.1,65.3,66.45,67.6,68.65,69.65,70.65,71.6,72.55,73.45,74.3,75.2,76,76.8,77.6,78.05,78.4,79.15,79.8,80.5,81.2,81.85,82.5,83.1,83.75,84.35,84.95,85.5,86.1,86.65,87.25,87.8,88.35,88.85,89.45,89.95,90.45,91,91.45,91.95,92.45,92.9,93.4,93.9,94.35,94.85,95.3,95.75,96.2,96.65,97.1,97.55],
                label: "HIDE!-3 SD",
                borderColor: "#cd6ea8",
                backgroundColor: "#cd6ea8",
                pointRadius: 0,
                pointHitRadius: 0,
                pointHoverRadius: 0,
                borderWidth: 1,
                fill: 15
            },

            //##################################################

            {
                //artificial base
                data: [42.7,46.8,50,52.45,54.5,56.3,57.75,59.1,60.55,61.7,62.9,63.95,65,65.95,66.95,67.95,68.8,69.65,70.55,71.3,72.2,73,73.6,74.4,74.75,75.2,75.85,76.4,77.1,77.8,78.35,78.9,79.5,80.05,80.65,81.25,81.7,82.3,82.75,83.35,83.8,84.25,84.75,85.35,85.85,86.35,86.8,87.15,87.65,88.15,88.5,89,89.5,89.85,90.35,90.7,91.05,91.6,91.95,92.3,92.85],
                label: "HIDE!lower",
                borderColor: "transparent",
                backgroundColor: "transparent",
                pointRadius: 0,
                pointHitRadius: 5,
                borderWidth: 1,
                fill: false
            }
        ]
    },

    //configuration options
    options: {
        animation: true,
        aspectRatio: aspectRatio,
        interaction: {
            intersect: false,
            mode: 'index',
            axis: 'x'
        },
        scales: {
            x: {
                label: "time",
                grid: {
                    display: true
                },

            },
            y: {
                label: "meassure",
                grid: {
                    display: true
                },
                stacked: false,
                beginAtZero: false,
                position: "right",
                ticks: {
                    callback: function(val, index) {
                        return parseInt(val) + ' cm';
                    }
                }
            }
        },
        plugins: {
            tooltip: {
                position: 'nearest',
                caretSize: 7,
                caretPadding: 10,
                filter: function (tooltipItem, data) {
                    if(tooltipItem.dataset.label.includes('HIDE!')) {
                        return false;
                    }
                    return true;
                }
            },
            legend: {
                display: true,
                position: 'top',
                labels: {
                    font: {
                        size: 14,
                        family: 'Inter, "sans-serif"'
                    },
                    filter: function(item, chart) {
                        return !item.text.includes('HIDE!');
                    }
                }
            }
        }
    }
}
const orgdata = JSON.parse(JSON.stringify(chartdata));

//draw chart
document.addEventListener('DOMContentLoaded', function(event) {
    var ctx = document.getElementById('rainbow').getContext('2d');
    chart = new Chart(ctx, chartdata);
});
</script>

Upvotes: 1

Views: 255

Answers (2)

Jordy
Jordy

Reputation: 1960

I think setting up plugins.tooltip.position to average is enough to avoid positioning the tooltip.

reference

Upvotes: 0

crg
crg

Reputation: 4557

You have to use the custome positioner.

Here is an example on how to implement it:

// Define the custom position mode function
Chart.Tooltip.positioners.custom = function(elements, eventPosition) {
  var tooltipWidth = this._chart.tooltip._view.width;
  var chartArea = this._chart.chartArea;
  var xPosition = eventPosition.x;
  var yPosition = eventPosition.y;
  
  // Check if the hovered element belongs to the second dataset
  if (elements[0]._datasetIndex === 1) {
    // If yes, set the x position to be the center of the chart
    xPosition = chartArea.left + chartArea.width / 2;
  }
  
  return {
    x: xPosition - tooltipWidth / 2,
    y: yPosition
  };
};

var chartdata = {
 = {
  type: 'line',
  ...
  options: {
    tooltips: {
      position: 'custom'
    }
  }
};

You can find more help in ChartJS documentation

Upvotes: 0

Related Questions