Завершення першого аргументу CD СТАРИЙ НОВИЙ


22

В zsh, то cdкоманда має вигляд двох аргументів: cd OLD NEWзмінюється ${PWD/OLD/NEW}. За допомогою системи завершення нового стилю zsh здатна завершити NEW: другий аргумент завершується на основі того, що OLDможна замінити, щоб отримати існуючий каталог. Але перший аргумент завершений лише для існуючих каталогів.

Як я можу змусити zsh запропонувати доповнення, які є можливими значеннями для OLDтого, щоб доповнити існуючі каталоги?

Наприклад, якщо поточний каталог /path/to/fooі є також каталоги /also/to/fooі /path/to/foo/prime, потім cd pTabзавершує pз prime. Якщо я маю намір запуститись, cd path alsoя хотів би також запропонувати zsh pathяк завершення. Як?

Використання вже набраних значень другого аргументу для обмеження можливостей першого аргументу було б плюсом, але і завершити перший аргумент самостійно було б також добре.


Чи буде вашим прикладом завершення 2-аргументів: cd p also <Tab>або cd p also <left arrow x 5> <Tab>?
Джефф Шаллер

@JeffSchaller Прикладом, що враховує другий аргумент, буде cd p also<Left*5><Tab>: якщо я натискаю, <Tab>поки курсор увімкнений also, я очікую, що alsoце буде завершено, а не p.
Жил "ТАК - перестань бути злим"

Якщо ви наберете cd t<tab>вона повинна запропонувати th/to/foo/primeі to/foo/prime? Або варто просто обмежитися межами каталогу?
Бармар

@Barmar Я думаю, що обмеження меж каталогів було б найзручнішим.
Жил "ТАК - перестань бути злим"

Зацікавлене питання ...
wogsland

Відповіді:


1

Я думаю, ви могли б додати компоненти $PWDдо списку cdзавершень, хоча це, як видається, вимагає співу з _cd; тобто спеціально налаштована версія _cdповинна з'являтися спочатку в $fpath.

% cd && mkdir zcomp
% cp $fpath[-1]/_cd zcomp
% fpath=(~/zcomp $fapth)

Потім вгорі ~/zcomp/_cdдодайте функцію

_our_pwd() {
  _values ourpwd ${(ps:/:)PWD}
}

а потім безпосередньо перед _alternativeрядком додайте те, що повертається до списку альтернатив

  ...
  alt=("$service-options:$service option:_cd_options" "$alt[@]")
fi

alt=(ourpwd:pwd:_our_pwd "$alt[@]")

_alternative "$alt[@]" && ret=0

return ret
...

хоча це завжди додасть pwdкомпоненти до cdзавершень:

% cd
Users    jdoe    Applications/  Desktop/  Documents/  Downloads/  Library/
...

з додатковою логікою ви могли додавати $PWDкомпоненти лише тоді, коли вже є другий аргумент замість завжди.

Однак! Це завжди псує cdзавершення і вимагає, щоб ми мавпи виправляли _cdзавершення вище . Іншим варіантом було б створити нове ім'я функції, наданої двома аргументами cd, можливо, викликається cdsub, і лише PWDдля цього з'являться завершення компонентів. Додайте це до~/.zshrc

function cdsub { builtin cd "$@" }

А потім поглиблене _cd завершення для_cdsub розміщення десь у $fpath:

#compdef cdsub
#
# Modified version of _cd from ZSH 5.3.1 with specific support for the
# `cd old new` form whereby PWD elements are provided for completion.

_cd_options() {
  _arguments -s \
  '-q[quiet, no output or use of hooks]' \
  '-s[refuse to use paths with symlinks]' \
  '(-P)-L[retain symbolic links ignoring CHASE_LINKS]' \
  '(-L)-P[resolve symbolic links as CHASE_LINKS]'
}

setopt localoptions nonomatch

local expl ret=1 curarg
integer argstart=2 noopts

if (( CURRENT > 1 )); then
  # if not in command position, may have options.
  # Careful: -<-> is not an option.
  while [[ $words[$argstart] = -* && argstart -lt CURRENT ]]; do
    curarg=$words[$argstart]
    [[ $curarg = -<-> ]] && break
    (( argstart++ ))
    [[ $curarg = -- ]] && noopts=1 && break
  done
fi

if [[ CURRENT -eq $((argstart+1)) ]]; then
  # cd old new: look for old in $PWD and see what can replace it
  local rep
  # Get possible completions using word in position 2
  rep=(${~PWD/$words[$argstart]/*}~$PWD(-/))
  # Now remove all the common parts of $PWD and the completions from this
  rep=(${${rep#${PWD%%$words[$argstart]*}}%${PWD#*$words[$argstart]}})
  (( $#rep )) && _wanted -C replacement strings expl replacement compadd -a rep
else
  _values ourpwd ${(ps:/:)PWD} && ret=0
  return ret
fi
Використовуючи наш веб-сайт, ви визнаєте, що прочитали та зрозуміли наші Політику щодо файлів cookie та Політику конфіденційності.
Licensed under cc by-sa 3.0 with attribution required.