I’m trying to create an web application using python streamlit, that displays a grid of images.
User’s can then click an image, perform an operation, and update the clicked image.
The problem I’m facing is that streamlit’s st.session_state seems to bring back values for clicked images, even when I try to wipe them.
Streamlit doesn’t have a solution to handle images clicks, so i used either streamlit_image_coordinates and st-click-detector. Both components reproduce this problem.
One solution for this problem is to set a key that is unique for each image, or every re-run. I used time.time() for this.
It’s not a great solution however, since it adds a significant load time on the application. From my understanding, streamlit does less processing on widgets (it this case, an image) for which their st.session_state.key did not change.
Here is a simple code, which I hope shows this problem:
import streamlit as st
from streamlit_image_coordinates import streamlit_image_coordinates as st_ic
st.subheader("START")
st.write(st.session_state)
grid = [[0, 1, 0],
[1, 1, 1],
[0, 1, 0]]
image_default = "data/sprites/Empty_Module.png"
col_states, col_grid = st.columns([2,2], gap="small")
# Store click in session_state.click
for k, v in st.session_state.items():
if k.startswith(("0_", "1_", "2_")) and v:
st.session_state.click = k
break
col_states.subheader("BEFORE SANITIZATION")
col_states.write(st.session_state)
# Set states for image coords to None
for k, v in st.session_state.items():
if k.startswith(("0_", "1_", "2_")) and v:
st.session_state[k] = None
col_states.subheader("AFTER SANITIZATION")
col_states.write(st.session_state)
# Main loop to generate grid layout
with col_grid:
for row_idx, row in enumerate(grid):
cols = st.columns(len(row), gap="small")
for cell_idx, cell in enumerate(cols):
if row[cell_idx] != 0:
with cell:
# Image coords are stored with key int_int in session_state
cell_key = f"{row_idx}_{cell_idx}"
st_ic(source=image_default,
key=f"{cell_key}",
use_column_width="always")
col_states.subheader("AFTER LOOP")
col_states.write(st.session_state)