首页 > 解决方案 > 如何自定义 Chart.js 折线图的工具提示?

问题描述

我正在尝试使用来自的折线图显示一些数据Chart.js

我当前的图表如下所示:

在此处输入图像描述

我想要的输出应该显示如下:

在此处输入图像描述

我的第一个图表代码如下:

var chart = new Chart(ctx, {
  type: "line",
  data: {
    labels: This.xAxis,
    datasets: [{
      backgroundColor: gradient,
      pointBackgroundColor: "white",
      borderWidth: 1,
      borderColor: "#5946B0",
      pointRadius: 2,
      displayColors: false,
      data: This.yAxis
    }]
  },
  options: {
    title: {
      display: false,
      text: "Test"
    },
    tooltips: {
      backgroundColor: "#FAFAFA",
      borderColor: "lightgreen",
      borderWidth: 1,
      titleFontColor: "black",
      titleFontStyle: "normal",
      displayColors: false,
      bodyFontColor: "black"
    },
    legend: {
      display: false
    },
    plugins: {
      zoom: {
        pan: {
          enabled: true,
          mode: "x",
          speed: 10,
          threshold: 10
        },
        zoom: {
          enabled: true,
          mode: "y"
        }
      }
    }
  }
});

标签: javascriptvue.jschart.jsplotly

解决方案


您可以使用 为工具提示的标题和内容定义回调函数options.tooltips.callbacks

const options = {
  type: 'line',
  options: {
    tooltips: {
      callbacks: {
        title: function(t, d) {
          return moment(d.labels[t[0].index]).format('dd MMM DD, YYYY');
        },
        label: function(t, d) {
          const label = d.datasets[t.datasetIndex].label;
          const value = d.datasets[t.datasetIndex].data[t.index];
          const sign = value >= 0 ? '+' : '';
          return `${label}: ${sign}${value.toFixed(2)}%`;
        }
      }
    }
  }
};

演示

const dateRange = n =>
  (now =>
    new Array(n).fill(0).map((value, index) =>
      new Date(now + (8.64e7 * index))))
  (Date.now());

const palette = [{
  hex: '#5946B0',
  rgba: 'rgba(89, 70, 176, 0.33)'
}, {
  hex: '#eab925',
  rgba: 'rgba(234, 185, 37, 0.33)'
}];

const randRange = n =>
  new Array(n).fill(0).map(() =>
    chance.floating({ min: -100, max: 300 }))

const options = {
  type: 'line',
  data: {
    labels: dateRange(7),
    datasets: [{
      label: 'Investment',
      data: randRange(7),
      borderColor: palette[0].hex,
      backgroundColor: palette[0].rgba,
      pointBackgroundColor: 'white',
      borderWidth: 1
    }, {
      label: 'Return',
      data: randRange(7),
      borderColor: palette[1].hex,
      backgroundColor: palette[1].rgba,
      pointBackgroundColor: 'white',
      borderWidth: 1
    }]
  },
  options: {
    scales: {
      xAxes: [{
        type: 'time',
        time: {
          unit: 'day'
        }
      }],
      yAxes: [{
        ticks: {
          reverse: false
        }
      }]
    },
    tooltips: {
      // See: https://stackoverflow.com/a/44010778/1762224
      callbacks: {
        title: function(t, d) {
          return moment(d.labels[t[0].index]).format('dd MMM DD, YYYY');
        },
        label: function(t, d) {
          const label = d.datasets[t.datasetIndex].label;
          const value = d.datasets[t.datasetIndex].data[t.index];
          const sign = value >= 0 ? '+' : '';
          return `${label}: ${sign}${value.toFixed(2)}%`;
        }
      },
      backgroundColor: "#FAFAFA",
      borderColor: "lightgreen",
      borderWidth: 1,
      titleFontColor: "black",
      titleFontStyle: "bold",
      displayColors: false,
      bodyFontColor: "black"
    }
  }
};

const ctx = document.getElementById('chart').getContext('2d');
new Chart(ctx, options);
<script src="https://cdnjs.cloudflare.com/ajax/libs/chance/1.0.18/chance.min.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/moment.js/2.29.1/moment.min.js"></script>
<link href="https://cdnjs.cloudflare.com/ajax/libs/Chart.js/2.9.4/Chart.min.css" rel="stylesheet" />
<script src="https://cdnjs.cloudflare.com/ajax/libs/Chart.js/2.9.4/Chart.min.js"></script>
<canvas id="chart" height="120"></canvas>

如果你需要用 CSS 渲染一个完全自定义的工具提示,你可能需要定义一个options.tooltips.custom渲染器函数,但这可能会更加困难。


推荐阅读