我刚开始使用Chart.js,但遇到了问题。
首先,我需要在简单的折线图中显示以下内容:
这是我当前的图表,在Y-axis
上,我有可能的等级(用于学生考试),范围从1 to 6
。
在X-axis
上,我给出了在给定考试中可能达到的分数。
现在,它变得更加复杂了,该图表正在根据输入和下拉列表的选择进行更新。
坡度(Y轴)可以是5种增量类型:Integer, Halves, Quarters, Decimal and Hundredths
这是通过下拉菜单选择的,默认值为Quarters
,这意味着在选择Quarters
的情况下,我的年级数字数组看起来像:
grades = [1, 1.25, 1.50, 1.75, 2....., 5.75, 6]
同时选择了Hundredths
,它看起来像:
grades = [1, 1.01, 1.02, 1.03, .... 5.97, 5.98, 5.99, 6]
对于每个年级,需要一定数量的点(X轴)才能达到目标。 所需的点是使用我在函数中输入的公式计算的:
mySecretFormula(grades: Array<Number>) {
grades.forEach(g => {
const currentPoints = g * mySecretFormula;
this.points.push(currentPoints);
}
所以基本上我在这个函数中通过了我的成绩,并且它返回了另一个具有相同数量元素的数字数组(因为每个成绩对应一个分数)
例如,如果我选择了“整数成绩”,则表示我的成绩数组如下:
grades = [1, 2, 3, 4, 5, 6]
我得到的分数将是:
scores = [0, 5, 10, 15, 25, 30]
如果最高分设置为30(最高分在输入中定义)
然后最后我使用chart.js
来显示我的数据,如下所示:
this.canvas.data.labels = this.points;
this.canvas.data.datasets[0].data = this.grades;
this.canvas.update();
因此,每当我更改有关成绩增量的下拉列表时,都会触发此函数并更新图表。
可以说它正在工作,但远非最佳。
我想要实现的很简单。
它应该像这样:
这是我选择整数等级时图表的外观,因此只有6个不同的等级和6个不同的分数。
无论选择什么增量,我都希望图表始终像这样, 因此,总是有5或6条网格线,并且X轴的刻度线总是相同。
然后,如果当前选择的增量是Integer,我将只有6个交点,但是如果我要交换为Decimal或Hundredths,那么对于许多交点,图表看起来就像这样,但是当您将鼠标悬停在用鼠标在直线上,我将获得每个有效交点的工具提示。
现在,如果我转换为十进制增量,我的图表将更新为:
(忽略舍入,忘记将它们舍入为两位小数) 因此当您看到刻度点发生变化时,网格宽度发生了变化,整个图表的高度也发生了变化。
但是交叉点可以正常工作,如果我将鼠标悬停在直线上,我将获得这些对的每个点的工具提示:
十进制增量等于:
等级= [1,1.1,1.2,1.3,1.4,.... 5.9,6] 点= [0,0.7,1.4,2.1,2.8,.... 34.3,35]
因此要获得相同的结果,BUT必须与图表始终相同,滴答点以及高度和宽度始终相同,因为成绩和分数的范围始终相同,但取决于增量选择,从最少6个交叉点(整数)到超过500个交叉点(百分之一)!
希望我说的很清楚,非常感谢
编辑:在您的帮助下进行管理,以在此两行中添加自定义工具提示:
afterBody: function([tooltipItem], data): any {
const multistringText = ["Points: " + tooltipItem.xLabel];
multistringText.push("Grade: " + tooltipItem.yLabel);
return multistringText;
}
可以正常工作,但是现在如何删除上面的原始工具提示字符串?在我的2行自定义工具提示上方查看图像,我还有另一行要隐藏!
最后,始终查看此图像,如何在相同宽度的X轴上制作网格线?如您所见,前四个大于最后一个!我希望它们的宽度始终相同!谢谢
答案 0 :(得分:1)
我建议您将图表转换为xy图表,设置轴选项并自定义工具提示
var ctx = document.getElementById("myChart").getContext('2d');
var precision = 0;
var data = getData();
var myChart = new Chart(ctx, {
type:"scatter",
data: {
datasets: [{
label: 'grades',
data: data,
fill: false,
pointRadius: 0,
pointHitRadius: 3
}]
},
options: {
scales: {
yAxes: [{
ticks: {
beginAtZero:true,
max:6
}
}],
xAxes: [{
ticks: {
beginAtZero:true,
max:35,
stepSize: 1,
callback: function(value){
if (value < 5){
return value;
} else {
if (value% 5 === 0){
return value;
}
}
}
}
}]
},
tooltips: {
callbacks: {
label: function(tooltipItem, data) {
var label = [
'X: ' + tooltipItem.xLabel.toFixed(precision),
'Y: ' + tooltipItem.yLabel.toFixed(precision)
];
return label;
}
}
}
}
});
function getData(){
var step = 10**-precision;
var arr = [];
for (var i=0; i<=6; i+=step){
arr.push({y: i, x: 35*i/6})
}
return arr;
}
setTimeout(function(){
precision = 1;
myChart.data.datasets[0].data = getData();
myChart.update();
}, 2000)
<script src="https://cdnjs.cloudflare.com/ajax/libs/Chart.js/2.6.0/Chart.js"></script>
<canvas id="myChart" width="100" height="100"></canvas>