Layout
At a glance
Section titled “At a glance”Align :: enum {...}Fill :: enum {...}actions :: proc() -> booladaptive :: proc(min_width: f32, gap := Space.MD, fill := Fill.Width) -> boolcard :: proc(title := "", gap := Space.SM, padding := Space.MD) -> boolcenter :: proc(gap := Space.SM) -> boolcollapsible :: proc(title: string, open := false) -> boolcolumn :: proc(gap := Space.SM, padding := Space.None, fill := Fill.Width, align := Align.Start, width: f32 = 0, bg := Surface.None, max_width: f32 = 0) -> boolelement_rect :: proc(eid: Id) -> (x, y, w, h: f32, found: bool)element_width :: proc(eid: Id) -> f32field :: proc(label: string, help := "", error := "") -> boolflow :: proc(gap := Space.SM, row_gap := Space.SM) -> boolflow_item :: proc(eid: Id, width: f32 = -1)grid :: proc(min_width: f32, gap := Space.MD) -> boollist_item :: proc(selected := false, disabled := false) -> boolrow :: proc(gap := Space.SM, padding := Space.None, fill := Fill.Width, align := Align.Center, width: f32 = 0, bg := Surface.None) -> boolrule :: proc(vertical := false)scroll :: proc(gap := Space.SM, padding := Space.None, height: f32 = 0) -> boolseparator :: proc()spacer :: proc()stacked :: proc() -> boolAlign :: enum { Start, Center, End,}Alignment of the children on the cross axis (horizontal in a column, vertical in a row).
Values: .Start, .Center, .End
Source: kiln/layout.odin:31
Fill :: enum { None, Width, Height, Both,}Which axes of a container grow to fill the available space; the others fit the content.
Values: .None, .Width, .Height, .Both
Source: kiln/layout.odin:23
Procedures
Section titled “Procedures”actions
Section titled “actions”actions :: proc() -> boolA row of buttons aligned to the end (dialog and form footers). On compact screens the buttons are stacked and fill the width.
| Returns | Type |
|---|---|
| #0 | bool |
Source: kiln/layout.odin:664
adaptive
Section titled “adaptive”adaptive :: proc(min_width: f32, gap := Space.MD, fill := Fill.Width) -> boolA row of children while it is at least min_width units wide, otherwise a column. When
stacked, child containers fill the width even if they have a fixed width in row mode:
if kiln.adaptive(720) { if kiln.column(fill = .Width) { ... } // main content if kiln.column(width = 280) { ... } // side panel, full width when stacked}| Argument | Type | Default |
|---|---|---|
min_width | f32 | required |
gap | Space | Space.MD |
fill | Fill | Fill.Width |
| Returns | Type |
|---|---|
| #0 | bool |
Source: kiln/layout.odin:500
card :: proc(title := "", gap := Space.SM, padding := Space.MD) -> boolA bordered, raised container with an optional title. Fills the width.
| Argument | Type | Default |
|---|---|---|
title | string | "" |
gap | Space | Space.SM |
padding | Space | Space.MD |
| Returns | Type |
|---|---|
| #0 | bool |
Source: kiln/layout.odin:317
center
Section titled “center”center :: proc(gap := Space.SM) -> boolFills the available space and centers its children both ways.
| Argument | Type | Default |
|---|---|---|
gap | Space | Space.SM |
| Returns | Type |
|---|---|
| #0 | bool |
Source: kiln/layout.odin:279
collapsible
Section titled “collapsible”collapsible :: proc(title: string, open := false) -> boolA bordered section with a clickable header that shows or hides the content. open is the
initial state, afterwards the section remembers the user’s choice. Returns whether it is open:
if kiln.collapsible("Erweitert") { ... }| Argument | Type | Default |
|---|---|---|
title | string | required |
open | bool | false |
| Returns | Type |
|---|---|
| #0 | bool |
Source: kiln/layout.odin:695
column
Section titled “column”column :: proc( gap := Space.SM, padding := Space.None, fill := Fill.Width, align := Align.Start, width: f32 = 0, bg := Surface.None, max_width: f32 = 0,) -> boolChildren top to bottom. Fills the width and fits the content’s height by default;
width (units) gives it a fixed width instead, max_width caps a growing width.
| Argument | Type | Default |
|---|---|---|
gap | Space | Space.SM |
padding | Space | Space.None |
fill | Fill | Fill.Width |
align | Align | Align.Start |
width | f32 | 0 |
bg | Surface | Surface.None |
max_width | f32 | 0 |
| Returns | Type |
|---|---|
| #0 | bool |
Source: kiln/layout.odin:226
element_rect
Section titled “element_rect”element_rect :: proc(eid: Id) -> (x, y, w, h: f32, found: bool)Position and size of an element in the previous frame in pixels, e.g. for widgets that place
floating children themselves. found is false before the element was first laid out.
| Argument | Type | Default |
|---|---|---|
eid | Id | required |
| Returns | Type |
|---|---|
x | f32 |
y | f32 |
w | f32 |
h | f32 |
found | bool |
Source: kiln/layout.odin:176
element_width
Section titled “element_width”element_width :: proc(eid: Id) -> f32Width of an element in the previous frame in pixels (the window width before it first appeared). Responsive widgets decide their layout from it.
| Argument | Type | Default |
|---|---|---|
eid | Id | required |
| Returns | Type |
|---|---|
| #0 | f32 |
Source: kiln/layout.odin:169
field :: proc(label: string, help := "", error := "") -> boolA form row: the label (and an optional help text) on the left and the controls declared in the block on the right. When the row is narrow, the label moves above the controls.
if kiln.field("Sprache", "Gilt für alle Fenster") { if v, ok := kiln.select(m.language, LANGUAGES[:]); ok { ... }}A non-empty error is shown instead of the help text, in the danger color, and gives the text
fields, selects and date fields in the block a danger border:
if kiln.field("E-Mail", error = valid(m.email) ? "" : "Keine gültige Adresse") { ... }| Argument | Type | Default |
|---|---|---|
label | string | required |
help | string | "" |
error | string | "" |
| Returns | Type |
|---|---|
| #0 | bool |
Source: kiln/layout.odin:608
flow :: proc(gap := Space.SM, row_gap := Space.SM) -> boolChildren left to right; a child that does not fit into the line any more starts a new one (chips, badges, legends, tags). Clay cannot wrap, so the lines are built from the children’s widths in the previous frame; in the first frame everything is in one line.
Containers and these widgets declared directly inside take part: button, badge, chip, avatar, checkbox, toggle, radio, swatch, spinner and text.
if kiln.flow() { for t in m.tags {kiln.badge(t, .Primary)}}| Argument | Type | Default |
|---|---|---|
gap | Space | Space.SM |
row_gap | Space | Space.SM |
| Returns | Type |
|---|---|
| #0 | bool |
Source: kiln/layout.odin:538
flow_item
Section titled “flow_item”flow_item :: proc(eid: Id, width: f32 = -1)Places the next child of a flow: opens a new line when it would not fit into the current one.
kiln’s widgets call it themselves; custom widgets call it before opening their element so
they wrap inside a flow too. width < 0 takes the element’s width from the previous frame.
Only children declared directly in the flow’s current line count, so widgets used inside
other widgets are not affected.
| Argument | Type | Default |
|---|---|---|
eid | Id | required |
width | f32 | -1 |
Source: kiln/layout.odin:565
grid :: proc(min_width: f32, gap := Space.MD) -> boolA grid of equal columns, each at least min_width units wide. Every container declared
directly inside (card, column, list_item, …) becomes a cell; cells in a row share its height.
The rows are balanced: 4 cells where 3 columns fit give 2 x 2, not 3 + 1.
if kiln.grid(220) { for s in stats { if kiln.card(s.title) { ... } }}| Argument | Type | Default |
|---|---|---|
min_width | f32 | required |
gap | Space | Space.MD |
| Returns | Type |
|---|---|
| #0 | bool |
Source: kiln/layout.odin:468
list_item
Section titled “list_item”list_item :: proc(selected := false, disabled := false) -> boolA clickable row (list entries, navigation, master lists). Ask kiln.clicked() after the block:
if kiln.list_item(i == m.selected) { kiln.avatar(p.name) kiln.text(p.name)}if kiln.clicked() {append(out, Select{i})}| Argument | Type | Default |
|---|---|---|
selected | bool | false |
disabled | bool | false |
| Returns | Type |
|---|---|
| #0 | bool |
Source: kiln/layout.odin:762
row :: proc( gap := Space.SM, padding := Space.None, fill := Fill.Width, align := Align.Center, width: f32 = 0, bg := Surface.None,) -> boolChildren left to right, vertically centered by default.
| Argument | Type | Default |
|---|---|---|
gap | Space | Space.SM |
padding | Space | Space.None |
fill | Fill | Fill.Width |
align | Align | Align.Center |
width | f32 | 0 |
bg | Surface | Surface.None |
| Returns | Type |
|---|---|
| #0 | bool |
Source: kiln/layout.odin:253
rule :: proc(vertical := false)A line in the border color for widgets that build their insides with Clay directly (there is no box to ask for the direction, so it is given).
| Argument | Type | Default |
|---|---|---|
vertical | bool | false |
Source: kiln/layout.odin:308
scroll
Section titled “scroll”scroll :: proc(gap := Space.SM, padding := Space.None, height: f32 = 0) -> boolA vertically scrolling container (mouse wheel or the scroll bar). It fills the available
space; height (units) gives it a fixed height instead.
| Argument | Type | Default |
|---|---|---|
gap | Space | Space.SM |
padding | Space | Space.None |
height | f32 | 0 |
| Returns | Type |
|---|---|
| #0 | bool |
Source: kiln/layout.odin:340
separator
Section titled “separator”separator :: proc()A thin line in the border color; vertical inside a row, horizontal everywhere else.
Source: kiln/layout.odin:301
spacer
Section titled “spacer”spacer :: proc()Takes all remaining space: in a row it pushes the following children to the right, in a column to the bottom.
Source: kiln/layout.odin:296
stacked
Section titled “stacked”stacked :: proc() -> boolTrue while the innermost adaptive is stacked (a column), e.g. to choose a different layout.
| Returns | Type |
|---|---|
| #0 | bool |
Source: kiln/layout.odin:589