Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Support fzf on GoDecls[Dir] #1437

Merged
merged 5 commits into from
Sep 25, 2017
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
7 changes: 5 additions & 2 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -24,8 +24,11 @@ IMPROVEMENTS:
* Syntax highlighting for variable declarations and assignments (disabled by default)
[[GH-1426]](https://github.com/fatih/vim-go/pull/1426) and
[[GH-1458]](https://github.com/fatih/vim-go/pull/1458).

* Add support for `:GoDecls[Dir]` in [unite.vim](https://github.com/Shougo/unite.vim) [[GH-1391]](https://github.com/fatih/vim-go/pull/1391).
* Add support for `:GoDecls[Dir]` in [unite.vim](https://github.com/Shougo/unite.vim)
[[GH-1391]](https://github.com/fatih/vim-go/pull/1391).
* Add support for [fzf.vim](https://github.com/junegunn/fzf.vim) in
`GoDecls[Dir]`.
[[GH-1437]](https://github.com/fatih/vim-go/pull/1437).
* Support relative imports for `:GoImpl` [[GH-1322]](https://github.com/fatih/vim-go/pull/1322).
* A new `g:go_list_type_commands` setting is added to individually set the list type for each command [[GH-1415]](https://github.com/fatih/vim-go/pull/1415). As en example:

Expand Down
154 changes: 154 additions & 0 deletions autoload/fzf/decls.vim
Original file line number Diff line number Diff line change
@@ -0,0 +1,154 @@
function! s:code(group, attr) abort
let code = synIDattr(synIDtrans(hlID(a:group)), a:attr, "cterm")
if code =~ '^[0-9]\+$'
return code
endif
endfunction

function! s:color(str, group) abort
let fg = s:code(a:group, "fg")
let bg = s:code(a:group, "bg")
let bold = s:code(a:group, "bold")
let italic = s:code(a:group, "italic")
let reverse = s:code(a:group, "reverse")
let underline = s:code(a:group, "underline")
let color = (empty(fg) ? "" : ("38;5;".fg)) .
\ (empty(bg) ? "" : (";48;5;".bg)) .
\ (empty(bold) ? "" : ";1") .
\ (empty(italic) ? "" : ";3") .
\ (empty(reverse) ? "" : ";7") .
\ (empty(underline) ? "" : ";4")
return printf("\x1b[%sm%s\x1b[m", color, a:str)
endfunction

function! s:sink(str) abort
if len(a:str) < 2
return
endif
let cd = exists('*haslocaldir') && haslocaldir() ? 'lcd ' : 'cd '
let dir = getcwd()
try
" we jump to the file directory so we can get the fullpath via fnamemodify
" below
execute cd . fnameescape(s:current_dir)

let vals = matchlist(a:str[1], '|\(.\{-}\):\(\d\+\):\(\d\+\)\s*\(.*\)|')

" i.e: main.go
let filename = vals[1]
let line = vals[2]
let col = vals[3]

" i.e: /Users/fatih/vim-go/main.go
let filepath = fnamemodify(filename, ":p")

let cmd = get({'ctrl-x': 'split',
\ 'ctrl-v': 'vertical split',
\ 'ctrl-t': 'tabe'}, a:str[0], 'e')
execute cmd fnameescape(filepath)
call cursor(line, col)
silent! norm! zvzz
finally
"jump back to old dir
execute cd . fnameescape(dir)
endtry
endfunction

function! s:source(mode,...) abort
let s:current_dir = expand('%:p:h')
let ret_decls = []

let bin_path = go#path#CheckBinPath('motion')
if empty(bin_path)
return
endif
let command = printf("%s -format vim -mode decls", bin_path)
let command .= " -include ". get(g:, "go_decls_includes", "func,type")

call go#cmd#autowrite()

if a:mode == 0
" current file mode
let fname = expand("%:p")
if a:0 && !empty(a:1)
let fname = a:1
endif

let command .= printf(" -file %s", shellescape(fname))
else
" all functions mode
if a:0 && !empty(a:1)
let s:current_dir = a:1
endif

let command .= printf(" -dir %s", shellescape(s:current_dir))
endif

let out = go#util#System(command)
if go#util#ShellError() != 0
call go#util#EchoError(out)
return
endif

if exists("l:tmpname")
call delete(l:tmpname)
endif

let result = eval(out)
if type(result) != 4 || !has_key(result, 'decls')
return
endif

let decls = result.decls

" find the maximum function name
let max_len = 0
for decl in decls
if len(decl.ident)> max_len
let max_len = len(decl.ident)
endif
endfor

for decl in decls
" paddings
let space = " "
for i in range(max_len - len(decl.ident))
let space .= " "
endfor

let pos = printf("|%s:%s:%s|",
\ fnamemodify(decl.filename, ":t"),
\ decl.line,
\ decl.col
\)
call add(ret_decls, printf("%s\t%s %s\t%s",
\ s:color(decl.ident . space, "Function"),
\ s:color(decl.keyword, "Keyword"),
\ s:color(pos, "SpecialComment"),
\ s:color(decl.full, "Comment"),
\))
endfor

return ret_decls
endfunc

function! fzf#decls#cmd(...) abort
let normal_fg = s:code("Normal", "fg")
let normal_bg = s:code("Normal", "bg")
let cursor_fg = s:code("CursorLine", "fg")
let cursor_bg = s:code("CursorLine", "bg")
let colors = printf(" --color %s%s%s%s%s",
\ &background,
\ empty(normal_fg) ? "" : (",fg:".normal_fg),
\ empty(normal_bg) ? "" : (",bg:".normal_bg),
\ empty(cursor_fg) ? "" : (",fg+:".cursor_fg),
\ empty(cursor_bg) ? "" : (",bg+:".cursor_bg),
\)
call fzf#run(fzf#wrap('GoDecls', {
\ 'source': call('<sid>source', a:000),
\ 'options': '-n 1 --ansi --prompt "GoDecls> " --expect=ctrl-t,ctrl-v,ctrl-x'.colors,
\ 'sink*': function('s:sink')
\ }))
endfunction

" vim: sw=2 ts=2 et
21 changes: 21 additions & 0 deletions autoload/go/decls.vim
Original file line number Diff line number Diff line change
@@ -0,0 +1,21 @@
if !exists('g:go_decls_mode')
let g:go_decls_mode = ''
endif

function! go#decls#Decls(mode, ...) abort
if g:go_decls_mode == 'ctrlp'
call ctrlp#init(call("ctrlp#decls#cmd", [a:mode] + a:000))
elseif g:go_decls_mode == 'fzf'
call call("fzf#decls#cmd", [a:mode] + a:000)
else
if globpath(&rtp, 'plugin/ctrlp.vim') != ""
call ctrlp#init(call("ctrlp#decls#cmd", [a:mode] + a:000))
elseif globpath(&rtp, 'plugin/fzf.vim') != ""
call call("fzf#decls#cmd", [a:mode] + a:000)
else
call go#util#EchoError("neither ctrlp.vim nor fzf.vim are installed. Please install either one")
end
end
endfunction

" vim: sw=2 ts=2 et
34 changes: 22 additions & 12 deletions doc/vim-go.txt
Original file line number Diff line number Diff line change
Expand Up @@ -144,6 +144,8 @@ The following plugins are supported for use with vim-go:
https://github.com/jodosha/vim-godebug

* Interactive |:GoDecls| and |:GoDeclsDir|:
https://github.com/ctrlpvim/ctrlp.vim or
https://github.com/junegunn/fzf.vim or
https://github.com/Shougo/unite.vim

==============================================================================
Expand Down Expand Up @@ -668,25 +670,25 @@ CTRL-t
*:GoDecls*
:GoDecls [file]

Only enabled if `ctrlp.vim` is installed. If run shows all function and
type declarations for the current file. If [file] is non empty it parses
the given file.
Show all function and type declarations for the current file. If
[file] is non empty it parses the given file.
Requires `ctrlp.vim` or `fzf`; it will autodetect the plugin if installed,
but you can use |'g:go_decls_mode'| to force using one or the other.
By default `type` and `func` declarations are shown. This can be changed
via |'g:go_decls_includes'|.
via |'g:go_decls_includes'|. Also see |unite-decls|.

*:GoDeclsDir*
:GoDeclsDir [dir]

Only enabled if `ctrlp.vim` is installed. If run shows all function and
type declarations for the current directory. If [dir] is given it parses
the given directory.
Show all function and type declarations for the current directory. If
[dir] is given it parses the given directory.

*unite-decls*
:Unite decls[:file or dir]

Only enabled if `unite.vim` is installed. If run shows declarations for
all functions and types on the current file or directory. If [:file or
dir] is non empty, it parses the given one.
Only enabled if `unite.vim` is installed. Show declarations for all
functions and types on the current file or directory. If [:file or dir]
is non empty, it parses the given one.
>
" show declarations on the parent directory of the current file
:Unite decls
Expand Down Expand Up @@ -1634,12 +1636,20 @@ By default the template file specified by |'g:go_template_file'| is used.
<
*'g:go_decls_includes'*

Only useful if `ctrlp.vim` or `unite.vim` are installed. This sets which
declarations to show for |:GoDecls| (`ctrp.vim`) and |unite-decls|
Only useful if `ctrlp.vim`, `unite.vim` or `fzf` are installed. This sets
which declarations to show for |:GoDecls| (`ctrp.vim`) and |unite-decls|
(`unite.vim`). It is a Comma delimited list Possible options are:
{func,type}. The default is: >

let g:go_decls_includes = 'func,type'
<
*'g:go_decls_mode'*

Define the tool to be used for |:GoDecls|. Valid options are `ctrlp.vim`,
`fzf`, or an empty string; in which case it will try to autodetect either
`ctrlp.vim` or `fzf`.
>
let g:go_decls_mode = ''
<
*'g:go_echo_command_info'*

Expand Down
15 changes: 3 additions & 12 deletions ftplugin/go/commands.vim
Original file line number Diff line number Diff line change
Expand Up @@ -82,18 +82,9 @@ command! -nargs=* -complete=customlist,go#package#Complete GoErrCheck call go#li
" -- alternate
command! -bang GoAlternate call go#alternate#Switch(<bang>0, '')

" -- ctrlp
if globpath(&rtp, 'plugin/ctrlp.vim') != ""
command! -nargs=? -complete=file GoDecls call ctrlp#init(ctrlp#decls#cmd(0, <q-args>))
command! -nargs=? -complete=dir GoDeclsDir call ctrlp#init(ctrlp#decls#cmd(1, <q-args>))
else
function! s:ctrlp_warning()
call go#util#EchoError("ctrlp.vim plugin is not installed. Please install from: https://github.com/ctrlpvim/ctrlp.vim")
endfunction

command! -nargs=? -complete=file GoDecls call <SID>ctrlp_warning()
command! -nargs=? -complete=file GoDeclsDir call <SID>ctrlp_warning()
endif
" -- decls
command! -nargs=? -complete=file GoDecls call go#decls#Decls(0, <q-args>)
command! -nargs=? -complete=dir GoDeclsDir call go#decls#Decls(1, <q-args>)

" -- impl
command! -nargs=* -buffer -complete=customlist,go#impl#Complete GoImpl call go#impl#Impl(<f-args>)
Expand Down