Last Updated on 2021-10-12 by Clay
When we developing a project, SVG (Scalable Vector Graphics) is a good picture format, but sometimes we also need PNG format to build our interface layout.
For example, when I using SVG picture to create a interface by PyQt5, the stripe of my picture is disappear. After I converting the picture to PNG format, if finally displays normally.
So, today I want to record how to use Python to convert a SVG picture to a PNG picture.
SVG
SVG is a image format base on XML, it describe the format of two-dimensional vector graphics via narration.
If we use Python to load a SVG picture:
This is the original picture.
print(open('input/ice.svg', 'r', encoding='utf-8').read())
Output:
<?xml version="1.0" encoding="UTF-8"?>
<svg width="100px" height="100px" viewBox="0 0 100 100" version="1.1" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink">
<!-- Generator: Sketch 50.2 (55047) - http://www.bohemiancoding.com/sketch -->
<title>mdpi/*/icons/svg/ice</title>
<desc>Created with Sketch.</desc>
<defs></defs>
<g id="*/icons/svg/ice" stroke="none" stroke-width="1" fill="none" fill-rule="evenodd">
<g id="Group" transform="translate(17.000000, 1.000000)">
<polygon id="Path-7" fill="#000000" fill-rule="nonzero" points="22.3153336 0 44 17.3574154 44 50.1643429 22.3621974 68 0 50.1930808 0 18.2289582"></polygon>
<polygon id="Path" fill="#AFCCEB" points="22.8494357 8 6 21.5793953 6 47.7995504 22.802651 61 39 47.827855 39 20.7542998"></polygon>
<polygon id="Path-8" fill="#37609F" fill-rule="nonzero" points="21.9136416 20 32 27.8870243 32 42.7034852 21.9638023 51 12 42.6983119 12 28.4119176"></polygon>
<polygon id="Path" fill="#AFCCEB" points="22.0218836 26 17 30.6553527 17 40.4690982 21.9775907 45 27 40.4641075 27 30.2527318"></polygon>
<polygon id="Path-9" fill="#000000" fill-rule="nonzero" points="53.1938749 54 67 66.677861 67 87.0085565 53.1722954 99 39 87.0278418 39 66.6563331"></polygon>
<polygon id="Path" fill="#AFCCEB" points="43 69.3303304 43 85.120844 52.6361735 93 62 85.1400901 62 69.3088463 52.6518923 61"></polygon>
<polygon id="Path-8" fill="#37609F" fill-rule="nonzero" points="52.4525029 69 58 73.3251423 58 81.4502983 52.4800913 86 47 81.4474614 47 73.6129871"></polygon>
</g>
</g>
</svg>
As we can see, this is a file to describe the SVG picture, we can draw the picture from these configures.
Convert SVG to PNG
I use a useful package: svglib to do it. If you use it in the first time, you need to use the following command to download:
pip3 install svglib
If you have interesting, you can refer the document in PyPi: https://pypi.org/project/svglib/
After installing, you just need some simple code to complete your task:
# -*- coding: utf-8 -*-
from svglib.svglib import svg2rlg
from reportlab.graphics import renderPM
drawing = svg2rlg('input/ice.svg')
renderPM.drawToFile(drawing, 'output/ice.png', fmt='PNG')
ice.svg is the input and ice.png is the output.
Output:
As you can see, we use python to convert a svg image to png format.
python3
Traceback (most recent call last):
File “/Users/sriniav/workspace/pypractice/svg2png.py”, line 2, in
from svglib.svglib import svg2rlg
File “/opt/homebrew/lib/python3.9/site-packages/svglib/svglib.py”, line 39, in
from lxml import etree
ImportError: dlopen(/opt/homebrew/lib/python3.9/site-packages/lxml/etree.cpython-39-darwin.so, 2): no suitable image found. Did find:
/opt/homebrew/lib/python3.9/site-packages/lxml/etree.cpython-39-darwin.so: mach-o, but wrong architecture
/opt/homebrew/lib/python3.9/site-packages/lxml/etree.cpython-39-darwin.so: mach-o, but wrong architecture
Looks like a Mac OS package issue…
I can run on Mac OS, the environment is:
Python 3.6.7
svglib 1.1.0
Finally a code that worked. Thanks man
My SVG has some custom fonts and gradients, which are not rendered properly into the png file.
The SVG is shown correct in Firefox, Inkscape and Edge.. so not a problem there.
Doesn’t work in my case. I get the following error:
“Unable to resolve percentage unit without knowing the node name”
To render my SVG into a PDF I use “pdfkit” which works pretty fine, but when it comes to PNG (or any other raster graphics format), no library worked so far 🙁
Pingback: Python Svg To Png? Best 5 Answer - Barkmanoil.com
Traceback (most recent call last):
File “f:/Astrology/jyotiSHYAM/svgtopngtry.py”, line 4, in
drawing = svg2rlg(‘./drawCharts/chart_images/Lagna_chart.svg’)
File “C:\Users\hp\AppData\Local\Programs\Python\Python37-32\lib\site-packages\svglib\svglib.py”, line
1417, in svg2rlg
drawing = svgRenderer.render(svg_root)
File “C:\Users\hp\AppData\Local\Programs\Python\Python37-32\lib\site-packages\svglib\svglib.py”, line
506, in render
view_box = self.get_box(node, default_box=True)
File “C:\Users\hp\AppData\Local\Programs\Python\Python37-32\lib\site-packages\svglib\svglib.py”, line
769, in get_box
return Box(*view_box)
TypeError: __new__() missing 2 required positional arguments: ‘width’ and ‘height’