Drawer
A side-anchored surface with the same contract as dialog: rendered in place, title via the text attribute, visibility model-owned behind an if, and on-dismiss dispatched on Escape or click-outside so update clears the open flag. As with the dialog, the title chrome is engine-drawn and children stack over the full content box, so lead the body column with a fixed-height spacer. For the bottom-edge variant, see sheet.
drawer

Markup
<column padding="24">
<button variant="outline" icon="menu" on-press="open_filters">Filters</button>
<if test="{filters_open}">
<drawer text="Filters" width="260" padding="24" on-dismiss="close_filters">
<column gap="12">
<spacer height="34"></spacer>
<checkbox checked="{only_unread}" on-toggle="toggle_unread">Only unread</checkbox>
<checkbox checked="{has_attachments}" on-toggle="toggle_attachments">Has attachments</checkbox>
<switch checked="{compact_rows}" on-toggle="toggle_compact">Compact rows</switch>
</column>
</drawer>
</if>
</column>Zig builder
// Rendered only while model.filters_open is true; on_dismiss clears it in update.
ui.el(.drawer, .{ .text = "Filters", .width = 260, .padding = 24, .on_dismiss = .close_filters }, .{
ui.column(.{ .gap = 12 }, .{
ui.column(.{ .height = 34 }, .{}), // clears the engine-drawn title line
ui.checkbox(.{ .text = "Only unread", .checked = model.only_unread, .on_toggle = .toggle_unread }),
ui.checkbox(.{ .text = "Has attachments", .checked = model.has_attachments, .on_toggle = .toggle_attachments }),
ui.el(.switch_control, .{ .text = "Compact rows", .checked = model.compact_rows, .on_toggle = .toggle_compact }, .{}),
}),
})Attributes
The drawer rejects gap — it layers children like the other stacking surfaces; put a column (or row) inside for flow.
| Attribute | Description |
|---|---|
text | Text value for text-bearing elements; a literal or one {binding}. |
width | Definite width (plain number): the element is exactly this wide; content neither shrinks nor overflows it. On resizable it is the initial width. |
height | Definite height (plain number): the element is exactly this tall; content neither shrinks nor overflows it. |
padding | Uniform padding (plain number). |
on-dismiss | Dismissible surfaces only (dialog, drawer, sheet, dropdown-menu): Msg dispatched when Escape or a click outside dismisses the surface, so the MODEL owns the close (clear the open flag in update). The engine hides the surface immediately as an optimistic echo; the source tree wins on the next rebuild. |
