@@ -188,6 +188,102 @@ def test_page_sidebar_width_persistence(page):
188188 expect (sidebar_paper ).to_have_css ("width" , "450px" )
189189
190190
191+ def test_page_main_width_default_unclamped (page ):
192+ """By default the main content area is not clamped (no max-width)."""
193+ pg = Page (main = [pn .pane .Markdown ("# Content" )])
194+
195+ serve_component (page , pg )
196+
197+ main_content = page .locator (".main-content" )
198+ expect (main_content ).to_be_attached ()
199+ expect (main_content ).to_have_css ("max-width" , "none" )
200+
201+
202+ def test_page_main_width_custom (page ):
203+ """main_width clamps and centers the main content area."""
204+ pg = Page (main = [pn .pane .Markdown ("# Content" )], main_width = 800 )
205+
206+ serve_component (page , pg )
207+
208+ main_content = page .locator (".main-content" )
209+ expect (main_content ).to_have_css ("max-width" , "800px" )
210+ # Centered via alignSelf in the column flex parent (margin:auto would
211+ # compute to resolved pixels, so we assert on align-self instead).
212+ expect (main_content ).to_have_css ("align-self" , "center" )
213+
214+
215+ def test_page_app_bar_width_default_unclamped (page ):
216+ """By default the app bar toolbar is not clamped (no max-width)."""
217+ pg = Page (main = [pn .pane .Markdown ("# Content" )])
218+
219+ serve_component (page , pg )
220+
221+ toolbar = page .locator (".header .MuiToolbar-root" )
222+ expect (toolbar ).to_have_css ("max-width" , "none" )
223+
224+
225+ def test_page_app_bar_width_custom (page ):
226+ """app_bar_width clamps and centers the app bar toolbar content."""
227+ pg = Page (main = [pn .pane .Markdown ("# Content" )], app_bar_width = 900 )
228+
229+ serve_component (page , pg )
230+
231+ toolbar = page .locator (".header .MuiToolbar-root" )
232+ expect (toolbar ).to_have_css ("max-width" , "900px" )
233+ expect (toolbar ).to_have_css ("align-self" , "center" )
234+
235+
236+ def test_page_main_width_css_string (page ):
237+ """main_width accepts a CSS length string (resolved by the browser)."""
238+ # 60rem resolves to 960px at the default 16px root font size.
239+ pg = Page (main = [pn .pane .Markdown ("# Content" )], main_width = "60rem" )
240+
241+ serve_component (page , pg )
242+
243+ main_content = page .locator (".main-content" )
244+ expect (main_content ).to_have_css ("max-width" , "960px" )
245+ expect (main_content ).to_have_css ("align-self" , "center" )
246+
247+
248+ def test_page_main_width_breakpoint_dict (page ):
249+ """main_width accepts a breakpoint dict, applying per-breakpoint clamps."""
250+ pg = Page (main = [pn .pane .Markdown ("# Content" )], main_width = {"xs" : "100%" , "md" : 800 })
251+
252+ serve_component (page , pg )
253+
254+ main_content = page .locator (".main-content" )
255+ # At/above the md breakpoint the 800px clamp applies.
256+ page .set_viewport_size ({"width" : 1200 , "height" : 800 })
257+ expect (main_content ).to_have_css ("max-width" , "800px" )
258+ # Below md the clamp falls back to the xs entry (100%), i.e. not 800px.
259+ page .set_viewport_size ({"width" : 500 , "height" : 800 })
260+ expect (main_content ).not_to_have_css ("max-width" , "800px" )
261+
262+
263+ def test_page_app_bar_width_follows_main_width (page ):
264+ """When app_bar_width is unset, the toolbar follows main_width so the
265+ header stays aligned with the clamped main content."""
266+ pg = Page (main = [pn .pane .Markdown ("# Content" )], main_width = 800 )
267+
268+ serve_component (page , pg )
269+
270+ toolbar = page .locator (".header .MuiToolbar-root" )
271+ expect (toolbar ).to_have_css ("max-width" , "800px" )
272+ expect (toolbar ).to_have_css ("align-self" , "center" )
273+
274+
275+ def test_page_app_bar_width_overrides_main_width (page ):
276+ """An explicit app_bar_width takes precedence over main_width for the toolbar."""
277+ pg = Page (main = [pn .pane .Markdown ("# Content" )], main_width = 800 , app_bar_width = 1200 )
278+
279+ serve_component (page , pg )
280+
281+ toolbar = page .locator (".header .MuiToolbar-root" )
282+ expect (toolbar ).to_have_css ("max-width" , "1200px" )
283+ main_content = page .locator (".main-content" )
284+ expect (main_content ).to_have_css ("max-width" , "800px" )
285+
286+
191287def test_page_linear_progress_hidden_when_idle (page ):
192288 """Test that linear progress bar is hidden (opacity: 0) when not busy."""
193289 pg = Page (
0 commit comments