You need to enable JavaScript to run this app.
最新活动
大模型
产品
解决方案
定价
生态与合作
支持与服务
开发者
了解我们

如何通过命令行或程序实现SVG取消分组并提取转换后路径数据

刚好做过类似的需求,给你几个靠谱的自动处理方案,不用再手动开Inkscape点来点去啦:

方案一:用Inkscape命令行(最贴近你手动操作的流程)

既然你本来就是用Inkscape手动处理,那直接用它的命令行工具就能完美模拟手动取消分组、应用变换的流程,还能批量处理文件。

完整命令

inkscape input.svg --actions="select-all;ungroup;select-all;object-to-path;select-all;apply-transform;export-plain-svg:output_transformed.svg"

命令拆解

  • select-all: 选中SVG里所有元素
  • ungroup: 取消所有嵌套分组,把路径从g容器里解放出来
  • object-to-path: 把矩形、圆形等基础形状全部转成路径(确保所有图形都能被变换处理)
  • apply-transform: 将所有元素的transform(包括你提到的translate(0.000000,1080.000000) scale(0.100000,-0.100000))直接应用到路径坐标上,移除transform属性,让路径的d数据直接对应viewBox="0 0 1920 1080"坐标系
  • export-plain-svg: 导出干净的SVG文件,去掉多余的元数据和注释

提取路径数据

如果只需要路径的d属性内容,不用完整SVG,可以结合grepsed过滤:

grep -o 'd="[^"]*"' output_transformed.svg | sed 's/d="//;s/"$//' > paths.txt

执行后paths.txt里每行就是一个路径的d数据,直接能用。

方案二:用Python脚本(更灵活,适合自定义处理)

如果需要更精细的控制(比如处理复杂嵌套的transform、自定义坐标转换逻辑),用Python的svgpathtools库直接解析和修改路径是最佳选择,不需要依赖Inkscape。

步骤1:安装依赖

pip install svgpathtools

步骤2:编写处理脚本

新建extract_transformed_paths.py文件,内容如下:

from svgpathtools import svg2paths, wsvg, Path, Line, Arc, CubicBezier, QuadraticBezier

# 读取原始SVG的路径和属性
paths, _ = svg2paths('input.svg')

# 定义逆变换:把路径从g的变换空间转换回1920x1080坐标系
# 原始变换:translate(0,1080) → scale(0.1, -0.1)
# 逆变换:先scale(10, -10) → 再translate(0, -1080)
def transform_point(point):
    x = 10 * point.real
    y = -10 * (point.imag - 1080)
    return complex(x, y)

transformed_paths = []
for path in paths:
    transformed_segments = []
    for seg in path:
        if isinstance(seg, Line):
            transformed_segments.append(Line(transform_point(seg.start), transform_point(seg.end)))
        elif isinstance(seg, CubicBezier):
            transformed_segments.append(CubicBezier(
                transform_point(seg.p0), transform_point(seg.p1),
                transform_point(seg.p2), transform_point(seg.p3)
            ))
        elif isinstance(seg, QuadraticBezier):
            transformed_segments.append(QuadraticBezier(
                transform_point(seg.p0), transform_point(seg.p1),
                transform_point(seg.p2)
            ))
        elif isinstance(seg, Arc):
            # 圆弧的半径也要同步缩放10倍
            new_r = (10 * seg.rx, 10 * seg.ry)
            transformed_segments.append(Arc(
                transform_point(seg.start), new_r, seg.rotation,
                seg.large_arc, seg.sweep, transform_point(seg.end)
            ))
    transformed_paths.append(Path(*transformed_segments))

# 保存变换后的SVG文件
wsvg(transformed_paths, filename='output_transformed.svg', viewBox='0 0 1920 1080')

# 直接提取所有路径的d属性到文本文件
with open('paths.txt', 'w') as f:
    for path in transformed_paths:
        f.write(path.d() + '\n')

运行脚本

python extract_transformed_paths.py

执行后会生成output_transformed.svg(变换后的完整SVG)和paths.txt(纯路径d数据)。

方案三:用轻量级命令行工具(适合服务器/无GUI环境)

如果你的环境没有GUI,Inkscape命令行又太笨重,可以用librsvg(轻量级SVG渲染工具)结合xmlstarlet(XML处理工具)来完成,体积小,速度快。

安装工具

  • Ubuntu/Debian:sudo apt install librsvg2-bin xmlstarlet
  • macOS:brew install librsvg xmlstarlet

处理命令

# 应用所有变换并导出干净的SVG
rsvg-convert --format svg --output output_transformed.svg input.svg
# 提取所有路径的d属性到文本文件
xmlstarlet sel -N svg=http://www.w3.org/2000/svg -t -m "//svg:path" -v "@d" -n output_transformed.svg > paths.txt

rsvg-convert会自动解析并应用所有transform,导出的SVG路径坐标就是1920x1080坐标系下的,再用xmlstarlet提取路径数据即可。


内容的提问来源于stack exchange,提问作者Noan Cloarec

火山引擎 最新活动