Open ChazRuler opened 1 month ago
sac.buttons callback args is still broken.
def callback(*args, **kwargs):
print(f"callback args: {args}")
def test():
key = uri + f"_{name}_buttons"
print(f"key: {key}")
sac.buttons(
[sac.ButtonsItem(uri) for uri in uris],
index=None,
size='xs',
key=key,
on_change=callback, args=(key,)
)
The above code is broken with an upgrade if streamlit1.36.0, the callback args print out empty tuple: ()
Streamlit==1.39.0 should use Streamlit's custom component onchange callback API,I modified the files in the directory streamlit_antd_components/utils/component_func.py according to the official method as follows, and it worked. `def component(id, kw, default=None, key=None, on_change=None): if key is not None and key not in st.session_state: st.session_state[key] = default
_on_change = None if on_change is not None: if key is None: st.error("You must pass a key if you want to use the on_change callback") else: def _on_change(): return on_change(key)
if key is not None: st_value = convert_session_value(id, st.session_state[key], kw.get('kv'), kw.get('return_index')) kw.update({"stValue": st_value}) else: kw.update({"stValue": None}) return component_func(id=id, kw=json.loads(json.dumps(kw, cls=CustomEncoder)), default=default, key=key, on_change=_on_change if _on_change is not None else None)`
Let me refine this—two modifications are needed to make it work:
For widgets.buttons.buttons, need to add the on_change parameter when returning, like this:
# in def buttons, pre as below:
# return component(id=get_func_name(), kw=kw, default=default, key=key)
return component(id=get_func_name(), kw=kw, default=default, key=key, on_change=on_change)
As you mentioned, modify the utils.component_func.component function.
def component(id, kw, default=None, key=None, on_change=None):
point_function()
if key is not None and key not in st.session_state:
st.session_state[key] = default
_on_change = None
if on_change is not None:
if key is None:
st.error("You must pass a key if you want to use the on_change callback")
else:
def _on_change():
return on_change(key)
if key is not None:
st_value = convert_session_value(
id, st.session_state[key], kw.get('kv'), kw.get('return_index')
)
kw.update({"stValue": st_value})
else:
kw.update({"stValue": None})
return component_func(
id=id,
kw=json.loads(json.dumps(kw, cls=CustomEncoder)),
default=default,
key=key,
on_change=_on_change if _on_change is not None else None
)
Currently, I am using it without any issues, and it perfectly triggers the corresponding function only when the button is clicked. Here is a sample of my code:
def show_rules():
def callback(*args, **kwargs):
print(f"callback args: {args}, { st.session_state.get('sac.rule_buttons')}")
rule_buttons_callbacks[st.session_state['sac.rule_buttons']]['callback']()
rule_buttons_callbacks = {
'Choose New CSV': {
'callback': select_tables_in_config_dialog,
'icon': "floppy2"
},
}
sac.buttons([
sac.ButtonsItem(label=label, icon=details['icon'])
for label, details in rule_buttons_callbacks.items()
],
key='sac.rule_buttons',
use_container_width=True,
index=None,
on_change=callback,
color="#00A355")
I'm affected by this issue too. Any news from the maintainers about a fix release on this issue?
Streamlit==1.39.0 streamlit_antd_components==0.3.2