X-Git-Url: https://jxself.org/git/?a=blobdiff_plain;f=config%2Fmenu.c;h=99222855544c3a7c2f67b3c33b3796eb36e5ff80;hb=bf909cc9605bfd77ab60b9dfead00c92af2852d2;hp=47bec3434fef16f1b0c46e0f8d908ee704aa57ca;hpb=2f1132cbcec40e431991cda7ff3744455b46c3df;p=carl9170fw.git diff --git a/config/menu.c b/config/menu.c index 47bec34..9922285 100644 --- a/config/menu.c +++ b/config/menu.c @@ -323,10 +323,19 @@ void menu_finalize(struct menu *parent) if (menu->sym && menu->sym->type == S_UNKNOWN) menu_set_type(sym->type); } + + /* + * Use the choice itself as the parent dependency of + * the contained items. This turns the mode of the + * choice into an upper bound on the visibility of the + * choice value symbols. + */ parentdep = expr_alloc_symbol(sym); } else if (parent->prompt) + /* Menu node for 'menu' */ parentdep = parent->prompt->visible.expr; else + /* Menu node for 'if' */ parentdep = parent->dep; /* For each child menu node... */ @@ -525,6 +534,35 @@ void menu_finalize(struct menu *parent) *ep = expr_alloc_one(E_LIST, NULL); (*ep)->right.sym = menu->sym; } + + /* + * This code serves two purposes: + * + * (1) Flattening 'if' blocks, which do not specify a submenu + * and only add dependencies. + * + * (Automatic submenu creation might still create a submenu + * from an 'if' before this code runs.) + * + * (2) "Undoing" any automatic submenus created earlier below + * promptless symbols. + * + * Before: + * + * A + * if ... (or promptless symbol) + * +-B + * +-C + * D + * + * After: + * + * A + * if ... (or promptless symbol) + * B + * C + * D + */ if (menu->list && (!menu->prompt || !menu->prompt->text)) { for (last_menu = menu->list; ; last_menu = last_menu->next) { last_menu->parent = parent; @@ -549,6 +587,15 @@ void menu_finalize(struct menu *parent) sym->flags |= SYMBOL_WARNED; } + /* + * For non-optional choices, add a reverse dependency (corresponding to + * a select) of ' && m'. This prevents the user from + * setting the choice mode to 'n' when the choice is visible. + * + * This would also work for non-choice symbols, but only non-optional + * choices clear SYMBOL_OPTIONAL as of writing. Choices are implemented + * as a type of symbol. + */ if (sym && !sym_is_optional(sym) && parent->prompt) { sym->rev_dep.expr = expr_alloc_or(sym->rev_dep.expr, expr_alloc_and(parent->prompt->visible.expr, @@ -781,14 +828,14 @@ static void get_symbol_str(struct gstr *r, struct symbol *sym, get_symbol_props_str(r, sym, P_SELECT, _(" Selects: ")); if (sym->rev_dep.expr) { str_append(r, _(" Selected by: ")); - expr_gstr_print(sym->rev_dep.expr, r); + expr_gstr_print_revdep(sym->rev_dep.expr, r); str_append(r, "\n"); } get_symbol_props_str(r, sym, P_IMPLY, _(" Implies: ")); if (sym->implied.expr) { str_append(r, _(" Implied by: ")); - expr_gstr_print(sym->implied.expr, r); + expr_gstr_print_revdep(sym->implied.expr, r); str_append(r, "\n"); }