I want to embed svg charts generated with PyGal ( https://www.pygal.org/) into my streamlit app.
I can do this using streamlite.image but the resulting svg graphic is not interactive, it is just a static image. The hover effect ( and the effect of clicking on legend to toggle data rows) is not working.
I tried to use the streamlit.components.v1.html component and it works, i get an interactive svg graphic with working hover effect…however, i only get the first ~200 pixels from top, then the rest of the svg graphic is empty. I tried putting the whole thing into an st.container with a given height, but no improvement.
I want the fully working svg graphic (with hover effect) displayed in streamlit in its full height. How can i do this ?
import streamlit as st
import pygal # install using pip install pygal
from streamlit.components.v1 import html
# create an svg using pygal
gauge_chart = pygal.Gauge(human_readable=True)
gauge_chart.title = f'speed in km/h'
gauge_chart.range = [0, 220]
gauge_chart.add('old car', 130)
gauge_chart.add("new car", 180)
gauge_chart.show_legend = True
st.html("<hr> without hover effect </hr>")
# put it into streamlit as static image (no hover effect)
st.image(gauge_chart.render(is_unicode=True), width=500)
# put it into streamlit as fully working svg with hover effect
def render_svg(svg_string):
"""Renders the given svg string."""
c = st.container()
with c:
html(svg_string)
st.html("<hr> with hover effect (but only top ~200 pixels are visible) </hr>")
with st.container(height=800):
render_svg(gauge_chart.render(is_unicode=True))
i find only a “viewbox” tag inside the svg-element produced by pygal. If i change it from 800x600 into 1600x1200 the resulting pygal chart is more visible ( circa 75%, but it is smaller).
Is the viewbox not compatible with a streamlit container ?
def render_svg(svg_string):
"""Renders the given svg string."""
c = st.container(height=800)
svg_string2 = svg_string.replace('viewBox="0 0 800 600"', 'viewBox="0 0 1600 1200"')
with c:
html(svg_string2)
import streamlit as st
import pygal # install using pip install pygal
from streamlit.components.v1 import html
# create an svg using pygal
gauge_chart = pygal.Gauge(human_readable=True) #, height=400)
gauge_chart.title = f'speed in km/h'
gauge_chart.range = [0, 220]
gauge_chart.add('old car', 130)
gauge_chart.add("new car", 180)
gauge_chart.show_legend = True
st.html("<hr> without hover effect </hr>")
# put it into streamlit as static image (no hover effect)
st.image(gauge_chart.render(is_unicode=True) , width=800) ## width argument is necessary here
# put it into streamlit as fully working svg with hover effect
def render_svg(svg_string):
"""Renders the given svg string."""
c = st.container()
with c:
html(svg_string, height=600) # <--- put the height in pixels here
st.html("<hr> with hover effect </hr>")
with st.container():
render_svg(gauge_chart.render(is_unicode=True))
#print(gauge_chart.render(is_unicode=True))