bugfixes.

This commit is contained in:
Dane Jensen
2026-08-30 09:17:20 -07:00
parent 1371ce4415
commit 54bd67d83f
5 changed files with 31 additions and 11 deletions

2
json.c
View File

@@ -40,7 +40,7 @@
* are not decoded, duplicate keys may go undetected.
*/
#define TOKENS_MAX 1000
#define TOKENS_MAX 8192
#define ERROR_CTX_LEN 8
/* JSON Token types. */

View File

@@ -445,9 +445,11 @@ layout_check(struct layout_cell *lc)
int
layout_parse(struct window *w, const char *layout, char **cause)
{
struct window_pane *wp;
struct layout_cell *lcchild, *lc = NULL;
struct layout_parse_ctx pctx;
u_int npanes, ncells, sx = 0, sy = 0;
int with_floating;
/* Build the layout. */
layout_parse_init_ctx(&pctx, cause);
@@ -456,14 +458,12 @@ layout_parse(struct window *w, const char *layout, char **cause)
layout_free_cell(pctx.root, 0);
return (-1);
}
with_floating = pctx.version >= 2;
/* Check this window will fit into the layout. */
if (pctx.version < 2)
npanes = window_count_panes(w, 0);
else
npanes = window_count_panes(w, 1);
npanes = window_count_panes(w, with_floating);
for (;;) {
ncells = layout_count_cells(pctx.root);
ncells = layout_count_cells(pctx.root, with_floating);
if (npanes > ncells) {
xasprintf(cause, "have %u panes but need %u", npanes,
ncells);
@@ -484,6 +484,19 @@ layout_parse(struct window *w, const char *layout, char **cause)
}
layout_destroy_cell(w, lcchild, &pctx.root);
}
/* Stitch in floating panes to version 1. */
if (pctx.version < 2) {
TAILQ_FOREACH(wp, &w->panes, entry) {
if (!window_pane_is_floating(wp))
continue;
lc = wp->layout_cell;
TAILQ_REMOVE(&lc->parent->cells, lc, entry);
/* A root node is guaranteed by this point. */
TAILQ_INSERT_TAIL(&pctx.root->cells, lc, entry);
lc->parent = pctx.root;
}
}
lc = pctx.root;
/*
@@ -589,13 +602,18 @@ layout_assign_fallback(struct window_pane **wp, struct layout_cell *lc)
switch (lc->type) {
case LAYOUT_WINDOWPANE:
while ((*wp)->layout_cell != NULL) /* skipping floats */
*wp = TAILQ_NEXT(*wp, entry);
layout_make_leaf(lc, *wp);
*wp = TAILQ_NEXT(*wp, entry);
return;
case LAYOUT_LEFTRIGHT:
case LAYOUT_TOPBOTTOM:
TAILQ_FOREACH(lcchild, &lc->cells, entry)
TAILQ_FOREACH(lcchild, &lc->cells, entry) {
if (lcchild->flags & LAYOUT_CELL_FLOATING)
continue;
layout_assign_fallback(wp, lcchild);
}
return;
}
}

View File

@@ -508,18 +508,20 @@ layout_fix_panes(struct window *w, struct window_pane *skip)
/* Count the number of available cells in a layout. */
u_int
layout_count_cells(struct layout_cell *lc)
layout_count_cells(struct layout_cell *lc, int with_floating)
{
struct layout_cell *lcchild;
u_int count = 0;
switch (lc->type) {
case LAYOUT_WINDOWPANE:
if (lc->flags & LAYOUT_CELL_FLOATING && !with_floating)
return 0;
return (1);
case LAYOUT_LEFTRIGHT:
case LAYOUT_TOPBOTTOM:
TAILQ_FOREACH(lcchild, &lc->cells, entry)
count += layout_count_cells(lcchild);
count += layout_count_cells(lcchild, with_floating);
return (count);
default:
fatalx("bad layout type");

2
tmux.1
View File

@@ -2702,7 +2702,7 @@ For example:
$ tmux list\-windows
0: ksh [159x48]
layout: {"V":2,"L":{"t":"h","w":159,"h":48,"x":0,"y":0,"c":[{"t":"p","w":79,"h":48,"x":0,"y":0,"l":0,"i":0,"I":"%0"},{"t":"p","w":79,"h":48,"x":80,"y":0,"a":true,"i":1,"I":"%2"}]}}
$ tmux select\-layout \[aq]{"V":2,"L":{"t":"h","w":159,"h":48,"x":0,"y":0,"c":[{"t":"p","w":79,"h":48,"x":0,"y":0,"l":0,"i":0,"I":"%0"},{"t":"p","w":79,"h":48,"x":80,"y":0,"a":true,"i":1","I":"%2"}]}}\[aq]
$ tmux select\-layout \[aq]{"V":2,"L":{"t":"h","w":159,"h":48,"x":0,"y":0,"c":[{"t":"p","w":79,"h":48,"x":0,"y":0,"l":0,"i":0,"I":"%0"},{"t":"p","w":79,"h":48,"x":80,"y":0,"a":true,"i":1,"I":"%2"}]}}\[aq]
.Ed
.Pp
.Nm

2
tmux.h
View File

@@ -3849,7 +3849,7 @@ struct visible_ranges *window_visible_ranges(struct window_pane *, int, int,
u_int, struct visible_ranges *);
/* layout.c */
u_int layout_count_cells(struct layout_cell *);
u_int layout_count_cells(struct layout_cell *, int);
struct layout_cell *layout_create_cell(struct layout_cell *);
void layout_free_cell(struct layout_cell *, int);
void layout_print_cell(struct layout_cell *, const char *, u_int);