HTML子弹图是用+CSS或SVG实现的非原生可视化组件,含背景条(范围)、主条(实际值)、目标线(目标值)三层结构;纯CSS方案依赖百分比宽度与绝对定位,SVG方案更精准可交互。

什么是 HTML 子弹图(Bullet Chart)?它不是原生 HTML 元素
HTML 本身没有 <bullet-chart></bullet-chart> 标签,子弹图必须用组合方式实现:通常基于 <div> + CSS 定位/宽度控制 + 可选的 SVG 或 Canvas 渲染。核心是三个视觉层:背景条(范围)、主条(实际值)、标记线(目标值)。别指望纯 HTML 标签一行搞定。<h3>用纯 CSS 实现最简子弹图(无 JS,兼容性好)</h3>
<p>适合静态数据、仪表盘嵌入、邮件内联样式等场景。关键靠嵌套 <code><div> 和百分比宽度控制,避免 flex 布局在旧版 Outlook 中失效。<ul>
<li>外层容器设 <code>position: relative,高度固定(如 24px)
background-color + width: 100% 占满width 按比例计算(如实际值 / 最大值 × 100%)::after 伪元素 + border-left 实现,left 值同样按比例算calc() 在 width 中混用单位,建议预计算好百分比值<div class="bullet">
<div class="bullet-bg"></div>
<div class="bullet-bar" style="width: 68%;"></div>
<div class="bullet-target" style="left: 75%;"></div>
</div>
<p>.bullet { position: relative; height: 24px; }
.bullet-bg { background: #e0e0e0; width: 100%; height: 8px; margin: 8px 0; }
.bullet-bar { background: #2196f3; height: 8px; position: absolute; top: 8px; }
.bullet-target::after {
content: ""; border-left: 2px solid #ff5722; height: 16px;
position: absolute; top: 4px; left: 0;
}用 SVG 实现更精准、可交互的子弹图
当需要缩放不失真、动态更新、绑定 tooltip 或点击事件时,SVG 是更稳妥的选择。重点在于 <rect></rect> 的 x/width 计算和 <line></line> 的 x1 定位。
- 所有坐标值必须是数字,不能带单位(如
"120px"错误,应写120) - 目标线推荐用
<line></line>而非<rect></rect>,避免锯齿 - 若需响应式,用
viewBox+ CSSwidth: 100%,不要设固定width/height属性 - Chrome 对
stroke-dasharray渲染有细微偏移,目标线建议加shape-rendering="crispEdges"
<svg viewBox="0 0 300 40" class="bullet-svg">
<!-- 背景条 -->
<rect x="0" y="16" width="300" height="8" fill="#e0e0e0"/>
<!-- 主条 -->
<rect x="0" y="16" width="204" height="8" fill="#2196f3"/>
<!-- 目标线 -->
<line x1="225" y1="8" x2="225" y2="32" stroke="#ff5722" stroke-width="2"
shape-rendering="crispEdges"/>
</svg>常见报错和渲染异常怎么快速定位
子弹图出问题,八成卡在比例计算或盒模型上。先检查这几个点:
将 Markdown 文章转换为微信公众号兼容的纯 HTML 格式。当用户要求"转成微信格式"、"生成公众号文章 HTML"、"排版到微信草稿箱"、"微信粘贴格式"时触发。输出带内联样式的纯 HTML,微信编辑器可直接渲染,无需额外适配。支持标题、段落、列表、粗体、行内代码、表格、引用块、代码块、配图的完整转换。
立即学习“前端免费学习笔记(深入)”;
-
width值为NaN或负数 → 检查除零、空字符串转数字(parseInt("") === NaN) - 目标线偏左/偏右 → 确认是否用了
getBoundingClientRect()获取父容器宽后又忘了减去 padding - 在 Safari 中主条不显示 → 检查是否误设了
overflow: hidden在父容器,且主条position: absolute超出裁剪范围 - 邮件客户端中完全空白 → Outlook 不支持
position: absolute和大部分伪元素,必须退回 table 布局 + 内联样式
真正难的不是画出来,而是让不同设备、不同邮件客户端、不同缩放比例下都对齐那根目标线。数值精度、CSS 重置、viewport 设置,一个没控住就偏 2 像素。


















