aboutsummaryrefslogtreecommitdiff
path: root/tmuxrdr/plugin/bin/command-prompt
blob: 8c4a4e4f98bc8d02b034c239a11d6b6258bc2e65 (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
#!/bin/sh
# tmux prefix+: (command-prompt). Herdr has no command language of its own, so
# this takes the tmux commands that have a herdr counterpart, with their usual
# aliases and flags, and passes anything else to the herdr CLI -- `:pane list`
# runs `herdr pane list` and shows the result. Run as a popup.
. "$(dirname "$0")/../lib.sh"

action() { "$H" plugin action invoke "tmuxrdr.tmux-mode.$1" >/dev/null; }
pause() { printf '\n[press any key]'; read_key >/dev/null; }

printf ':'
IFS= read -r line || exit 0
[ -n "$line" ] || exit 0
eval "set -- $line" || { pause; exit 1; }
cmd="$1"
shift

p="$(active_pane)"
has() { case " $* " in *" $flag "*) return 0 ;; esac; return 1; }
opt() { # opt -t ARGS...: the value after -t, if any
    _f="$1"; shift
    while [ $# -gt 0 ]; do
        [ "$1" = "$_f" ] && { printf '%s' "${2:-}"; return; }
        shift
    done
}

# The case lives in a function: bash 3.2, which is macOS /bin/sh, misparses a
# case statement written inside $(...) -- its pattern parentheses end the
# substitution early.
run() {
    case "$cmd" in
    kill-pane | killp) "$H" pane close "$p" ;;
    kill-window | killw) "$H" tab close "$(pane_info "$p" tab_id)" ;;
    kill-session) "$H" workspace close "$(pane_info "$p" workspace_id)" ;;
    kill-server) "$H" server stop ;;
    new-window | neww) "$H" tab create --workspace "$(pane_info "$p" workspace_id)" --focus ;;
    split-window | splitw | new-pane | newp)
        flag=-h; dir=down; has "$@" && dir=right
        "$H" pane split "$p" --direction "$dir" --focus ;;
    rename-window | renamew) "$H" tab rename "$(pane_info "$p" tab_id)" "$*" ;;
    rename-session | rename) "$H" workspace rename "$(pane_info "$p" workspace_id)" "$*" ;;
    select-window | selectw) t="$(opt -t "$@")"; t="${t#:}"; sh "$BIN/select-window" "${t#=}" ;;
    break-pane | breakp) sh "$BIN/break-pane" ;;
    move-window | movew) t="$(opt -t "$@")"; sh "$BIN/move-window" "${t#:}" ;;
    swap-pane | swapp)
        flag=-U; if has "$@"; then sh "$BIN/swap-pane" prev
        else flag=-D; if has "$@"; then sh "$BIN/swap-pane" next; else action swap-marked; fi; fi ;;
    rotate-window | rotatew) flag=-D; if has "$@"; then sh "$BIN/rotate-window" down; else sh "$BIN/rotate-window" up; fi ;;
    last-window | last) action last-window ;;
    switch-client | switchc) flag=-l; if has "$@"; then action last-session; else echo "switch-client: only -l is supported"; exit 1; fi ;;
    select-pane | selectp)
        flag=-m; if has "$@"; then action mark; exit; fi
        flag=-M; if has "$@"; then action clear-mark; exit; fi
        for d in L:left R:right U:up D:down; do
            flag="-${d%%:*}"; has "$@" && { "$H" pane focus --direction "${d#*:}" --pane "$p"; exit; }
        done
        echo "select-pane: only -L -R -U -D -m -M are supported"; exit 1 ;;
    resize-pane | resizep)
        flag=-Z; has "$@" && { "$H" pane zoom "$p" --toggle; exit; }
        n="$(printf '%s\n' "$@" | grep -x '[0-9][0-9]*' | head -n 1)"
        for d in L:left R:right U:up D:down; do
            flag="-${d%%:*}"; has "$@" && { "$H" pane resize --direction "${d#*:}" --amount "$(awk "BEGIN { print ${n:-1} / 100 }")" --pane "$p"; exit; }
        done
        echo "resize-pane: only -L -R -U -D [N] and -Z are supported"; exit 1 ;;
    select-layout | selectl) flag=-E; if has "$@"; then action spread-layout; else echo "select-layout: only -E is supported"; exit 1; fi ;;
    display-message | display) if [ $# -gt 0 ]; then say "$*"; else sh "$BIN/display-message"; fi ;;
    paste-buffer | pasteb) sh "$BIN/paste-buffer" ;;
    source-file | source) "$H" server reload-config ;;
    detach-client | detach) echo "detach-client: not scriptable in herdr; use prefix+d"; exit 1 ;;
    *) "$H" "$cmd" "$@"; echo; exit 2 ;;
    esac
}

out="$(run "$@" 2>&1)"
status=$?
# tmux's own commands close the prompt quietly on success; errors, and
# anything handed to the herdr CLI, stay on screen until a key.
case "$status" in
0) ;;
*) printf '%s\n' "$out"; pause ;;
esac