1

Я пытаюсь настроить причудливое завершение zle, которое требует передачи слова в подпроцесс.

Zsh, очевидно, знает о текущем каталоге word/token/, и я вижу, как связать вещи, основываясь на текущем слове, но я не могу понять, как превратить "где я" в переменную, которую можно передавать в подпроцессы. , (Я хочу, чтобы emacs был в точке, но в zsh.)

1 ответ1

1

Я использую простой виджет zle print-current-word чтобы проиллюстрировать, как можно извлечь текущее слово в командной строке в простых случаях, то есть предположить, что пробелы всегда являются разделителями слов. (Таким образом, это терпит неудачу, когда цитирование или экранированные пробелы входят в игру):

print-current-word() {
  CURRENTWORD="${LBUFFER/* /}${RBUFFER/ */}"
  print; print "The current word is: $CURRENTWORD"
}
zle -N print-current-word
  • $LBUFFER и $RBUFFER содержат командную строку слева и справа от курсора, соответственно.
  • ${name/pattern/repl} возвращает имя переменной с шаблоном, замененным на repl. Так что в этом случае это обрезает в $LBUFFER все до последнего пробела, оставляя часть слева от курсора текущего слова. Аналог для $RBUFFER .

Более сложный подход будет:

print-current-word () {
    local words i beginword
    i=0 
    beginword=0
    words=("${(z)BUFFER}") 

    while (( beginword <= CURSOR )); do
            (( i++ ))
            (( beginword += ${#words[$i]}+1 ))
    done
    CURRENTWORD="$words[$i]"
    print; print "The current word is: $CURRENTWORD"
}

Однако это также не свободно от предположений, так как предполагается, что каждое слово отделено ровно одним пробелом (добавление +1 к beginword).

Несколько слов о некоторых особых вещах:

  • words=("${(z)BUFFER}") разбивает $BUFFER , то есть полную командную строку, на слова оболочки, используя правила синтаксического анализа оболочки с помощью флага расширения (z) и помещает его в массив
  • (( ... )) активирует математический режим Zsh
  • ${#name} задает длину имени переменной

Всё ещё ищете ответ? Посмотрите другие вопросы с метками .