pythonpygtkwebkitgtk

Some SVG elements not rendering in python webkitgtk application


I'm writing a small application to generate circuit diagrams using python gtk3 bindings with WebKit and SchemDraw. My intention is to use the svg output of SchemDraw (uses matplotlib internally) and render it in a WebView widget. When I load an svg generated by matplotlib (from file and from StringIO) some horizontal and vertical line elements are missing in the WebView window.

I tried opening the same svg files in multiple browsers (Firefox, Google Chrome and Epiphany) and all elements are rendered correctly. I thought Epiphany would be a good test as it seems to use WebView instances, albeit in C.

The gtk program:

import pgi as gi
gi.install_as_gi()
gi.require_version('Gtk', '3.0')
gi.require_version('WebKit', '3.0')
from gi.repository import Gtk
from gi.repository import Gdk
from gi.repository import WebKit
print ("PyGtk v%s" % gi.__version__)

# Test webkit SVG rendering
window = Gtk.Window(title="Hello World")
webview1 = WebKit.WebView()
webview1.open('file:///redacted_path/example.svg')
window.add(webview1)
window.show_all()
window.connect("destroy", Gtk.main_quit)
Gtk.main()

The code that renders example.svg (the example on the SchemDraw website):

import SchemDraw as schem
import SchemDraw.elements as e
d = schem.Drawing()
V1 = d.add(e.SOURCE_V, label='10V')
d.add(e.RES, d='right', label='100K$\Omega$')
d.add(e.CAP, d='down', botlabel='0.1$\mu$F')
d.add(e.LINE, to=V1.start)
d.add(e.GND)
d.draw()
d.save("example.svg")

I suspect there is some more WebView instance setup required to get this working similarly to the browsers I have tested, but I not sure how to proceed here.


Solution

  • I tried out your code on my laptop (Ubuntu 19.10) and it worked. I had to change a few things though (Ubuntu 19.10 features a more up-to-date version of gir-webkitgtk and I additionally saved the SVG to a file and open it through an URL).

    Here is my code with the modifications included:

    #!/usr/bin/env python
    
    import SchemDraw as schem
    import SchemDraw.elements as e
    
    d = schem.Drawing()
    V1 = d.add(e.SOURCE_V, label='10V')
    d.add(e.RES, d='right', label='100K$\Omega$')
    d.add(e.CAP, d='down', botlabel='0.1$\mu$F')
    d.add(e.LINE, to=V1.start)
    d.add(e.GND)
    d.draw()
    d.save("example.svg")
    

    I noticed 'example.svg' was not being automatically saved. So once the window with the circuit opened up I saved it to a SVG file manually using the menus.

    #!/usr/bin/env python
    
    import pgi as gi
    
    gi.install_as_gi()
    gi.require_version('Gtk', '3.0')
    gi.require_version('WebKit2', '4.0')
    from gi.repository import Gtk
    from gi.repository import Gdk
    from gi.repository import WebKit2
    print ("PyGtk v%s" % gi.__version__)
    
    # Test webkit SVG rendering
    url = 'http://127.0.0.1:8001/example.svg'
    window = Gtk.Window(title="Hello World")
    webview1 = WebKit2.WebView()
    webview1.load_uri(url)
    window.add(webview1)
    window.show_all()
    window.connect("destroy", Gtk.main_quit)
    Gtk.main()
    

    Screenshot:

    enter image description here

    It seems to me the SVG is rendered just fine (I cannot notice any elements missing).