From: NeilBrown Date: Wed, 2 Dec 2015 01:56:07 +0000 (+1100) Subject: tile: fix 'next' to walk through all pop-ups. X-Git-Tag: lca2016~142 X-Git-Url: http://git.neil.brown.name/?a=commitdiff_plain;h=108f00acf03ead059c640b0b86542b408277c8e0;p=edlib.git tile: fix 'next' to walk through all pop-ups. Still need to work on 'prev'! Signed-off-by: NeilBrown --- diff --git a/lib-tile.c b/lib-tile.c index 34afbf68..21f403e9 100644 --- a/lib-tile.c +++ b/lib-tile.c @@ -499,6 +499,50 @@ static int tile_grow(struct pane *p, int horiz, int size) return 1; } +static struct pane *next_popup(struct pane *parent, struct pane *prev) +{ + struct pane *p2; + list_for_each_entry(p2, &parent->children, siblings) { + if (p2 == prev) { + prev = NULL; + continue; + } + if (prev) + continue; + if (p2->z == 0) + continue; + return p2; + } + return NULL; +} + +static struct tileinfo *tile_first(struct tileinfo *ti) +{ + while (!ti->leaf) { + struct pane *p = pane_child(ti->p); + ti = p->data; + } + return ti; +} + +static int tile_is_first(struct tileinfo *ti) +{ + while (ti->direction != Neither) { + if (ti->p != pane_child(ti->p->parent)) + return 0; + ti = ti->p->parent->data; + } + return 1; +} + +static struct pane *tile_root_popup(struct tileinfo *ti) +{ + while (ti->direction != Neither) + ti = ti->p->parent->data; + return next_popup(ti->p, NULL); +} + + DEF_CMD(tile_command) { struct pane *p = ci->home; @@ -510,8 +554,36 @@ DEF_CMD(tile_command) if (!ci->str) return 0; if (strcmp(ci->str, "next")==0) { - t2 = list_next_entry(ti, tiles); + /* If currently on a popup, go to next popup if there is one, else + * to this tile. + * If was not on a pop-up, go to next tile and if there is a popup, + * go there. + */ + if (p->focus->z) { + p2 = next_popup(p, p->focus); + if (p2) { + pane_focus(p2); + return 1; + } else if (ti->leaf) { + pane_focus(pane_child(p)); + return 1; + } + t2 = tile_first(ti); + } else { + if (ti->leaf) { + t2 = list_next_entry(ti, tiles); + if (tile_is_first(t2) && + (p2 = tile_root_popup(t2)) != NULL) { + pane_focus(p2); + return 1; + } + } else + t2 = tile_first(ti); + } pane_focus(t2->p); + p2 = next_popup(t2->p, NULL); + if (p2) + pane_focus(p2); } else if (strcmp(ci->str, "prev")==0) { t2 = list_prev_entry(ti, tiles); pane_focus(t2->p);