如何使用Vega/Vega-Lite创建响应式饼图并解决内容裁切问题
修复方案
核心优化点
- 容器层面:将原本行内的
span容器改为块级元素,设置宽度100%、最小高度,无需手动固定尺寸,天然跟随屏幕宽度自适应 - 图表配置层面:设置
width和height为container,让图表尺寸直接继承容器大小 - 动态半径:用Vega-Lite内置的
expr表达式,基于当前容器的宽高动态计算饼图半径,无需额外写JS监听重绘 - 裁切修复:给图表配置左侧内边距,预留图例展示空间,避免内容被裁切
完整可运行代码
<!DOCTYPE html> <html> <head> <title>Data visualizer</title> <meta charset="utf-8" /> <meta name="viewport" content="width=device-width, initial-scale=1.0" /> <script src="https://cdn.jsdelivr.net/npm/vega@5"></script> <script src="https://cdn.jsdelivr.net/npm/vega-lite@5"></script> <script src="https://cdn.jsdelivr.net/npm/vega-embed@6"></script> <style> /* 容器自适应,无需固定宽高 */ #pie-chart { display: block; width: 100%; min-height: 400px; } </style> </head> <body> <div id="pie-chart"></div> <script> vegaEmbed("#pie-chart", { $schema: "https://vega.github.io/schema/vega-lite/v5.json", autosize: { type: "fit", contains: "padding", resize: true }, // 图表尺寸跟随容器 width: "container", height: "container", // 预留左侧边距解决裁切问题 padding: {left: 30, right: 10, top: 10, bottom: 10}, layer: [ { mark: { type: "arc", // 动态计算内外半径,取容器宽高最小值的比例,保证不超出边界 innerRadius: {expr: "min(containerWidth, containerHeight) * 0.15"}, outerRadius: {expr: "min(containerWidth, containerHeight) * 0.35"} } }, { mark: { type: "text", // 文字半径取内外半径中间值 radius: {expr: "min(containerWidth, containerHeight) * 0.25"}, fill: "white" }, encoding: { text: {field: "count", type: "nominal"}, }, }, ], encoding: { color: { field: "name", type: "nominal", }, theta: { field: "count", type: "quantitative", stack: true, }, }, data: { values: [ {name: "a", count: 21}, {name: "b", count: 6}, {name: "c", count: 3}, {name: "d", count: 3}, {name: "e", count: 2}, {name: "f", count: 1}, {name: "g", count: 2}, {name: "h", count: 1}, ], }, }); </script> </body> </html>
内容的提问来源于stack exchange,提问作者Noam I.
相关产品推荐
相关产品推荐

