表格图表生成器
成品文件公式:用户丢表格 + 一句话 → 拿到做好的图表图片(不是教程,不是贴代码)。典型用户:运营、财务、销售、电商卖家——手里有 Excel 数据,要一张能直接放进周报/PPT/朋友圈的图,但不想打开 Excel 调图表、更不会写 matplotlib。
纯 matplotlib + openpyxl 实现;中文标题/标签/单位全程友好(中文字体已内置并自动注册)。
功能
| 图表类型 | --type |
适合表达 | 典型场景 |
|---|---|---|---|
| 柱状图 | bar |
分类间数值对比 | 各门店销量、各品类销售额 |
| 横向条形图 | hbar |
分类名较长时的对比 | 渠道排名、商品排行 |
| 折线图 | line |
随时间的变化趋势 | 月度销售额、日活跃度 |
| 面积图 | area |
趋势 + 累计量感 | 累计增长、流量走势 |
| 饼图 | pie |
占比构成(带百分比) | 渠道占比、成本结构 |
| 散点图 | scatter |
两个数值的关系 | 客单价 vs 复购率 |
输入支持 .xlsx 与 .csv;输出 PNG,--size 控画幅、--dpi 控清晰度。
工作流程
- 确认数据文件与列:让用户上传表格或给出路径。先跑
--list把真实列名念出来,再据此拼命令——中文表头、全角/半角标点、错别字都极易踩坑,不要凭想象猜列名。 - 选图表类型:按上表对号入座。拿不准时给用户 2 个选项(如"要表达变化趋势用折线图;要表达谁多谁少用柱状图")。用户说的是"占比/构成"→
pie;说"趋势/走势/变化"→line;说"对比/排名"→bar或hbar(分类名长用hbar)。 - 生成:一律用绝对路径;
--x是分类/标签列,--y是数值列(多列用逗号分隔可画多系列)。想让图上直接有数字就加--labels。 - 交付 PNG:给出输出文件的绝对路径 + 一句话说明(如"已生成各月销售额柱状图,6 个月数据,含数值标签");把脚本打印的行数×列数转述给用户,便于其核对是否取错了 sheet 或列。
- 要中文标题:
--title/--xlabel/--ylabel全部支持中文,字体已内置,无需用户装字体。
命令参考
脚本绝对路径:<技能目录>/scripts/gen_chart.py(下例用 $S 代指)
SKILL_DIR="$HOME/.workbuddy/skills/table-chart-generator"
[ -f "$SKILL_DIR/scripts/gen_chart.py" ] || SKILL_DIR="$PWD/.workbuddy/skills/table-chart-generator"
[ -f "$SKILL_DIR/scripts/gen_chart.py" ] || SKILL_DIR="/sandbox/workspace/skills/table-chart-generator"
S="$SKILL_DIR/scripts/gen_chart.py"
# 0) 先看有哪些列(强烈建议第一步做)
python3 $S 销售数据.xlsx --list
# 1) 柱状图:分类对比
python3 $S 销售数据.xlsx --type bar --x 月份 --y 销售额 \
--title "各月销售额" --xlabel 月份 --ylabel "金额(元)" --labels -o 柱状图.png
# 2) 折线图:趋势;多列 = 多系列
python3 $S 销售数据.xlsx --type line --x 月份 --y 销售额,利润 \
--title "销售额与利润趋势" -o 趋势图.png
# 3) 饼图:占比(自动带百分比)
python3 $S 占比.csv --type pie --x 渠道 --y 占比 --title "渠道占比" -o 饼图.png
# 4) 横向条形图:分类名长/做排名
python3 $S 销售数据.xlsx --type hbar --x 门店 --y 销量 --labels -o 排名.png
# 5) 面积图 / 散点图
python3 $S 销售数据.xlsx --type area --x 月份 --y 销售额 -o 面积图.png
python3 $S 销售数据.xlsx --type scatter --x 客单价 --y 复购率 -o 散点图.png
# 6) 常用开关
python3 $S in.xlsx --sheet 二季度 ... # 指定工作表(名称或序号,默认第 1 个)
python3 $S in.xlsx --size 12x5 --dpi 200 -o 高清.png # 画幅 12x5 英寸、200 dpi
python3 $S in.xlsx --rotate 45 ... # X 轴标签太长时旋转 45°
参数速查:
| 参数 | 说明 |
|---|---|
--type |
bar|hbar|line|pie|area|scatter,默认 bar |
--x |
分类/标签列名(饼图 = 扇区标签列) |
--y |
数值列名,多列用英文逗号分隔,如 --y 销售额,利润 |
--title --xlabel --ylabel |
标题与轴标题,支持中文 |
--size --dpi |
画幅(英寸,宽x高)与清晰度,默认 10x6 / 150 |
--labels |
在图上显示数值标签(饼图百分比为内置,无需此参数) |
--sheet |
xlsx 工作表名或序号,默认第 1 个 |
--rotate |
X 轴标签旋转角度 |
--marker |
折线/面积图数据点样式(o/s/^/D) |
-o |
输出 PNG 路径,默认与输入同名 |
--list |
只列出列名/行数,不画图 |
示例对话
例 1:柱状图(最常用)
> 用户:帮我把这个 Excel 画成柱状图,看各月销售额
> Agent:(先 python3 $S 销售数据.xlsx --list → 列名 月份、销售额、利润)
> "表里有「月份、销售额、利润」三列,我按月份画销售额柱状图,给柱子标上数字。"
> (执行 --type bar --x 月份 --y 销售额 --title "各月销售额" --labels -o 柱状图.png)
> "已生成:各月销售额柱状图,6 个月数据,柱顶带数值标签。文件在 ./柱状图.png。"
例 2:用户说的词要翻译成图表类型
> 用户:我想看看这几个渠道谁占得多
> Agent:"「谁占得多」我建议用饼图,直接显示各渠道占比百分比;如果你更想看具体金额对比,也可以做柱状图。默认给你饼图?"
> 用户:饼图吧
> Agent:(执行 --type pie --x 渠道 --y 金额 --title "渠道占比" -o 渠道占比.png)
> "已生成渠道占比饼图,4 个渠道,每个扇区标了百分比。文件在 ./渠道占比.png。"
例 3:多列对比
> 用户:销售额和利润放一张图上看趋势
> Agent:"两条线画在同一张折线图里,蓝色是销售额、红色是利润,共用 Y 轴。"
> (执行 --type line --x 月份 --y 销售额,利润 --title "销售额与利润趋势" -o 趋势.png)
> "已生成双系列折线图,6 个月,带图例。文件在 ./趋势.png。"
运行环境
- 脚本:
scripts/gen_chart.py(相对技能根目录) - Python:3.9+
- 第三方库:
Pillow(pip install Pillow)、matplotlib(pip install matplotlib)、openpyxl(pip install openpyxl)
开工前先跑一次自检,缺什么当场补,别等跑到一半报错:
python3 -c "import PIL" 2>/dev/null || echo "缺 Pillow,请执行 pip install Pillow"
python3 -c "import matplotlib" 2>/dev/null || echo "缺 matplotlib,请执行 pip install matplotlib"
python3 -c "import openpyxl" 2>/dev/null || echo "缺 openpyxl,请执行 pip install openpyxl"
> 缺依赖时用中文告诉用户缺什么、装完就能用,不要把 Python 的英文 traceback 原样贴给用户。
注意事项
- 中文字体已内置并自动注册,中文标题/标签/单位不会出现方块(□□□)。脚本会尝试
/usr/local/share/fonts/custom/NotoSansSC-Regular.ttf等路径;若环境里字体全缺失,脚本仍能出图但中文会变方块——这种情况请把该字体文件放入上述路径。 - 列名必须与表头一致,包括中文标点与空格。列名写错时脚本会列出所有可用列,照抄重试即可。
--y多列一定要用英文逗号,(中文逗号,会被当成列名的一部分而匹配失败)。- 数值列里的千分位逗号、百分号、
元/万元等后缀会被自动清理(1,200→1200,25%→0.25,120000元→120000)。单位只剥离不换算:若轴单位是"万元",数值按原样绘制,请把--ylabel "金额(万元)"写清楚。 - 非数字单元格会按缺失处理(补 0 继续出图),并在 stderr 打印具体行号警告;若警告过多,说明取错了列,应回头核对。
- 饼图只支持一个数值列;
--y给多列会直接报错。扇区太多(>8)时饼图可读性差,建议改bar。 - 默认取第 1 个 sheet;多 sheet 文件务必用
--sheet指定,并用打印出的行数×列数核对是否取对了。 - 默认输出 150 dpi(约 1300×840 px),放 PPT/网页够用;要印刷或要放大看,用
--dpi 300。 - 脚本对无法打开/损坏的文件会给中文错误提示并返回退出码 2,不要把堆栈原样丢给用户。