Skip to content

Commit c3a56d8

Browse files
committed
Navbar: Fix navigation component;
Multilit: Fix url and native navigation control and optimize spawn multiple bad containers. Remove space on styles and COI instances Loader: Fix bad css selector;
1 parent e0b50d6 commit c3a56d8

File tree

19 files changed

+342
-221
lines changed

19 files changed

+342
-221
lines changed

VERSION

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1 +1 @@
1-
0.7.2
1+
0.7.3

examples/components/navbar/native_streamlit_multipage/app.py

Lines changed: 37 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -96,7 +96,37 @@ def account():
9696

9797

9898
def settings():
99-
st.button("Theme")
99+
menu_definition = [
100+
{
101+
"id": "account",
102+
"label": "Account",
103+
"icon": "material/account_circle",
104+
"ttip": "Account",
105+
},
106+
{
107+
"id": "preferences",
108+
"label": "Preferences",
109+
"icon": "material/settings",
110+
"ttip": "Preferences",
111+
}
112+
]
113+
# default_definition = menu_definition.pop(0)
114+
selected_tab = st_navbar(
115+
menu_definition,
116+
sticky_nav=False,
117+
theme_changer=False,
118+
# home_definition=default_definition
119+
)
120+
121+
if selected_tab == "account":
122+
st.subheader("Account settings")
123+
st.text_input("Email", value="", placeholder="Email")
124+
st.text_input("Username", value="", placeholder="Username")
125+
st.text_input("Full name", value="", placeholder="Full name")
126+
elif selected_tab == "preferences":
127+
st.subheader("Preferences")
128+
st.checkbox("Enable notifications", value=True)
129+
st.checkbox("Dark mode", value=False)
100130

101131

102132
def logout():
@@ -124,7 +154,8 @@ def logout():
124154
logout_page = st.Page(logout, title="Log out", icon=":material/logout:", url_path="logout")
125155

126156
# HERE IS THE CHANGE
127-
from streamlit_plugins.components.navbar import NavbarPositionType, st_navigation, st_switch_home
157+
from streamlit_plugins.components.navbar import NavbarPositionType, st_navigation, st_switch_home, st_navbar, \
158+
set_force_next_page, st_switch_page
128159

129160
my_sidebar()
130161

@@ -156,10 +187,8 @@ def logout():
156187
)
157188
print(f"{page.title=}, {native_way=}, {sticky_nav=}, {position_mode=}")
158189
print()
159-
if st.session_state.logged_in:
160-
# SOME TEXT ABOVE THE NAVBAR
161-
page.run()
162190

163-
else:
164-
login_page._can_be_called = True
165-
login_page.run()
191+
if not st.session_state.logged_in and page._script_hash != login_page._script_hash:
192+
st_switch_page(login_page._script_hash, native_way=True)
193+
194+
page.run()

examples/framework/multi_page.py

Lines changed: 34 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -53,7 +53,7 @@ def run():
5353

