[Chartjs]-How to add a horizontal line at a specific point in chart.js when hovering?

3👍

You can use chart.js annotations plugin to draw horizontal lines at specific values, then you can implement a proper onHover callback (events on the whole chart) to show/hide those lines.

annotation : {
    drawTime : "afterDraw",
    annotations : [{
            id : "line1",
            type : "line",
            mode : "horizontal",
            scaleID : "y-axis",
            value : 4.5,
            borderWidth : 2,
            borderColor : "red",
            label : {
                content : "threshold 1",
                enabled : true,
                position : "right"
            }
        }
    ]
},

See my fiddle exemplifying the approach: https://jsfiddle.net/beaver71/5jg4wgdh/

var data_set = [{x: 1, y: 12}, {x: 2, y: 3}, {x: 3, y: 2}, {x: 4, y: 1}, {x: 5, y: 8}, {x: 6, y: 8}, {x: 7, y: 2}, {x: 8, y: 2}, {x: 9, y: 3}, {x: 10, y: 5}, {x: 11, y: 11}, {x: 12, y: 1}];
var labels = ["JAN", "FEB", "MAR", "APR", "MAY", "JUN", "JUL", "AUG", "SEP", "OCT", "NOV", "DEC"];

var lines = [], id = 0;
var linesOn = false;

var data = {
  labels: labels,
  datasets: [{
    label: "My First dataset",
    backgroundColor: "rgba(255,99,132,0.2)",
    borderColor: "rgba(255,99,132,1)",
    borderWidth: 2,
    hoverBackgroundColor: "rgba(255,99,132,0.4)",
    hoverBorderColor: "rgba(255,99,132,1)",
    data: data_set,
  }]
};

var option = {
  legend: false,
  title: {
    display: true,
  },
  onHover: function(evt) {
  	console.log("onHover", evt.type);
    if (evt.type == 'mousemove' && linesOn == false) {
    	linesOn = true;
      myLineChart.options.annotation.annotations = lines;
      myLineChart.update();
    } else if (evt.type == 'mouseout' && linesOn == true) {
    	linesOn = false;
    	myLineChart.options.annotation.annotations = [];
    	myLineChart.update();
    }
    var item = myLineChart.getElementAtEvent(evt);
    if (item.length) {
      console.log(">item", item);
      console.log(">data", item[0]._index, data.datasets[0].data[item[0]._index]);
    }
  },
  onClick: function(evt) {
    var el = myLineChart.getElementAtEvent(evt);
    console.log("onClick", el, evt);
  },
  annotation: {
    drawTime: "afterDraw",
    annotations: lines
  },
  scales: {
    xAxes: [{
      id: 'x-axis',
      type: 'linear',
      position: 'bottom',
      ticks: {
        max: 12,
        min: 1,
        stepSize: 1,
        callback: function(value, index, values) {
          return data.labels[index];
        }
      }
    }],
    yAxes: [{
      id: 'y-axis',
      type: 'linear',
    }],
  }

};

var myLineChart = Chart.Line('myChart', {
  data: data,
  options: option
});

// define two lines (these code must be after chart creation)
addLine(3.5);
addLine(7);

function addLine(value) {
  id++;
  var ln = {
    id: "line" + id,
    type: "line",
    mode: "horizontal",
    scaleID: "y-axis",
    value: value,
    borderWidth: 2,
    borderColor: "red",
    label: {
      content: "threshold " + id,
      enabled: true,
      position: "right"
    }
  };
  lines.push(ln);
}
<script src="https://cdnjs.cloudflare.com/ajax/libs/Chart.js/2.7.1/Chart.bundle.min.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/chartjs-plugin-annotation/0.5.7/chartjs-plugin-annotation.min.js"></script>

<canvas id="myChart" width="400" height="200"></canvas>

Update:

If you need to animate annotation hovering on them, here is another example:

https://jsfiddle.net/beaver71/yxy402rk/

var data_set = [{x: 1, y: 12}, {x: 2, y: 3}, {x: 3, y: 2}, {x: 4, y: 1}, {x: 5, y: 8}, {x: 6, y: 8}, {x: 7, y: 2}, {x: 8, y: 2}, {x: 9, y: 3}, {x: 10, y: 5}, {x: 11, y: 11}, {x: 12, y: 1}];
var labels = ["JAN", "FEB", "MAR", "APR", "MAY", "JUN", "JUL", "AUG", "SEP", "OCT", "NOV", "DEC"];

var lines = [], id = 0;
var linesOn = false;

var data = {
  labels: labels,
  datasets: [{
    label: "My First dataset",
    backgroundColor: "rgba(255,99,132,0.2)",
    borderColor: "rgba(255,99,132,1)",
    borderWidth: 2,
    hoverBackgroundColor: "rgba(255,99,132,0.4)",
    hoverBorderColor: "rgba(255,99,132,1)",
    data: data_set,
  }]
};

var option = {
  legend: false,
  title: {
    display: true,
  },
  onHover: function(evt) {
    var item = myLineChart.getElementAtEvent(evt);
    if (item.length) {
      console.log(">item", item);
      console.log(">data", item[0]._index, data.datasets[0].data[item[0]._index]);
    }
  },
  onClick: function(evt) {
    var el = myLineChart.getElementAtEvent(evt);
    console.log("onClick", el, evt);
  },
  annotation: {
    drawTime: "afterDraw",
    events: ['click','mouseenter','mouseleave'],
    annotations: lines
  },
  scales: {
    xAxes: [{
      id: 'x-axis',
      type: 'linear',
      position: 'bottom',
      ticks: {
        max: 12,
        min: 1,
        stepSize: 1,
        callback: function(value, index, values) {
          return data.labels[index];
        }
      }
    }],
    yAxes: [{
      id: 'y-axis',
      type: 'linear',
    }],
  }

};

addLine(3.5);
addLine(7);

var myLineChart = Chart.Line('myChart', {
  data: data,
  options: option
});

console.log(myLineChart.annotation.elements.line1);
myLineChart.annotation.elements.line1.hidden = true;
myLineChart.update();

function addLine(value) {
  id++;
  var ln = {
    id: "line" + id,
    type: "line",
    mode: "horizontal",
    scaleID: "y-axis",
    value: value,
    borderWidth: 2,
    borderColor: "rgba(0,0,255,0.3)",
    label: {
      content: "threshold " + id,
      enabled: true,
      position: "right",
      backgroundColor: 'rgba(0,0,0,0.3)',
    },
    onMouseenter: function(e) {
    	console.log("onMouseenter", e, this);
      this.options.borderColor = "rgba(0,0,255,0.8)";
      this.options.label.backgroundColor = 'rgba(0,0,0,0.8)';
      myLineChart.update();
    },
    onMouseleave: function(e) {
    	console.log("onMouseleave", e);
      this.options.borderColor = "rgba(0,0,255,0.3)";
      this.options.label.backgroundColor = 'rgba(0,0,0,0.3)';
      myLineChart.update();
    },
  };
  lines.push(ln);
}
<script src="https://cdnjs.cloudflare.com/ajax/libs/Chart.js/2.7.1/Chart.bundle.min.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/chartjs-plugin-annotation/0.5.7/chartjs-plugin-annotation.min.js"></script>

<canvas id="myChart" width="400" height="200"></canvas>

Leave a comment