Skip to content

Commit ceb64f3

Browse files
committed
Updates from rstudio/bslib#798
1 parent ddeb8a7 commit ceb64f3

File tree

3 files changed

+57
-32
lines changed

3 files changed

+57
-32
lines changed

shiny/ui/_sidebar.py

Lines changed: 31 additions & 23 deletions
Original file line numberDiff line numberDiff line change
@@ -1,11 +1,20 @@
11
from __future__ import annotations
22

33
import random
4+
import warnings
45
from typing import Literal, Optional, cast
56

6-
from htmltools import Tag, TagAttrs, TagAttrValue, TagChild, TagList, css, div
7-
from htmltools import svg as svgtags
8-
from htmltools import tags
7+
from htmltools import (
8+
HTML,
9+
Tag,
10+
TagAttrs,
11+
TagAttrValue,
12+
TagChild,
13+
TagList,
14+
css,
15+
div,
16+
tags,
17+
)
918

1019
from .._deprecated import warn_deprecated
1120
from .._docstring import add_example
@@ -184,10 +193,10 @@ def sidebar(
184193
CSS classes for the sidebar container element, in addition to the fixed
185194
`.sidebar` class.
186195
max_height_mobile
187-
The maximum height of the horizontal sidebar when viewed on mobile devices.
188-
The default is `250px` unless the sidebar is included in a
189-
:func:`~shiny.ui.layout_sidebar` with a specified height, in
190-
which case the default is to take up no more than 50% of the layout container.
196+
A CSS length unit (passed through :func:`~shiny.ui.css.as_css_unit`) defining
197+
the maximum height of the horizontal sidebar when viewed on mobile devices. Only
198+
applies to always-open sidebars that use `open = "always"`, where by default the
199+
sidebar container is placed below the main content container on mobile devices.
191200
gap
192201
A CSS length unit defining the vertical `gap` (i.e., spacing) between elements
193202
provided to `*args`.
@@ -215,6 +224,14 @@ def sidebar(
215224
"""
216225
# TODO-future; validate `open`, bg, fg, class_, max_height_mobile
217226

227+
if max_height_mobile is not None and open != "always":
228+
warnings.warn(
229+
"The `shiny.ui.sidebar(max_height_mobile=)` argument only applies to when `open = 'always'`. The `max_height_mobile` argument will be ignored.",
230+
# `stacklevel=2`: Refers to the caller of `sidebar()`
231+
stacklevel=2,
232+
)
233+
max_height_mobile = None
234+
218235
if id is None and open != "always":
219236
# but always provide id when collapsible for accessibility reasons
220237
id = f"bslib_sidebar_{random.randint(1000, 10000)}"
@@ -360,8 +377,6 @@ def layout_sidebar( # TODO-barret-API; Should this be `layout_sidebar(*args, si
360377
"class": f"main{' bslib-gap-spacing' if fillable else ''}",
361378
""
362379
"style": css(
363-
background_color=bg,
364-
color=fg,
365380
gap=as_css_unit(gap),
366381
padding=as_css_padding(padding),
367382
),
@@ -391,8 +406,10 @@ def layout_sidebar( # TODO-barret-API; Should this be `layout_sidebar(*args, si
391406
data_bslib_sidebar_border_radius=trinary(border_radius),
392407
style=css(
393408
__bslib_sidebar_width=as_css_unit(sidebar.width),
394-
__bslib_sidebar_bg=as_css_unit(sidebar.color_bg),
395-
__bslib_sidebar_fg=as_css_unit(sidebar.color_fg),
409+
__bslib_sidebar_bg=sidebar.color_bg,
410+
__bslib_sidebar_fg=sidebar.color_fg,
411+
__bslib_sidebar_main_fg=fg,
412+
__bslib_sidebar_main_bg=bg,
396413
__bs_card_border_color=border_color,
397414
height=as_css_unit(height),
398415
__bslib_sidebar_max_height_mobile=as_css_unit(max_height_mobile),
@@ -532,18 +549,9 @@ def callback() -> None:
532549
_sidebar_func = sidebar
533550

534551

535-
def _collapse_icon() -> Tag:
536-
return tags.svg(
537-
svgtags.path(
538-
fill_rule="evenodd",
539-
d="M1.646 4.646a.5.5 0 0 1 .708 0L8 10.293l5.646-5.647a.5.5 0 0 1 .708.708l-6 6a.5.5 0 0 1-.708 0l-6-6a.5.5 0 0 1 0-.708z",
540-
),
541-
xmlns="http://www.w3.org/2000/svg",
542-
viewBox="0 0 16 16",
543-
class_="bi bi-chevron-down collapse-icon",
544-
style="fill:currentColor;",
545-
aria_hidden="true",
546-
role="img",
552+
def _collapse_icon() -> TagChild:
553+
return HTML(
554+
'<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 16 16" class="bi bi-arrow-bar-left collapse-icon" style="fill:currentColor;" aria-hidden="true" role="img" ><path fill-rule="evenodd" d="M12.5 15a.5.5 0 0 1-.5-.5v-13a.5.5 0 0 1 1 0v13a.5.5 0 0 1-.5.5ZM10 8a.5.5 0 0 1-.5.5H3.707l2.147 2.146a.5.5 0 0 1-.708.708l-3-3a.5.5 0 0 1 0-.708l3-3a.5.5 0 1 1 .708.708L3.707 7.5H9.5a.5.5 0 0 1 .5.5Z"></path></svg>'
547555
)
548556

549557

tests/e2e/bugs/0666-sidebar/app.py

Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -20,6 +20,16 @@
2020
ui.panel_main("Main content - 2", id="m2"),
2121
"right",
2222
),
23+
ui.layout_sidebar(
24+
ui.sidebar("Sidebar content - 3", id="s3"),
25+
"Main content - 3",
26+
id="m3",
27+
),
28+
ui.layout_sidebar(
29+
ui.sidebar("Sidebar content - 4", id="s4", position="right"),
30+
"Main content - 4",
31+
id="m4",
32+
),
2333
)
2434

2535
app = App(app_ui, None)

tests/e2e/bugs/0666-sidebar/test_sidebar_colors.py

Lines changed: 16 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -2,6 +2,7 @@
22

33
from colors import bg_color, fg_color
44
from conftest import ShinyAppProc
5+
from controls import _expect_class_value
56

67
# from controls import Sidebar
78
from playwright.sync_api import Page, expect
@@ -15,19 +16,25 @@ def test_colors_are_rgb() -> None:
1516
def test_sidebar_bg_colors(page: Page, local_app: ShinyAppProc) -> None:
1617
page.goto(local_app.url)
1718

18-
first_content = page.locator("#m1")
19-
first_sidebar = page.locator("#s1")
19+
for i in range(1, 5):
20+
content = page.locator(f"#m{i}")
21+
sidebar = page.locator(f"#s{i}")
2022

21-
main_layout = first_sidebar.locator("..")
23+
main_layout = sidebar.locator("..")
2224

23-
expect(main_layout).to_have_attribute("data-bslib-sidebar-open", "always")
25+
open_val = "always" if i <= 2 else "desktop"
26+
position_val = "left" if i % 2 == 1 else "right"
2427

25-
expect(first_content).to_have_text("Main content - 1")
26-
expect(first_sidebar).to_have_text("Sidebar content - 1")
28+
expect(main_layout).to_have_attribute("data-bslib-sidebar-open", open_val)
2729

28-
# Only works if css file is loaded
29-
expect(first_sidebar).to_have_css("background-color", bg_color)
30-
expect(first_sidebar).to_have_css("color", fg_color)
30+
_expect_class_value(main_layout, "sidebar-right", position_val == "right")
31+
32+
expect(content).to_have_text(f"Main content - {i}")
33+
expect(sidebar).to_have_text(f"Sidebar content - {i}")
34+
35+
# Only works if css file is loaded
36+
expect(sidebar).to_have_css("background-color", bg_color)
37+
expect(sidebar).to_have_css("color", fg_color)
3138

3239
# # TODO-karan; Test that sidebar position is left
3340
# s1 = Sidebar(page, "s1")

0 commit comments

Comments
 (0)