Html 如何控制我的 Chart.JS 饼图图例的位置及其外观?
声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow
原文地址: http://stackoverflow.com/questions/39540981/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me):
StackOverFlow
How can I control the placement of my Chart.JS pie chart's legend, as well as its appearance?
提问by B. Clay Shannon
I am able to create a pie chart using Chart.JS with this code:
我可以使用 Chart.JS 和以下代码创建饼图:
HTML
HTML
<div>
<canvas id="top10ItemsChart" style="padding-left:20px" width="320" height="320"></canvas>
<div id="top10Legend" class="chart-legend"></div>
</div>
jQuery
jQuery
var data = [{
value: 2755,
color: "#FFE135",
label: "Bananas"
}, {
value: 2256,
color: "#3B5323",
label: "Lettuce, Romaine"
}, {
value: 1637,
color: "#fc6c85",
label: "Melons, Watermelon"
}, {
value: 1608,
color: "#ffec89",
label: "Pineapple"
}, {
value: 1603,
color: "#021c3d",
label: "Berries"
}, {
value: 1433,
color: "#3B5323",
label: "Lettuce, Spring Mix"
}, {
value: 1207,
color: "#046b00",
label: "Broccoli"
}, {
value: 1076,
color: "#cef45a",
label: "Melons, Honeydew"
}, {
value: 1056,
color: "#421C52",
label: "Grapes"
}, {
value: 1048,
color: "#FEA620",
label: "Melons, Cantaloupe"
}];
var optionsPie = {
legend: {
display: true,
position: 'right',
labels: {
fontColor: 'rgb(255, 99, 132)'
}
}
}
var ctx = $("#top10ItemsChart").get(0).getContext("2d");
var top10PieChart = new Chart(ctx).Pie(data, optionsPie);
document.getElementById('top10Legend').innerHTML = top10PieChart.generateLegend();
The problem is that it positions the legend to the bottom of the pie, and even spilling and bleeding outside of the boundaries of the div to which I want the pie to restrict itself:
问题是它将图例定位到饼图的底部,甚至在我希望饼图限制自身的 div 边界之外溢出和流血:
It also presents the legend as a simple unordered list. What I want to do is to control the color of the various elements in the legend ("Banana" should be the same color (#FFE135) as the piece of banana pie (so to speak), etc.)
它还将图例显示为一个简单的无序列表。我想要做的是控制图例中各种元素的颜色(“香蕉”应该与香蕉派(可以这么说)等颜色相同(#FFE135)等)
How can I make the individual elements match the color of its respective data point?
如何使各个元素与其各自数据点的颜色相匹配?
UPDATE
更新
The "Legend Label Configuration" topic in the official docs hereindicate you can set the fontColor of the legends, but this is for the whole shebang; what I want to know is, how is it possible to control the color of each item?
这里官方文档中的“Legend Label Configuration”主题表明您可以设置图例的fontColor,但这是针对整个shebang的;我想知道的是,如何控制每个项目的颜色?
UPDATE 2
更新 2
In an attempt to at least get the legend displaying in the desired spot, I added this to the jQuery:
为了至少让图例显示在所需的位置,我将其添加到 jQuery:
var optionsPie = {
legend: {
display: true,
position: 'right',
labels: {
fontColor: 'rgb(255, 99, 132)'
}
}
}
. . .
var myPieChart = new Chart(ctx).Pie(data, optionsPie);
document.getElementById("legendDiv").innerHTML = myPieChart.generateLegend();
...but it makes no difference - the legend is still hung from the bottom of the pie chart, and its font is still the default black.
...但它没有区别 - 图例仍然悬挂在饼图的底部,其字体仍然是默认的黑色。
UPDATE 3
更新 3
I utilized some suggested code, but the legend is still gravity-fed instead of hanging off to the right:
我使用了一些建议的代码,但图例仍然是重力馈送而不是挂在右侧:
So the legend impinges on the chart below it, rather than restricting itself to its own neighborhood.
因此,图例会影响其下方的图表,而不是将其限制在自己的附近。
Also, I don't want the bullet points to infest the legend - the colored squares (and the verbiage - but also the values) are all I need. How can I shove the legend from south of the pie to east of the pie?
此外,我不希望项目符号感染图例 - 彩色方块(和措辞 - 以及值)是我所需要的。我怎样才能把馅饼南边的传说推到馅饼东边?
UPDATE 4
更新 4
I have refactored the code based on thisand it's looking better (I added more data to the "label" value of the data array, too):
我已经基于此重构了代码,它看起来更好(我也向数据数组的“标签”值添加了更多数据):
Still, though, as you can see the legend is infringing on the quadrant below it. There is a "ton" of empty/wasted space around the pie, though - I want to move the pie to the left, and the legend to the right of the pie. That would also allow more vertical space for the pie to grow in stature.
尽管如此,正如您所看到的,图例侵犯了它下方的象限。不过,馅饼周围有很多空/浪费的空间 - 我想将馅饼向左移动,将图例移到馅饼的右侧。这也将为馅饼的成长提供更多的垂直空间。
How can I do that? Here is the code I'm using now:
我怎样才能做到这一点?这是我现在使用的代码:
HTML
HTML
<div>
<canvas id="top10ItemsChart" class="pie" style="padding-left:20px"></canvas>
<div id="top10Legend"></div>
</div>
CSS
CSS
.pie-legend {
list-style: none;
margin: 0;
padding: 0;
}
.pie-legend span {
display: inline-block;
width: 14px;
height: 14px;
border-radius: 100%;
margin-right: 16px;
margin-bottom: -2px;
}
.pie-legend li {
margin-bottom: 10px;
display: inline-block;
margin-right: 10px;
}
JQUERY
查询
var data = [{
value: 2755,
color: "#FFE135",
label: "Bananas: 2,755 (18%)"
}, {
. . .
}, {
value: 1048,
color: "#FEA620",
label: "Melons, Cantaloupe: 1,048 (7%)"
}];
var optionsPie = {
responsive: true,
scaleBeginAtZero: true,
legendTemplate: "<ul class=\"<%=name.toLowerCase()%>-legend\"><% for (var i=0; i<segments.length; i++){%><li><span style=\"background-color:<%=segments[i].fillColor%>\"></span><%if(segments[i].label){%><%=segments[i].label%><%}%></li><%}%></ul>"
}
var ctx = $("#top10ItemsChart").get(0).getContext("2d");
var top10PieChart = new Chart(ctx).Pie(data, optionsPie);
$("#top10Legend").html(top10PieChart.generateLegend());
NOTE: Adding this to optionsPie:
注意:将此添加到 optionsPie:
legend: {
display: true,
position: 'right'
},
...does nothing - the legend remains weighted down to the floor like a frog filled to the chin with quail shot.
......什么都不做 - 传说仍然沉重地压在地板上,就像一只用鹌鹑射击填满下巴的青蛙。
UPDATE 5
更新 5
I've played around with Teo's example, trying to get it to work just right but, although it's better, the pie is very puny, and the legend should be wider, but I can't figure out how to stretch the legend horizontally and the pie in all directions. Here's how it looks now:
我玩过 Teo 的例子,试图让它恰到好处地工作,但是,虽然它更好,但馅饼非常小,而且图例应该更宽,但我不知道如何水平拉伸图例和各个方向的馅饼。这是它现在的样子:
This is the code now (JQUERY is the same):
这是现在的代码(JQUERY 是一样的):
HTML
HTML
<div class="col-md-6">
<div class="topleft">
<h2 class="sectiontext">Top 10 Items</h2>
<br />
<div class="legendTable">
<div class="legendCell">
<canvas id="top10ItemsChart" class="pie" style="padding-left:20px"></canvas>
</div>
<div class="legendCell" id="top10Legend">
</div>
</div>
</div>
</div>
CSS
CSS
.topleft {
margin-top: -4px;
margin-left: 16px;
margin-bottom: 16px;
padding: 16px;
border: 1px solid black;
}
canvas {
width: 100% !important;
height: auto !important;
}
.legendTable {
border: 1px solid forestgreen;
display: table;
width: 100%;
table-layout: fixed;
}
.legendCell {
display: table-cell;
vertical-align: middle;
}
.pie-legend ul {
list-style: none;
margin: 0;
padding: 0;
width: 300px;
}
.pie-legend span {
display: inline-block;
width: 14px;
height: 12px;
border-radius: 100%;
margin-right: 4px;
margin-bottom: -2px;
}
.pie-legend li {
margin-bottom: 4px;
display: inline-block;
margin-right: 4px;
}
Something is squashing the pie and pushing the outer edges of the legend together.
有些东西正在挤压馅饼并将图例的外边缘推到一起。
UPDATE 6
更新 6
Ochi, et al: Here's what I see after the Ochification of my code:
Ochi 等人:这是我的代码 Ochification 后看到的内容:
This is my code - I even ordered the jQuery in the way you have it, although I doubt that is really necessary:
这是我的代码 - 我什至按照你的方式订购了 jQuery,尽管我怀疑这是否真的有必要:
HTML
HTML
<div class="row" id="top10Items">
<div class="col-md-6">
<div class="topleft">
<h2 class="sectiontext">Top 10 Items</h2>
<br />
@*<div class="legendTable">
<div class="legendCell">
<canvas id="top10ItemsChart" class="pie" style="padding-left:20px"></canvas>
</div>
<div class="legendCell" id="top10Legend">
</div>
</div>*@
<div class="chart">
<canvas id="top10ItemsChart" class="pie"></canvas>
<div id="pie_legend"></div>
</div>
</div>
</div>
. . .
</div>
CSS
CSS
.pie-legend {
list-style: none;
margin: 0;
padding: 0;
}
.pie-legend span {
display: inline-block;
width: 14px;
height: 14px;
border-radius: 100%;
margin-right: 16px;
margin-bottom: -2px;
}
.pie-legend li {
margin-bottom: 10px;
display: block;
margin-right: 10px;
}
.chart,
#priceComplianceBarChart,
#pie_legend {
display: inline-flex;
padding: 0;
margin: 0;
}
JQUERY
查询
var optionsPie = {
responsive: true,
scaleBeginAtZero: true,
legendTemplate: "<ul class=\"<%=name.toLowerCase()%>-legend\"><% for (var i=0; i<segments.length; i++){%><li><span style=\"background-color:<%=segments[i].fillColor%>\"></span><%if(segments[i].label){%><%=segments[i].label%><%}%></li><%}%></ul>"
}
var ctx = $("#top10ItemsChart").get(0).getContext("2d");
var data = [{
value: 2755,
color: "#FFE135",
label: "Bananas: 2,755 (18%)"
. . .
}, {
value: 1048,
color: "#FEA620",
label: "Melons, Cantaloupe: 1,048 (7%)"
}];
var top10PieChart = new Chart(ctx).Pie(data, optionsPie);
$("#pie_legend").html(top10PieChart.generateLegend());
...and yet the pie is stretchier than stretch pants on an elephant.
...然而,馅饼比大象身上的弹力裤更有弹性。
UPDATE 7
更新 7
Maybe there's a configuration problem or something. I decided to "upgrade" to version 2.1.3 of Chart.JS (started out w. version 1.0.2):
可能是配置问题什么的。我决定“升级”到 Chart.JS 的 2.1.3 版(从 1.0.2 版开始):
@*<script src="https://cdnjs.cloudflare.com/ajax/libs/Chart.js/1.0.2/Chart.min.js"></script>*@
<script src="https://cdnjs.cloudflare.com/ajax/libs/Chart.js/2.1.3/Chart.js"></script>
...and copied almost exactly Teo Dragovic's CodePen here.
...并在此处几乎完全复制了 Teo Dragovic 的 CodePen 。
The only things I changed were the names of two CSS class ("table" became "legendTable" and "cell" became "legendCell") and the color of the table border from red to forestgreen, and I get this now:
我唯一改变的是两个 CSS 类的名称(“table”变成了“legendTable”,“cell”变成了“legendCell”)和表格边框的颜色从红色变成了森林绿色,我现在得到了这个:
Do I need to also a reference a Chart.JS CSS file or something?
我是否还需要引用 Chart.JS CSS 文件或其他内容?
采纳答案by B. Clay Shannon
This is what works (more or less) using version 2 of Chart.JS:
这是使用 Chart.JS 的第 2 版(或多或少)有效的方法:
HTML
HTML
<h2 class="sectiontext">Top 10 Items</h2>
<br />
<div class="chart">
<canvas id="top10ItemsChart" class="pie"></canvas>
<div id="pie_legend"></div>
</div>
JQUERY
查询
var data = {
labels: [
"Bananas: 2,755 (18%)",
"Lettuce, Romaine: 2,256 (14%)",
"Melons, Watermelon: 1,637 (10%)",
"Pineapple: 1,608 (10%)",
"Berries: 1,603 (10%)",
"Lettuce, Spring Mix: 1,433 (9%)",
"Broccoli: 1,207 (8%)",
"Melons, Honeydew: 1,076 (7%)",
"Grapes: 1,056 (7%)",
"Melons, Cantaloupe: 1,048 (7%)"
],
datasets: [
{
data: [2755, 2256, 1637, 1608, 1603, 1433, 1207, 1076, 1056, 1048],
backgroundColor: [
"#FFE135",
"#3B5323",
"#fc6c85",
"#ffec89",
"#021c3d",
"#3B5323",
"#046b00",
"#cef45a",
"#421C52",
"#FEA620"
],
}]
};
var optionsPie = {
responsive: true,
scaleBeginAtZero: true
}
var ctx = $("#top10ItemsChart").get(0).getContext("2d");
var top10PieChart = new Chart(ctx,
{
type: 'pie',
data: data,
options: optionsPie
});
$("#top10Legend").html(top10PieChart.generateLegend());
I say, "more or less" because the pie pieces are still pitifully puny:
我说,“或多或少”是因为馅饼仍然微不足道:
回答by Teo Dragovic
I think this what you want: DEMO
我认为这是你想要的:DEMO
First, you need to make canvas
responsive by overriding fixed width and height and wrap it in additional div
that can be used for positioning. I used display: table
for centering elements but setting inner divs to inline-block
also works if you wish for chart and legend to take different amount of space than 50:50.
首先,您需要canvas
通过覆盖固定的宽度和高度来做出响应,并将其包装在div
可用于定位的附加内容中。我用于display: table
居中元素,但inline-block
如果您希望图表和图例占用与 50:50 不同的空间量,也可以将内部 div 设置为也可以使用。
HTML:
HTML:
<div class="table">
<div class="cell">
<canvas id="top10ItemsChart" class="pie"></canvas>
</div>
<div class="cell" id="top10Legend"></div>
</div>
CSS:
CSS:
canvas {
width: 100% !important;
height: auto !important;
}
.table {
border: 1px solid red;
display: table;
width: 100%;
table-layout: fixed;
}
.cell {
display: table-cell;
vertical-align: middle;
}
UPDATE:Did some adjustment based on additional information by OP NEW DEMO
更新:根据 OP NEW DEMO 的附加信息进行了一些调整
HTML:
HTML:
<div class="container">
<div class="row">
<div class="col-md-6">
<div class="topleft">
<h2 class="sectiontext">Top 10 Items</h2>
<br />
<div class="chart">
<div class="pie">
<canvas id="top10ItemsChart" class="pie"></canvas>
</div>
<div class="legend" id="top10Legend">
</div>
</div>
</div>
</div>
</div>
</div>
CSS:
CSS:
.topleft {
margin-top: -4px;
margin-left: 16px;
margin-bottom: 16px;
padding: 16px;
border: 1px solid black;
}
canvas {
width: 100% !important;
height: auto !important;
margin-left: -25%;
}
.chart {
border: 1px solid forestgreen;
width: 100%;
overflow: hidden;
position: relative;
}
.pie {
position: relative;
padding: 10px 0;
// adjust as necessary
padding-left: 10px;
padding-right: 0;
}
.legend {
position: absolute;
right: 10px;
top: 10px;
height: 100%;
// adjust as necessary:
width: 48%;
}
@media (max-width: 480px) {
.legend {
position: relative;
width: 100%;
}
.pie {
margin: 0;
}
}
.pie-legend ul {
list-style: none;
margin: 0;
padding: 0;
width: 300px;
}
.pie-legend span {
display: inline-block;
width: 14px;
height: 12px;
border-radius: 100%;
margin-right: 4px;
margin-bottom: -2px;
}
.pie-legend li {
margin-bottom: 4px;
display: inline-block;
margin-right: 4px;
}
回答by Domenic D.
As @B.ClayShannon mentioned, version 2 is quite a bit different than verison 1. Here is an example of how to customize the legend template using version 2.
正如@B.ClayShannon 提到的,版本 2 与版本 1 有很大不同。以下是如何使用版本 2 自定义图例模板的示例。
options: {
legendCallback: function (chart) {
var text = [];
text.push('<ul class="' + chart.id + '-legend" style="list-style:none">');
for (var i = 0; i < chart.data.datasets[0].data.length; i++) {
text.push('<li><div style="width:10px;height:10px;display:inline-block;background:' + chart.data.datasets[0].backgroundColor[i] + '" /> ');
if (chart.data.labels[i]) {
text.push(chart.data.labels[i]);
}
text.push('</li>');
}
text.push('</ul>');
return text.join('');
},
legend: {display: false},
}
It's not shown directly in the accepted solution above, but to render your legend elsewhere you'll want to call:
它没有直接显示在上面接受的解决方案中,但要在其他地方呈现您的图例,您需要调用:
$("#myChartLegend").html(myChart.generateLegend());
Finally, some HTML to pull it together (note clearfix is a Bootstrap class that :
最后,一些 HTML 将它们组合在一起(注意 clearfix 是一个 Bootstrap 类:
<div class="chart">
<div style="float:left">
<canvas id="myChart" class="pie" style="max-width:300px;"></canvas>
</div>
<div class="legend" id="myChartLegend" style="float:left;"></div>
<div style="clear: both;"/>
</div>