# Welcome to bbmenu.sh. This file defines two functions: bbmenu and bbconfmenu.
# These functions provide the core menu-driven interface for BashBurn.

# Standard menu engine
# Parameters:
#   $1: titleref - The name of a global variable containing the menu title string.
#   $2: menu_items - The name of a global array containing menu definitions.
#       Format: "Label Text@Action to Execute"
# 
# This function loops indefinitely, rendering the menu and waiting for user input.
# Selecting a valid number executes the associated action via 'eval'.
bbmenu()
{
    local titleref="$1"
    local -n menu_items="$2"
    local size=${#menu_items[@]}
    local i selection item action prompt

    while true; do
        pretty_top
        echo -e "${BBTABLECOLOR}|-(${BBSUBCOLOR}${!titleref}${BBTABLECOLOR})"
        
        for (( i=0; i < size; i++ )); do
            IFS='@' read -r item action <<< "${menu_items[i]}"
            printf "%b|%b %2d) %s\n" "${BBTABLECOLOR}" "${BBMAINCOLOR}" "$i" "$item"
        done

        prompt=$(printf "\n%b|\n%b$bb_menu_input [0-$((size-1))] |>%b " \
            "${BBTABLECOLOR}" "${BBINPUTCOLOR}" "${BBMAINCOLOR}")
        
        read -e -p "$prompt" selection
        
        if [[ "$selection" =~ ^[0-9]+$ ]] && (( selection >= 0 && selection < size )); then
            IFS='@' read -r item action <<< "${menu_items[selection]}"
            eval "$action"
        elif [[ -n "$selection" ]]; then
            top_info_line
            message "$bb_menu_error_range ${BBHEADCOLOR}$bb_exit_err [0-$(( size - 1 ))]${BBCOLOROFF}\n"  
        fi
    done
}

# Configuration menu engine
# Parameters:
#   $1: menu_items - The name of a global array defining configuration rows.
#       Format: "LabelVar@ConfigVar@PromptVar@InfoCmd@StrictEnum"
#       - LabelVar: Var name for the item's display label.
#       - ConfigVar: Var name for the actual configuration parameter.
#       - PromptVar: Var name for the prompt shown when changing the value.
#       - InfoCmd: (Optional) Command to run to show help/options for this setting.
#       - StrictEnum: (Optional) If 1, only allow values returned by InfoCmd.
#   $2: toptext1name - Var name for the left-side header title.
#   $3: toptext2name - Var name for the right-side header (usually 'Current Value').
#   $4-7: apply, default, revert, back - Shell code to eval for the bottom action items.
#
# This engine tracks pending changes by checking the global array named in $CFG_CHANGES.
# Modified items are marked with an asterisk (*).
bbconfmenu()
{
    local -n menu_items="$1"
    local toptext1name="$2"
    local toptext2name="$3"
    local apply_action="$4"
    local default_action="$5"
    local revert_action="$6"
    local back_action="$7"
    local -n changes="$CFG_CHANGES"
    
    local i j item var prompt_var info_cmd strict_enum
    local star dispval selection act
    local extra_actions=("bb_conf_menu_apply" "bb_conf_menu_default" "bb_conf_menu_revert" "bb_conf_menu_back")
    local size=${#menu_items[@]}
    local extra_size=${#extra_actions[@]}

    while true; do
        pretty_top
        local t1="${!toptext1name}"
        local t2="${!toptext2name}"
        # Alignment logic: Header values start at column 37 (offset 36).
        # We calculate padding to ensure the second header aligns with values.
        local pad=$((32 - ${#t1}))
        (( pad < 0 )) && pad=0
        printf '%b|-(%b%s%b)%*s(%b%s%b)\n' \
            "$BBTABLECOLOR" "$BBSUBCOLOR" "$t1" "$BBTABLECOLOR" \
            "$pad" "" \
            "$BBSUBCOLOR" "$t2" "$BBTABLECOLOR"

        for (( i=0; i < size; i++ )); do
            IFS='@' read -r label_var var prompt_var info_cmd strict_enum <<< "${menu_items[i]}"
            
            star=""
            dispval="${!var}"
            
            # Check for pending changes in the changes array (linked via $CFG_CHANGES)
            for (( j=0; j < ${#changes[@]}; j++ )); do
                IFS='|' read -r c_var c_val <<< "${changes[j]}"
                if [[ "$var" == "$c_var" ]]; then
                    star="*"
                    dispval="$c_val"
                    break
                fi
            done
            
            # Print configuration row with fixed column for the value
            printf "%b|%b  %2d) %-29b(%b%b%b)%b\n" \
                "$BBTABLECOLOR" "$BBMAINCOLOR" $i "${!label_var}" \
                "$BBOPTIONCOLOR" "$dispval" "$BBMAINCOLOR" "$star"
        done

        # Actions separator and bottom menu items
        echo -e "${BBTABLECOLOR}|-(${BBSUBCOLOR}${bb_conf_action_desc}${BBTABLECOLOR})"
        for (( i=0; i < extra_size; i++ )); do
            local label_var="${extra_actions[i]}"
            printf "%b|-%b %2d) %s%b\n" "$BBTABLECOLOR" "$BBMAINCOLOR" $((i + size)) "${!label_var}" "$BBTABLECOLOR"
        done

        prompt=$(printf "%b$bb_conf_menu_entry |> %b" "$BBINPUTCOLOR" "$BBMAINCOLOR")
        read -e -p "$prompt" selection
        echo -e "${BBCOLOROFF}"

        if [[ "$selection" =~ ^[0-9]+$ ]]; then
            act=$selection
            if (( act < size )); then
                # User selected a configuration parameter to change
                IFS='@' read -r label_var var prompt_var info_cmd strict_enum <<< "${menu_items[act]}"
                change_option "$var" "${!prompt_var}" "${!info_cmd:-$info_cmd}" "$strict_enum"
            elif (( act < size + extra_size )); then
                # User selected one of the action items (Apply, Default, etc.)
                case $((act - size)) in
                    0) eval "$apply_action" ;;
                    1) eval "$default_action" ;;
                    2) eval "$revert_action" ;;
                    3) eval "$back_action" ;;
                esac
            else
                top_info_line
                message "$bb_menu_error_range ${BBHEADCOLOR}$bb_exit_err [0-$((size + extra_size - 1))]${BBCOLOROFF}\n"
            fi
        elif [[ -n "$selection" ]]; then
            top_info_line
            message "$bb_menu_error_range ${BBHEADCOLOR}$bb_exit_err [0-$((size + extra_size - 1))]${BBCOLOROFF}\n"
        fi
    done
}
