Vous pouvez essayer le code suivant:
let s:option_values = {'foldmethod' : ['manual', 'indent', 'expr', 'marker', 'syntax'],
\ 'bufhidden' : ['hide', 'unload', 'delete', 'wipe'],
\ 'virtualedit' : ['block', 'insert', 'all', 'onemore'] ,}
set wildcharm=<c-z>
cnoremap <expr> <tab>
\ getcmdline() !~# '^\s*set\s\+\w\+=' <bar><bar> wildmenumode() ?
\ '<c-z>' :
\ '<c-u>' . substitute(getcmdline(), 'set', 'Set', '') . '<c-z>'
command! -nargs=1 -complete=customlist,s:SetComplete Set exe 'set' <q-args>
function! s:SetComplete(A, L, P) abort
let option = matchstr(a:A, '^.*\ze=')
if !has_key(s:option_values, option)
return
endif
let candidates = copy(s:option_values[option])
call map(candidates, 'option . "=" . v:val')
return filter(candidates, 'v:val =~ "^" . a:A')
endfunction
Il définit d'abord un dictionnaire s:option_values
dont le but est de contenir vos options (comme ses clés) et leurs valeurs (comme ses valeurs qui sont des listes). Ici, à titre d'exemple, 3 options + valeurs sont stockées:
'foldmethod'
, 'bufhidden'
, 'virtualedit'
.
set wildcharm=<c-z>
Cette ligne définit l' 'wildcharm'
option et indique à Vim que s'il voit <c-z>
dans un mappage, il doit activer le menu wild. Sans définir cette option, si vous écrivez <tab>
dans un mappage, il insérera simplement un caractère de tabulation littéral.
cnoremap <expr> <tab>
Commencez la définition d'un mappage qui tapera l'évaluation d'une expression chaque fois que vous frappez <tab>
sur la ligne de commande.
\ getcmdline() !~# '^\s*set\s\+\w\+=' <bar><bar> wildmenumode() ?
Le mappage teste si la ligne de commande correspond au modèle ^\s*set\s\+\w\+=
, qui est une ligne suivant le formulaire set option=
, ou si le menu générique est actif.
\ '<c-z>' :
Si le test précédent réussit, le mappage active le menu wild.
\ '<c-u>' . substitute(getcmdline(), 'set', 'Set', '') . '<c-z>'
Sinon, il remplace la commande système :set
par la commande personnalisée :Set
et active le menu générique.
command! -nargs=1 -complete=customlist,s:SetComplete Set exe 'set' <q-args>
Définissez la commande personnalisée :Set
qui fait la même chose que :set
, sauf qu'elle peut utiliser une fonction de complétion personnalisée dont le nom est ici s:SetComplete()
.
function! s:SetComplete(A, L, P) abort
Commencez la définition de la fonction d'achèvement personnalisée.
Il doit renvoyer des suggestions / candidats à travers une liste.
La :Set
commande lui enverra automatiquement 3 arguments:
- la partie principale de l'argument en cours de finalisation (c.-à-d.
option=...
)
- toute la ligne de commande
- la position du curseur dedans
Voir :h :command-completion-customlist
pour plus d'informations.
let option = matchstr(a:A, '^.*\ze=')
Extrayez le nom de l'option de l'argument en cours de finalisation.
if !has_key(s:option_values, option)
return
endif
Vérifiez s'il se option
trouve dans votre dictionnaire. Si ce n'est pas le cas, la fonction ne renvoie rien.
let candidates = copy(s:option_values[option])
Obtenez une copie de la liste des valeurs que l'option peut prendre dans votre dictionnaire.
call map(candidates, 'option . "=" . v:val')
Pour chaque valeur de la liste candidates
, ajoutez la chaîne option=
(où option
sera évaluée).
return filter(candidates, 'v:val =~ "^" . a:A')
Supprimez les éléments candidates
dont le début ne correspond pas à l'argument en cours de finalisation et retournez le résultat.