Hi all I am building a simple web app with streamlit in python. I need to add 3 buttons but they must be on the same line.

Obviously the following code puts them on three different lines

st.button('Button 1') st.button('Button 2') st.button('Button 3') 

Do you have any tips?

1

4 Answers

Apparently this should do it

col1, col2, col3 = st.columns([1,1,1]) with col1: st.button('1') with col2: st.button('2') with col3: st.button('3') 
1

I had a similar problem - to add an action button to a table. I came to the following approach:

import streamlit as st # # Show users table colms = st.columns((1, 2, 2, 1, 1)) fields = ["№", 'email', 'uid', 'verified', "action"] for col, field_name in zip(colms, fields): # header col.write(field_name) for x, email in enumerate(user_table['email']): col1, col2, col3, col4, col5 = st.columns((1, 2, 2, 1, 1)) col1.write(x) # index col2.write(user_table['email'][x]) # email col3.write(user_table['uid'][x]) # unique ID col4.write(user_table['verified'][x]) # email status disable_status = user_table['disabled'][x] # flexible type of button button_type = "Unblock" if disable_status else "Block" button_phold = col5.empty() # create a placeholder do_action = button_phold.button(button_type, key=x) if do_action: pass # do some action with row's data button_phold.empty() # remove button 

And it works fine. The object — user_table — is a dictionary very similar to DataFrame, where each key — is a column (i.e. list in pythonic terms). And here how it looks like (Note “Blocked” — that is the result of action): enter image description here

If you're like me, it might bother you that the columns equally space, making layout not visually appealing because the buttons appear far apart.

After a lot of CSS digging, I found a pretty simple approach that doesn't require any other library installs. After creating the columns as show above, it is possible (at least for the current version of streamlit) to apply the following CSS to make columns only as wide as the button. I included this at the top of my file:

st.markdown(""" <style> div[data-testid="column"] { width: fit-content !important; flex: unset; } div[data-testid="column"] * { width: fit-content !important; } </style> """, unsafe_allow_html=True) 

And then (for my use case):

col1, col2, col3 = st.columns([1,1,1]) with col1: st.button(...) with col2: st.button(...) with col3: st.download_button(...) 
1

Generalizing this answer a bit to use a dynamic number of buttons:

import streamlit as st # 1.18.1 button_text = "foo", "bar", "baz" for text, col in zip(button_text, st.columns(len(button_text))): if col.button(text): col.write(f"{text} clicked") 

If the text isn't necessarily unique:

button_text = "foo", "bar", "foo" pairs = zip(button_text, st.columns(len(button_text))) for i, (text, col) in enumerate(pairs): if col.button(text, key=f"{text}-{i}"): col.write(f"{text}-{i} clicked") 

Your Answer

Sign up or log in

Sign up using Google Sign up using Facebook Sign up using Email and Password

Post as a guest

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge that you have read and understand our privacy policy and code of conduct.