【问题标题】:Importing an svg file into a matplotlib figure将 svg 文件导入 matplotlib 图
【发布时间】:2015-10-05 19:05:08
【问题描述】:

我喜欢制作高质量的绘图,因此尽可能避免光栅化图形。

我正在尝试将 svg 文件导入 matplotlib 图:

import matplotlib.pyplot as plt
earth   = plt.imread('./gfx/earth.svg')
fig, ax = plt.subplots()
im      = ax.imshow(earth)
plt.show()

这适用于 png 完美。有人可以告诉我如何使用 svg 或至少指出我正确的文档。

我知道有人问过类似的问题(但没有回答):here。自那以后有什么变化吗?

附:我知道我可以只导出一个高分辨率的 png 并达到类似的效果。这不是我正在寻找的解决方案。

这是我要导入的图片:

.

【问题讨论】:

  • 附注:如果您有兴趣在地图上绘制数据,cartopy package 就是专门的。

标签: python matplotlib svg python-imaging-library


【解决方案1】:

也许你要找的是svgutils

import svgutils.compose as sc
from IPython.display import SVG # /!\ note the 'SVG' function also in svgutils.compose
import numpy as np

# drawing a random figure on top of your SVG
fig, ax = plt.subplots(1, figsize=(4,4))
ax.plot(np.sin(np.linspace(0,2.*np.pi)), np.cos(np.linspace(0,2.*np.pi)), 'k--', lw=2.)
ax.plot(np.random.randn(20)*.3, np.random.randn(20)*.3, 'ro', label='random sampling')
ax.legend()
ax2 = plt.axes([.2, .2, .2, .2])
ax2.bar([0,1], [70,30])
plt.xticks([0.5,1.5], ['water  ', ' ground'])
plt.yticks([0,50])
plt.title('ratio (%)')
fig.savefig('cover.svg', transparent=True)
# here starts the assembling using svgutils 
sc.Figure("8cm", "8cm", 
    sc.Panel(sc.SVG("./Worldmap_northern.svg").scale(0.405).move(36,29)),
    sc.Panel(sc.SVG("cover.svg"))
    ).save("compose.svg")
SVG('compose.svg')

输出:

【讨论】:

    【解决方案2】:

    致 2021 年来到这里的任何人...

    我建议看看cairosvg
    (conda install -c conda-forge cairosvg)

    https://cairosvg.org/

    import cairosvg
    import matplotlib.pyplot as plt
    from PIL import Image
    from io import BytesIO
    
    img = cairosvg.svg2png("... the content of the svg file ...")
    img = Image.open(BytesIO(img_png))
    plt.imshow(img)
    

    【讨论】:

    • 谢谢,效果很好!
    【解决方案3】:

    SVG(Scalable Vector Graphics)是一种矢量格式,这意味着图像不是由像素组成,而是由可以任意缩放的相对路径组成。

    NumPy/Matplotlib 作为数值计算软件,仅真正适用于像素图形,无法处理svg。我建议首先将 svg 文件转换为例如png 文件,通过在 Inkscape(免费)等软件中打开并保存它。然后,在 Python 中打开导出的png

    或者,在the picture's information page (click on the download button to the right of the picture) 上使用维基媒体提供的png 格式的文件版本。

    如果你真的认为你需要矢量形式,那么,没有办法做到这一点。您始终可以手动将 matplotlib 图形叠加到图形上(使用 matplotlib Artist 在绘图画布上绘制),或通过一些 pycairo 魔术,然后保存。但是 Matplotlib 不能直接使用 svg 内容。

    【讨论】:

    • 感谢您的回复。但是,从我的问题中,你可以看出我对这两种格式的特点有所了解。我还明确指出,使用 png 一切正常。此外,matplotlib 与路径一起使用。每次将图像保存为 eps 或 svg 时,都在保存矢量图形。大多数绘图在保存之前都是可以任意缩放的矢量图形。
    • Matplotlib 可能像svg 一样在内部使用路径,但是使用路径的两件事并不意味着这两件事一起工作。注意我还建议单独生成 matplotlib 图形并将它们合并到第二个手动或脚本步骤中。除非您深入研究 Matplotlib 艺术家并准备手动解析 svg 文件,否则我强烈怀疑您能否让 Matplotlib 使用该文件作为背景。
    • 我没想到这么复杂,会尝试看看解析的东西是如何工作的。您能否编辑您的答案,以便我对其进行投票?
    • @Sasha,完成。请不要过早投票以防止这种情况发生。
    • 我很困惑,因为我可以从 Matplotlib 导出为 svg,但我无法回读
    猜你喜欢
    • 1970-01-01
    • 2018-02-18
    • 2017-07-06
    • 2023-03-29
    • 2017-11-25
    • 2021-06-06
    • 2019-03-23
    • 1970-01-01
    • 2020-02-19
    相关资源
    最近更新 更多