mcpField
G
graphing

graphing

github.com/anthropics数据与数据库7451 次安装3 周前更新
代码仓库

关于 graphing

用于制作静态或交互式图表的绘图技能与 Python 工具包。它提供统一样式和导出辅助功能,图表类型与构建由使用者决定。

主要功能

  1. 01Matplotlib 主题与调色板
  2. 02标题和说明文字排版
  3. 03导出 PNG 和 SVG
  4. 04生成离线交互式 HTML
  5. 05处理常见数据问题的辅助函数

适用场景

  1. 01制作样式统一的图表
  2. 02将图表导出为 PNG 或 SVG
  3. 03离线分享交互式图表
  4. 04处理时间序列中的日期缺口

安装

复制下面的命令,在终端中运行。

$npx skills add https://github.com/anthropics/claude-tag-plugins --skill graphing

安装后在 Claude Code 中输入/graphing确认已加载。

附带文件scripts/chartkit.py

详细介绍

绘图

绘图代码由你编写。该工具包提供了适用于所有图表、应保持一致的部分:排版、根据背景推导颜色、标题和说明文字框架,以及离线 HTML 打包。图表本身的一切设计,都由你根据眼前的数据来判断。

基本组件

将此技能的 scripts/ 目录加入 sys.path,以导入 chartkit。请使用绝对路径,而不是相对路径,因为你的工作目录是用户的项目目录。以下示例中使用 /path/to/graphing/scripts 表示该路径;请替换为实际路径。

相关基本组件:

  • theme(bg, font):设置 matplotlib rcParams 并返回解析后的颜色。前景色根据背景亮度推导,因此深色 bg 会生成适用于深色主题的图表。字段:bg dark text muted grid spine accent secondary series font_css。
  • palette(n, base):生成 n 种颜色。不指定 base 时,按顺序循环使用默认系列色;指定十六进制 base 时,会以该颜色为基础生成渐变;指定列表时,会循环使用列表中的颜色。
  • finish(ax, title, subtitle, source):提供排版框架,包括左对齐的粗体标题、柔和的副标题和简短的来源说明。
  • save(fig, stem, formats, dpi):保存为 stem.png、stem.svg 或两者兼有。返回文件路径。
  • write_html(out, data, component_js, title, bg, font):生成独立的交互式页面。从 third_party/ 内嵌 React、ReactDOM、react-is 和 Recharts,因此该文件可离线打开。你的组件会读取 window.__CHART_DATA__,并渲染到 #root 中。
  • zero_fill_days(pairs) rolling_mean(values, w) log_floor(values):用于处理下方所列易错点的小型数据辅助函数。仅在适用时使用。

步骤

  1. 查看数据,判断适合采用什么图表。 根据数据的形状、数量和含义来选择:时间趋势适合折线图或按日柱状图;类别排名适合水平条形图;切片较少的整体构成适合饼图;相关性适合散点图。你不必局限于这些选择:堆叠面积图、双轴图、小多图、标注阈值等都可以通过代码实现。

  2. 根据上下文推断颜色。 查看对话和记忆中的设计线索,例如 tailwind 配置、CSS 变量或品牌指南;同时考虑数据的语义(例如,错误用红色或琥珀色表示,成功用绿色表示)。将目标背景传给 theme(bg=...),将品牌颜色传给 palette(base=...) 或直接使用。只有在无法推断时才使用默认值。字体默认为 Inter;只有用户指定了字体,或目标位置有明确记录的品牌字体时,才更改字体。

  3. 在临时工作区编写简短脚本,导入 chartkit,使用纯 matplotlib 构建图形(交互式输出则使用 Recharts 组件),调用 finish 并保存。

  4. 渲染并检查结果。 交付前重新读取 PNG 并亲自检查:标签是否清晰易读、是否存在重叠、颜色是否容易区分,以及数据的核心信息是否清楚呈现。持续修正并重新渲染,直到效果符合要求。

图表脚本的结构

