The four shapes almost every admin screen falls into — how wide they are, in what order they are assembled, and what they show while the data is not there yet.
The width of a page is a decision taken once and then named. Without a name every screen reaches for the nearest number, and two screens with the same kind of content end up measuring differently without anybody having decided that.
| Width | Token | What for |
|---|---|---|
full | --frame | Lists and tables. A column bitten off a table is a column missing from it. |
wide | --page-wide | A detail that is read: facts in two columns, panels. A block stretched across the whole frame stops being one object. |
reading | --page-reading | A form, a long setting, a text. A line across a whole monitor is skimmed, not read. |
card | --page-card | The whole screen is one box: signing in, confirming, a module with nothing in it yet. The only width that also centres itself. |
The name is chosen by what the page IS, never by what happens to look right. That is the whole difference between a decision and a guess.
full
wide
reading
card
The width is the page's frame; this is the inside of a block. Two different decisions, and easy to confuse: a grid must not know how wide the page it stands on is.
columns 2, 3 or 4 — how many there are once there is room. Three and four step down through two rather than straight to one.minItemWidth for tiles: name the narrowest cell and the row holds as many as fit.gap is a step of the space scale, not a number. A gap that can be missed by two pixels stops being a scale.Column 1
Column 2
Column 3
Column 4
Tile 1
Tile 2
Tile 3
Tile 4
Tile 5
Tile 6
The commonest admin screen: records with the same set of columns. It takes the frame's whole width, because a column bitten off a table is a column missing from it.
IngotPageHeader — the module's name and the action the user came here to take.IngotToolbar — search and filters. Above the data, not beside it.IngotTable — the records; row actions are the table's last column.IngotPagination — paging under the list.What is in progress and what is due this week.
| Number | Customer | State | Due |
|---|---|---|---|
| ZAK-2026-0179 | Kovo Sedlčany | Late | 2. 9. 2026 |
| ZAK-2026-0184 | Strojírny Beneš | In production | 12. 9. 2026 |
| ZAK-2026-0185 | Zámečnictví Hrubý | Queued | 18. 9. 2026 |
Empty is part of this screen rather than an exception to it: filter for a state that is not here and a sentence stands where the rows were, saying why. An empty table with no sentence looks like loading that broke.
One record with everything true about it. It is read but it is not a form — hence wide: the facts read in two columns and the text stays within one glance.
DN80 flange · 120 pcs
A block whose data has not arrived holds its place with a skeleton. Not with emptiness: a screen whose blocks pop in looks different every time and the reader cannot tell when it is finished.
A screen that is filled in. A reading column, sections by group of fields, and an action bar at the end — so Save is still in reach after the ninth field.
Details that reach documents and the public pages.
Try changing the name: the bar starts saying there are unsaved changes. The state beside the action is why the action is still there.
A module with nothing in it yet is the page a user sees first — and most often the only one on which they decide whether to create anything here at all. It is not an error state; it is an introduction.
No orders yet
An order holds a product, a due date and a customer together. The first one can be created by hand; the rest arrive from orders.
card: the text and the action stay together in the middle. Stretched across 1,440 px they look like the rest of a page that failed to load.