5454
multilit = Multilit(
5555
title="Demo", nav_horizontal=True, layout='wide', favicon="📚",
56-
use_st_navigation_navbar=native_way, allow_url_nav=True,
56+
use_st_navigation=native_way, allow_url_nav=False,
5757
navbar_sticky=sticky_nav, navbar_mode=position_mode,
5858
use_cookie_cache=True, sidebar_state='auto',
5959
hide_streamlit_markers=False, use_banner_images=None,
@@ -93,9 +93,39 @@ def account():
9393
st.write("Account page")
9494
st.caption("This is a protected page. Only logged in users can view this.")
9595

96-
@multilit.page(title="Settings", icon=":material/settings:", page_type="settings")
96+
@multilit.page(title="Settings", icon=":material/settings:", page_type="settings", with_loader=False)
9797
def settings():
98-
st.button("Theme")
98+
menu_definition = [
99+
{
100+
"id": "account",
101+
"label": "Account",
102+
"icon": "material/account_circle",
103+
"ttip": "Account",
104+
},
105+
{
106+
"id": "preferences",
107+
"label": "Preferences",
108+
"icon": "material/settings",
109+
"ttip": "Preferences",
110+
}
111+
]
112+
# default_definition = menu_definition.pop(0)
113+
selected_tab = st_navbar(
114+
menu_definition,
115+
sticky_nav=False,
116+
theme_changer=False,
117+
# home_definition=default_definition
118+
)
119+
120+
if selected_tab == "account":
121+
st.subheader("Account settings")
122+
st.text_input("Email", value="", placeholder="Email")
123+
st.text_input("Username", value="", placeholder="Username")
124+
st.text_input("Full name", value="", placeholder="Full name")
125+
elif selected_tab == "preferences":
126+
st.subheader("Preferences")
127+
st.checkbox("Enable notifications", value=True)
128+
st.checkbox("Dark mode", value=False)
99129

100130
@multilit.logout_callback
101131
def logout():
@@ -145,7 +175,7 @@ def no_sectioned_page():
145175

146176
multilit.add_page(page=multilit.default_home_dashboard(), page_type="home")
147177
with multilit.new_section(title="Reports"):
148-
multilit.add_page(bugs)
178+
multilit.add_page(bugs, with_loader=False)
149179
multilit.add_page(alerts)
150180

151181
with multilit.new_section(title="Tools"):

streamlit_plugins/components/loader/__init__.py

Lines changed: 5 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -2,6 +2,7 @@
22
import atexit
33
import time
44
from enum import Enum, auto
5+
from typing import TypeVar
56

67
import streamlit as st
78

@@ -3421,7 +3422,7 @@ def book_loader(**kwargs):
34213422
style = """
34223423
<link rel="stylesheet" href="https://fonts.googleapis.com/icon?family=Material+Icons">
34233424
<style>
3424-
div:has(.book-parent) {
3425+
div:has(>.book-parent) {
34253426
width: inherit;
34263427
display: flex;
34273428
justify-content: center;
@@ -4419,7 +4420,9 @@ def run_loader(self):
44194420
def stop_loader(self):
44204421
pass
44214422

4422-
class Loader(BaseLoader):
4423+
LoaderType = TypeVar('LoaderType', bound=BaseLoader)
4424+
4425+
class DefaultLoader(BaseLoader):
44234426
def __init__(self,
44244427
loader_container=None, text='', loader_name: LoadersLib = LoadersLib.book_loader, height=256,
44254428
index=0, primary_color=None

streamlit_plugins/components/navbar/__init__.py

Lines changed: 61 additions & 73 deletions
Original file line numberDiff line numberDiff line change
@@ -595,12 +595,15 @@ def st_navbar(
595595
reclick_load=True,
596596
input_styles: str | None = None,
597597
themes_data: list[dict]| None = None,
598-
theme_changer: bool = True,
598+
theme_changer: bool = False,
599599
collapsible: bool = True,
600600
prefix_url: str = "",
601601
url_navigation: bool = False,
602602
key="NavBarComponent",
603603
):
604+
if home_definition is None:
605+
home_definition = menu_definition.pop(0)
606+
604607
is_navigation = False
605608
# se recupera del callstack si se ha llamado desde la anterior funcion desde st_navigation
606609
inspect_stack = inspect.stack()
@@ -618,15 +621,25 @@ def st_navbar(
618621

619622
if "navbar_coi_instance" not in st.session_state:
620623
st.session_state.navbar_coi_instance = False
621-
622-
if themes_data is None and theme_changer:
623-
themes_data = DEFAULT_THEMES
624-
elif not theme_changer:
625-
themes_data = []
624+
625+
if "navbar_st_styles_loaded" not in st.session_state:
626+
st.session_state.navbar_st_styles_loaded = False
627+
628+
if is_navigation:
629+
if themes_data is None and theme_changer:
630+
themes_data = DEFAULT_THEMES
631+
elif not theme_changer:
632+
themes_data = []
633+
else:
634+
theme_changer = False
635+
636+
navbar_view = st.container(key=f"{key}_container_navbar")
637+
coi_styles_view = st.container(key=f"{key}_container_coi_styles")
626638

627639
# https://github.com/SnpM/streamlit-scroll-navigation
628-
inject_crossorigin_interface()
629-
time.sleep(0.1)
640+
with coi_styles_view:
641+
inject_crossorigin_interface()
642+
# time.sleep(0.1)
630643

631644
# ctx = get_script_run_ctx(suppress_warning=True)
632645

@@ -686,69 +699,38 @@ def st_navbar(
686699
if override_page_selected_id:
687700
default_page_selected_id = override_page_selected_id
688701

689-
# if key not in st.session_state:
690-
# override_app_selected_id = default_app_selected_id
691-
# elif st.session_state[key] is None:
692-
# override_app_selected_id = default_app_selected_id
693-
coi_scripts_instance = st.empty()
694-
styles = ""
695-
if not st.session_state.navbar_coi_instance:
702+
input_styles = input_styles or ""
703+
styles = f"\ndiv:has(> .st-key-{key}_container_coi_styles) {{\nheight: 0;\nposition: absolute;\n}}\n"
704+
if not st.session_state.navbar_st_styles_loaded:
705+
styles += load_st_styles()
706+
with coi_styles_view:
707+
st.markdown(f"<style>\n{input_styles}\n{styles}\n<style>", unsafe_allow_html=True)
708+
709+
# if not st.session_state.navbar_coi_instance:
710+
# styles = load_st_styles()
711+
with coi_styles_view:
712+
instantiate_crossorigin_interface(_component_func.name, key, is_navigation, default_page_selected_id, position_mode, sticky_nav)
696713
st.session_state.navbar_coi_instance = True
697-
styles = load_st_styles()
698-
with coi_scripts_instance.container():
699-
instantiate_crossorigin_interface(_component_func.name, key, is_navigation, default_page_selected_id, position_mode, sticky_nav)
700-
time.sleep(0.2)
701-
702-
# print()
703-
# print(f"FROM Override Multi: {override_app_selected_id}")
704-
style = NAV_TOP_UNDER_STYLE
705-
706-
if position_mode == 'under':
707-
style += UNDER_NAV_STYLE
708-
if sticky_nav:
709-
style += UNDER_NAV_STICKY_STYLE
710-
else:
711-
style += UNDER_NAV_FIXED_STYLE
712-
elif position_mode == 'top':
713-
style += NAV_TOP_STYLE
714-
style += VERTICAL_ST_STYLE
715-
if sticky_nav:
716-
style += NAV_TOP_STICKY_STYLE
717-
else:
718-
style += NAV_TOP_FIXED_STYLE
719-
elif position_mode == 'side':
720-
style += SIDE_NAV_STYLE
721714

722-
if position_mode in ['top', 'under']:
723-
if sticky_nav:
724-
style += STICKY_NAV_STYLE
725-
if position_mode == 'top':
726-
style += NAV_TOP_STICKY_STYLE
727-
else:
728-
style += FIXED_NAV_STYLE
729-
730-
if hide_streamlit_markers:
731-
style += HIDE_ST_STYLE
732-
733-
input_styles = input_styles or ""
734-
# st.markdown(f"<style>\n{input_styles}\n{style}\n<style>", unsafe_allow_html=True)
735-
component_value = _component_func(
736-
menu_definition=menu_definition, home=home_data or None, login=login_data or None,
737-
override_theme=override_theme,
738-
position_mode=position_mode, is_sticky=sticky_nav,
739-
default_page_selected_id=default_page_selected_id,
740-
override_page_selected_id=override_page_selected_id,
741-
reclick_load=reclick_load,
742-
styles=styles, custom_styles=input_styles,
743-
is_navigation=is_navigation,
744-
themes_data=themes_data,
745-
theme_changer=theme_changer,
746-
collapsible=collapsible,
747-
prefix_url=prefix_url,
748-
url_navigation=url_navigation and is_navigation,
749-
default=default_page_selected_id,
750-
key=key, fvalue=force_value,
751-
)
715+
with navbar_view:
716+
component_value = _component_func(
717+
menu_definition=menu_definition, home=home_data or None, login=login_data or None,
718+
override_theme=override_theme,
719+
position_mode=position_mode, is_sticky=sticky_nav,
720+
default_page_selected_id=default_page_selected_id,
721+
override_page_selected_id=override_page_selected_id,
722+
reclick_load=reclick_load,
723+
styles=styles, custom_styles=input_styles,
724+
is_navigation=is_navigation,
725+
themes_data=themes_data,
726+
theme_changer=theme_changer,
727+
collapsible=collapsible,
728+
prefix_url=prefix_url,
729+
url_navigation=url_navigation and is_navigation,
730+
default=default_page_selected_id,
731+
is_visible=True,
732+
key=key, fvalue=force_value,
733+
)
752734

753735
# with coi_scripts_styles.container():
754736
# apply_styles(key, f"`{input_styles}`")
@@ -810,14 +792,16 @@ def st_navigation(
810792
default_page = None
811793
if isinstance(pages, dict):
812794
st_pages = {**pages}
813-
if account_page or settings_page or logout_page:
795+
if account_page or settings_page or logout_page or login_page:
814796
st_pages["Account"] = []
815797
if account_page:
816798
st_pages["Account"].append(account_page)
817799
if settings_page:
818800
st_pages["Account"].append(settings_page)
819801
if logout_page:
820802
st_pages["Account"].append(logout_page)
803+
if login_page:
804+
st_pages["Account"].append(login_page)
821805

822806
organized_pages = []
823807
for section, sub_pages in pages.items():
@@ -861,6 +845,8 @@ def st_navigation(
861845
st_pages[""].append(settings_page)
862846
if logout_page:
863847
st_pages[""].append(logout_page)
848+
if login_page:
849+
st_pages[""].append(login_page)
864850

865851
if default_page is None:
866852
raise ValueError("You must provide a default page")
@@ -875,7 +861,8 @@ def st_navigation(
875861
st.session_state["navigation_menu_pages"] = menu_pages
876862
st.session_state["navigation_menu_account_pages"] = menu_account_pages
877863
st.session_state["navigation_default_page_id"] = default_page._script_hash
878-
864+
865+
logout_page_id, login_page_id = None, None
879866
if login_page:
880867
login_page_id = login_page._script_hash
881868
st.session_state["navigation_login_page_id"] = login_page_id
@@ -949,7 +936,8 @@ def st_navigation(
949936
# Solo si se cambia de pagina
950937
if prev_page_id != next_page_id:
951938
st.session_state["navigation_page_id"] = next_page_id
952-
st.session_state["navigation_prev_page_id"] = prev_page_id
939+
if prev_page_id not in [logout_page_id, login_page_id]:
940+
st.session_state["navigation_prev_page_id"] = prev_page_id
953941
st_switch_page(next_page_id, native_way=native_way)
954942

955943
page._can_be_called = True
@@ -982,7 +970,7 @@ def st_switch_page(page_id: str, native_way: bool = False):
982970
page = pages.get(page_id, None)
983971
if page is None:
984972
raise ValueError(f"Page with id {page_id} not found")
985-
973+
986974
st.session_state["navigation_force_page_id"] = page._script_hash
987975
if native_way:
988976
st.switch_page(page)

0 commit comments

Comments
 (0)