App Shell
Examples for the ss-l-app layout: a full-height frame with a
header, optional left and right sidebars, a main viewport and an optional
status bar. Size it with --ss-app-header-height,
--ss-app-sidebar-width (or -left-width /
-right-width) and --ss-app-footer-height.
On a page the shell fills the viewport (100dvh); the examples
below use ss-l-app--contained to fill a sized box instead. Below
the md breakpoint the sidebars are hidden and open as overlays
when their data-state is "open";
"closed" hides them at every width. SheetManager
toggles the state from any button with data-ss-sheet-toggle.
Header, sidebars, viewport and status bar
<div style="height: 420px; border: 1px solid var(--ss-color-border)">
<div class="ss-l-app ss-l-app--contained" style="--ss-app-sidebar-width: 200px">
<div class="ss-l-app__header">
<button type="button" class="ss-c-button ss-c-button--ghost ss-c-button--sm"
data-ss-sheet-toggle aria-controls="demo-app-nav">Menu</button>
<strong>Spatial viewer</strong>
<span class="ss-l-app__spacer"></span>
<a class="ss-c-button ss-c-button--ghost ss-c-button--sm" href="#">← All demos</a>
</div>
<nav class="ss-l-app__sidebar" id="demo-app-nav" aria-label="Layers">
<ul style="margin: 0; padding: var(--ss-space-4); list-style: none">
<li>Buildings</li>
<li>Roads</li>
<li>Water</li>
</ul>
</nav>
<div class="ss-l-app__main ss-l-app__main--bleed">
<div class="ss-l-app__fill" style="background: var(--ss-color-surface-2)"></div>
</div>
<div class="ss-l-app__sidebar ss-l-app__sidebar--right" role="region" aria-label="Inspector">
<p style="margin: 0; padding: var(--ss-space-4)">Inspector</p>
</div>
<div class="ss-l-app__footer ss-t-text-sm">
<span>Lon 5.2913</span><span>Lat 52.1326</span><span>Zoom 14</span>
</div>
</div>
</div>
Collapsed sidebar
data-state="closed" hides a sidebar; the main area takes its space.
<div style="height: 240px; border: 1px solid var(--ss-color-border)">
<div class="ss-l-app ss-l-app--contained">
<div class="ss-l-app__header"><strong>Viewer</strong></div>
<nav class="ss-l-app__sidebar" data-state="closed" aria-label="Scene tree">…</nav>
<div class="ss-l-app__main" style="padding: var(--ss-space-4)">Main viewport</div>
</div>
</div>
Resizable sidebar
A ss-c-split__handle--edge inside the sidebar, driven by
SplitPaneManager, writes the sidebar width to
--ss-app-sidebar-left-width on the shell
(data-ss-split-root).
<div style="height: 240px; border: 1px solid var(--ss-color-border)">
<div class="ss-l-app ss-l-app--contained" data-ss-split-root>
<div class="ss-l-app__header"><strong>IFC viewer</strong></div>
<nav class="ss-l-app__sidebar" id="demo-app-tree" aria-label="Model tree">
<p style="margin: 0; padding: var(--ss-space-4)">Model tree</p>
<div class="ss-c-split__handle ss-c-split__handle--edge" role="separator" tabindex="0"
aria-orientation="vertical" aria-controls="demo-app-tree"
aria-valuenow="25" aria-valuemin="15" aria-valuemax="50"
aria-label="Resize model tree"
data-ss-split-property="--ss-app-sidebar-left-width"
data-ss-split-unit="px"></div>
</nav>
<div class="ss-l-app__main ss-l-app__main--bleed">
<canvas aria-label="3D view" style="background: var(--ss-color-surface-2)"></canvas>
</div>
</div>
</div>
Padded sidebar
A sidebar has no inner padding by default, so content that sets its
own spacing is not doubled. Add ss-l-app__sidebar--padded
for the standard inner padding (--ss-space-4) when the
content has none.
<div style="height: 200px; border: 1px solid var(--ss-color-border)">
<div class="ss-l-app ss-l-app--contained">
<div class="ss-l-app__header"><strong>Viewer</strong></div>
<aside class="ss-l-app__sidebar ss-l-app__sidebar--padded" aria-label="Details">
<p style="margin: 0">Content without its own padding.</p>
</aside>
<div class="ss-l-app__main" style="padding: var(--ss-space-4)">Main viewport</div>
</div>
</div>