diff --git a/functions/__config_settings_draw_value.fish b/functions/__config_settings_draw_value.fish index f289537..27e015d 100644 --- a/functions/__config_settings_draw_value.fish +++ b/functions/__config_settings_draw_value.fish @@ -28,6 +28,10 @@ function __config_settings_draw_value set -l cur_row $argv[1] set -l page $argv[2] + # Inline-edit state: when argv[3] is "edit", the cur_row field renders the + # live input buffer (argv[4]) with a caret instead of its stored value. + set -l edit_mode $argv[3] + set -l edit_buf $argv[4] set -l c_ok (set_color green) set -l c_err (set_color red) @@ -126,13 +130,36 @@ function __config_settings_draw_value end end + # Inline edit: render the active row's field as the live buffer with a + # block caret, tail-anchored so the caret stays visible as text grows. + if test "$edit_mode" = edit -a $i -eq $cur_row + set -l fw (math $iw - 33) + set -l avail (math $fw - 1) + set -l shown "$edit_buf" + set -l blen (string length -- "$edit_buf") + if test $blen -gt $avail + set shown (string sub -s (math $blen - $avail + 1) -- "$edit_buf") + end + set badge "$c_head"" EDIT $c_reset" + set field "$shown"(set_color --reverse)" "(set_color normal) + end + set -l curs " " if test $i -eq $cur_row set curs "$c_sel▶$c_reset " end + set -l fw (math $iw - 33) set -l lpad (string pad -r -w 12 -- $label) - set -l fpad (string pad -r -w (math $iw - 33) -- (string shorten -m (math $iw - 33) -- "$field")) + # The edit field is already length-constrained and contains a reverse + # caret; running it through `string shorten` miscounts the escapes, so + # pad it directly. Non-edit fields still shorten to add an ellipsis. + set -l fpad + if test "$edit_mode" = edit -a $i -eq $cur_row + set fpad (string pad -r -w $fw -- "$field") + else + set fpad (string pad -r -w $fw -- (string shorten -m $fw -- "$field")) + end printf '%s│ %s%s [ %s ] %s │\n' $p $curs $lpad $badge $fpad end @@ -145,8 +172,11 @@ function __config_settings_draw_value # ── Bottom divider ──────────────────────────────────────────────────── printf '%s│%s│\n' $p $HBR - # ── Hint line ───────────────────────────────────────────────────────── + # ── Hint line (changes while editing) ───────────────────────────────── set -l hint_line " ↑↓ move Enter edit ←/h clear Tab page q quit" + if test "$edit_mode" = edit + set hint_line " type value Enter save Esc cancel ⌫ delete" + end printf '%s│%s%s%s│\n' $p $c_dim (string pad -r -w $iw -- $hint_line) $c_reset # ── Bottom border ───────────────────────────────────────────────────── diff --git a/functions/__config_settings_read_key.fish b/functions/__config_settings_read_key.fish index d360d2e..4040d81 100644 --- a/functions/__config_settings_read_key.fish +++ b/functions/__config_settings_read_key.fish @@ -24,7 +24,7 @@ # RETURNS # 0 A key was read; one of these tokens is printed to stdout: # up down left right arrow keys -# space tab backtab enter escape +# space tab backtab enter escape backspace # quit Ctrl-C (byte 3) in raw mode # any other single printable character # "" nothing decodable was read @@ -74,6 +74,8 @@ function __config_settings_read_key echo space case 10 13 echo enter + case 8 127 + echo backspace case 3 echo quit case '' diff --git a/functions/config-settings.fish b/functions/config-settings.fish index 53f9040..6e76229 100644 --- a/functions/config-settings.fish +++ b/functions/config-settings.fish @@ -204,35 +204,65 @@ function config-settings --description 'Interactive TUI for managing fish config if test $cur_page -ge 2 set -l v_vars $sponge_vars set -l v_types $sponge_types - set -l v_labels $sponge_labels set -l v_defaults $sponge_defaults if test $cur_page -eq 3 set v_vars $paths_vars set v_types $paths_types - set v_labels $paths_labels set v_defaults $paths_defaults end set -l ridx (math $cur_row + 1) set -l varname $v_vars[$ridx] set -l vtype $v_types[$ridx] - set -l vlabel $v_labels[$ridx] # Only path/int/list rows are editable; bool rows toggle with ←/→. if test "$vtype" != toggle -a "$vtype" != bool - # Erase panel, drop to cooked mode, prompt, redraw. - set -l prev_max_lw (math --scale=0 "($last_cols + 78) / 2") - set -l erase_h (math --scale=0 "$panel_h * max(1, ceil($prev_max_lw / $COLUMNS))") - printf '\e[%dA\e[J' $erase_h - printf '\e[?25h' - printf '%s (blank = reset to default): ' "$vlabel" - read -l new_val - # Blank / Escape reverts to the row's default (a value, or - # erase when the var tolerates unset) — never leaves it empty. - if test -n "$new_val" - __config_settings_set_value $varname $vtype "$new_val" - else - __config_settings_set_value $varname $vtype "$v_defaults[$ridx]" + # Inline editor: edit in-place in the row's value field + # using the raw key reader — no fish `read` / `read>` + # prompt, and the panel cleans itself up on exit. The + # buffer is pre-filled with the current value; clearing it + # and pressing Enter reverts to the row's default. + set -l page sponge + test $cur_page -eq 3; and set page paths + set -l buf (__config_settings_get_raw $varname) + test "$buf" = DEFAULT; and set buf "" + set -l committed 0 + while true + set -l pml (math --scale=0 "($last_cols + 78) / 2") + set -l eh (math --scale=0 "$panel_h * max(1, ceil($pml / $COLUMNS))") + printf '\e[%dA\e[J' $eh + set last_cols $COLUMNS + __config_settings_draw_value $cur_row $page edit "$buf" + + set -l ek (__config_settings_read_key) + or break + switch $ek + case enter + set committed 1 + break + case escape + break + case backspace + set buf (string sub -s 1 -e -1 -- "$buf") + case space + set buf "$buf " + case up down left right tab backtab quit '' + # ignored while editing + case '*' + set buf "$buf$ek" + end end - printf '\e[?25l' + if test $committed -eq 1 + # Empty buffer reverts to the row default (a value, or + # erase when the var tolerates being unset). + if test -n "$buf" + __config_settings_set_value $varname $vtype "$buf" + else + __config_settings_set_value $varname $vtype "$v_defaults[$ridx]" + end + end + # Redraw the normal panel in place of the editor. + set -l pml (math --scale=0 "($last_cols + 78) / 2") + set -l eh (math --scale=0 "$panel_h * max(1, ceil($pml / $COLUMNS))") + printf '\e[%dA\e[J' $eh set last_cols $COLUMNS __cs_dispatch_draw set did_redraw 1