如何在Streamlit中创建多组独立的样式化按钮行?
问题:Streamlit多组样式按钮互相干扰的解决方法
我参考《HOW TO STYLE A BUTTON IN STREAMLIT》教程实现了Streamlit按钮样式定制,但遇到问题:点击某组的YES按钮时,其他组的YES按钮也会自动变成选中的绿色状态。尝试过修改按钮数量、定义新的style_button函数,但因为对CSS nth-child规则不熟悉,没能解决问题。需要实现多组互相独立的样式化按钮行。
问题原因
原代码中的CSS选择器div[data-testid*="stHorizontalBlock"]会匹配页面上所有的水平布局块,导致样式会同时作用于所有组内对应位置的按钮,无法区分不同的按钮组。
解决方案
通过给每组按钮添加唯一标识,让CSS样式只作用于目标组内的按钮。具体步骤如下:
- 给
style_button函数新增group_id参数,用于指定目标按钮组 - 修改CSS选择器,限定样式仅作用于指定
group_id对应的容器内的按钮 - 每个按钮组用带唯一testid的容器包裹,实现样式隔离
修改后的完整代码
样式函数部分
def style_button(click_button_i, nb_buttons, group_id): def get_button_indices(button_i): return { 'nth_child': button_i, 'nth_last_child': nb_buttons - button_i + 1, 'group_id': group_id } click_style = """ div[data-testid="button-group-%(group_id)s"] div[data-testid*="stHorizontalBlock"] > div:nth-child(%(nth_child)s):nth-last-child(%(nth_last_child)s) button { border-color: rgb(50,205,50); color: rgb(50,205,50); box-shadow: rgba(50,205,50, 0.5) 0px 0px 0px 0.2rem; outline: currentcolor none medium; } """ unclick_style = """ div[data-testid="button-group-%(group_id)s"] div[data-testid*="stHorizontalBlock"] > div:nth-child(%(nth_child)s):nth-last-child(%(nth_last_child)s) button { pointer-events: none; cursor: not-allowed; opacity: 0.65; filter: alpha(opacity=65); -webkit-box-shadow: none; box-shadow: none; } """ style = "" for i in range(nb_buttons): i += 1 if i == click_button_i: style += click_style % get_button_indices(i) else: style += unclick_style % get_button_indices(i) st.markdown(f"<style>{style}</style>", unsafe_allow_html=True)
主程序部分
# 第一组按钮 st.subheader("这是正确答案吗?") # 用带唯一testid的container包裹按钮组 with st.container(data_testid="button-group-1"): col1, col2 = st.columns([1,1]) with col1: st.button("YES", on_click=style_button, key="a", kwargs={ 'click_button_i': 1, 'nb_buttons': 2, 'group_id': 1 }) with col2: st.button("NO", on_click=style_button, key="b", kwargs={ 'click_button_i': 2, 'nb_buttons': 2, 'group_id': 1 }) st.subheader("这里是其他内容...") # 第二组按钮 st.subheader("这是正确答案吗?") with st.container(data_testid="button-group-2"): col1, col2 = st.columns([1,1]) with col1: st.button("YES", on_click=style_button, key="c", kwargs={ 'click_button_i': 1, 'nb_buttons': 2, 'group_id': 2 }) with col2: st.button("NO", on_click=style_button, key="d", kwargs={ 'click_button_i': 2, 'nb_buttons': 2, 'group_id': 2 })
改动说明
- 新增
group_id参数:让样式函数可以精准定位到目标按钮组 - CSS选择器优化:通过
div[data-testid="button-group-%(group_id)s"]限定样式作用范围,避免影响其他组 - 容器包裹:用
st.container(data_testid="button-group-xxx")给每组按钮添加唯一标识,实现完全隔离
内容的提问来源于stack exchange,提问作者Claudia Unteșu
相关产品推荐
相关产品推荐

