floating panes, and use a more modern serialization format.
## Serialization
layout-custom.c now emits a canonical current format with:
- Pane syntax: %pane-id,z-index:geometry[:flags]
- Semicolons between child cells.
- X-style geometry: WxH+X+Y
- Every pane represented inside layout_root, including floating panes.
- No legacy <...> floating-pane wrapper.
- Z-index serialized for tiled and floating panes.
- Flags:
- f: floating
- h: hidden
- z: zoomed
- Hidden panes use their saved restoration geometry.
- Single-pane windows serialize as a pane root cell.
window_layout and list-windows continue emitting a four-digit checksum.
## Geometry
Current layouts accept:
- +N: absolute positive offset
- ++N: equivalent to +N
- +-N: absolute negative offset
- -N: right/bottom-relative offset for floating panes
- Omitted offsets: +0+0
- One offset: second defaults to +0
Relative offsets are resolved immediately. Output always contains canonical absolute
coordinates.
Widths and heights are restricted to 1..PANE_MAXIMUM; offsets and resolved offsets are
restricted to -PANE_MAXIMUM..PANE_MAXIMUM.
## Checksums and whitespace
- The outer checksum is optional on input for current and legacy layouts.
- If supplied, it must be correct.
- Output still includes it.
- Checksums cover all non-whitespace layout text.
- Whitespace and newlines may be inserted between tokens.
- Optional nested checksums are accepted and validated but not emitted.
## Legacy compatibility
Legacy comma-separated layouts remain accepted:
WxH,x,y{cell,cell,...}
WxH,x,y,pane-id
Additional compatibility behavior includes:
- The reported e6db,113x28,... layout works and resizes existing panes correctly.
- Older inconsistent root dimensions are corrected safely.
- Legacy layouts with surplus cells continue pruning cells until the target pane count
matches.
- Legacy panes remain assigned in tree order.
- Legacy input is re-emitted in the current canonical format.
Mixed legacy/current syntax is rejected.
## Pane matching and counts
For current layouts:
- Pane IDs must be unique.
- With matching pane counts:
- An exact ID set maps panes by identity.
- A completely disjoint ID set maps panes in tree order.
- A partial ID match is rejected as ambiguous.
- If the target has fewer panes:
- Cells are removed from the end of the tree.
- Remaining z-indexes are compacted while preserving order.
- Existing panes are assigned in tree order.
- No panes are killed or created.
- A target with more panes than layout cells is rejected.
Layouts are therefore snapshots that rearrange existing panes and windows, not complete
session-restoration data.
## Validation and safety
Parsing now constructs and validates a temporary tree before replacing the active layout:
- Maximum input length: 8192 bytes.
- Maximum nesting depth: 64.
- Checked signed and unsigned numeric parsing.
- Dimension and offset bounds.
- Container size consistency.
- Exact trailing-input checks.
- Unique, contiguous z-indexes starting at zero.
- Floating panes must precede tiled panes in z-order.
- Unknown and duplicate flags are rejected.
- Hidden and zoomed flags cannot be combined.
- Only one pane may be zoomed.
- Relative positioning is accepted only for floating panes.
- Overflow-safe size aggregation.
Invalid single-window layouts are validated before the window is unzoomed. Multi-window
layouts are all validated before any window is changed.
## Multi-window layouts
cmd-select-layout.c accepts:
@window-id:layout[@window-id:layout...]
Records may be adjacent or separated by whitespace/newlines. Unknown and duplicate window IDs
are rejected.
This allows direct reuse of:
tmux list-windows -F '#{window_id}:#{window_layout}'
## Supporting runtime changes
- tmux.h adds parsed pane IDs, z-indexes, hidden/zoomed/relative cell flags, and
layout_validate.
- layout.c initializes parsed metadata safely.
- window.c treats hidden cells, including saved cells, as non-visible.
## Documentation
tmux.1 now documents:
- Current and legacy grammars.
- Geometry and flags.
- Z-index and pane-ID rules.
- Optional checksums.
- Multi-window wrappers.
- Pane-count pruning.
- Snapshot versus session-restoration semantics.
The authoritative description is under select-layout; list-windows and list-panes reference
it.
## Tests
Added regress/layout-custom.sh covering serialization, compatibility, validation, geometry,
IDs, pruning, flags, zoom, checksums, whitespace, and multi-window application.
Updated regress/control-client-sanity.sh for canonical output.
Verified:
- Debug build
- Layout regression
- Floating-pane geometry regression
- Control-client regression
- Man-page rendering
- git diff --check
replaces the previous "modal" behaviour where the pane would be resized,
which tended to make a mess. Instead, the scrollbar appears when
scrolling or when hovered over with the mouse and disappears a
(configurable) short period later. From Michael Grant.
are now wrapped up in prompt*.c and do not depend on a client. These
functions are used to provide the original client prompt but also to
allow panes to have their own prompts, which works much much better for
floating panes. The mode prompts for both the tree modes and copy mode
are switched over to be per pane.
There are some visible changes (some of these may be changed if they
don't seem to be working well):
- Prompts in modes now appear in the bottom line, covering whatever
content was there.
- command-prompt has a -P flag to open a pane prompt.
- Because they cover the content, the default style for prompts in modes
now does not fill the entire line; the main command prompt stays the
same.
- The old completion menu has gone, and completions are now shown after
the text. Builtin aliases are no longer completed.
- Clicking the mouse on the prompt now moves the cursor or selects a
completion.
is generated and cached in the client: it holds positions and sizes of
panes, borders and so on. The scene is invalidated when a pane is moved
or resized or relevant option is changed. This scene is then drawn to
the client as needed and text and colours are filled in. With Michael
Grant.