通过 matplotlib 输出 PNG 或 SVG:

import sys
sys.path.insert(0, "/path/to/graphing/scripts")
import chartkit as ck
import matplotlib.pyplot as plt

c = ck.theme()                       # or theme(bg="#0f1419") for a dark surface
fig, ax = plt.subplots(figsize=(10, 5))
# ...plain matplotlib against the data, using c.accent, c.secondary, ck.palette(...)
ck.finish(ax, title="What the chart shows", subtitle="scope or time range",
          source="source: where the data came from, date")
print(ck.save(fig, "out/report", formats=("png", "svg")))

使用 Recharts 输出交互式 HTML,以不含 JSX、无需构建步骤的 React.createElement 编写:

component = """
(function () {
  var e = React.createElement
  var R = window.Recharts
  var DATA = window.__CHART_DATA__
  function App() {
    return e(R.ResponsiveContainer, { width: "100%", height: 420 },
      e(R.LineChart, { data: DATA },
        e(R.CartesianGrid, { stroke: "GRID", vertical: false }),
        e(R.XAxis, { dataKey: "x" }), e(R.YAxis, null),
        e(R.Tooltip, null),
        e(R.Line, { dataKey: "y", stroke: "ACCENT", strokeWidth: 2.4,
                    dot: false, isAnimationActive: false })))
  }
  ReactDOM.createRoot(document.getElementById("root")).render(e(App))
})()
"""
ck.write_html("out/report.html", data, component, title="What the chart shows")

将主题中的实际颜色替换到组件中,并将 isAnimationActive: false 保留下来,以确保文件打开时图表已完整呈现。

判断,而非标志

以下是优质图表的默认做法。若数据表明有更好的选择,则可以偏离。

  • 仅当 x 轴标签会彼此重叠时才旋转。较短的标签保持水平。
  • 类别较少时限制柱宽。两根柱子不应从画布一边铺满到另一边。
  • 类别大约不超过十几个时,为柱子标注数值。坐标轴和网格线用于读取趋势,而非精确数值。
  • 除非类别有自然顺序,否则按数值对分类柱状图排序。
  • 较长的类别名称用水平柱状图更易阅读。
  • 标题说明图表展示的内容。副标题注明时间范围或范围。来源说明注明数据来自何处以及时间。只有经过慎重考虑后才省略其中任何一项。
  • 仅在有多个系列时使用图例。单个系列由标题命名。
  • 在图表上标注重要信息:部署线、阈值、峰值,或用户询问的异常。读者并不需要的标注会造成杂乱。

这些辅助工具旨在解决的问题

  • 日历缺口:时间序列缺少某些日期时,在连续坐标轴上会产生误导。zero_fill_days 会用零填补这些缺口。如果零会造成误导(数据采样稀疏,而非没有事件),则不要使用。
  • 滚动平均:rolling_mean 是向后计算的,前面的点会对截至当时已有的数据求平均。对于截至今天的数据,不要将其居中。
  • 对数刻度:数值等于坐标轴最小值的柱子高度为零。log_floor 会将下限设为低一个数量级。
  • 负值:matplotlib 可以处理负值,但要确认 y 轴范围包含负值,并在柱子正负都有时添加零线。Recharts 的 y 轴范围默认从零开始,因此数据为负值或使用对数刻度时,请在 YAxis 上传入显式的 domain。

验证

执行最简渲染并查看结果。

python3 -c "
import sys
sys.path.insert(0, '/path/to/graphing/scripts')
import chartkit as ck
import matplotlib.pyplot as plt
c = ck.theme()
fig, ax = plt.subplots(figsize=(8, 4))
ax.bar(['A', 'B', 'C'], [10, 30, 20], color=c.accent, width=0.5)
ck.finish(ax, title='chartkit smoke test')
print(ck.save(fig, '/tmp/ck_smoke'))
"

确认已写入非空 PNG,然后读回该文件并检查渲染是否正确。

评论

支持 Markdown