" Author: Eric Van Dewoestine " " Description: {{{ " see http://eclim.org/vim/java/impl.html " " License: " " Copyright (C) 2005 - 2014 Eric Van Dewoestine " " This program is free software: you can redistribute it and/or modify " it under the terms of the GNU General Public License as published by " the Free Software Foundation, either version 3 of the License, or " (at your option) any later version. " " This program is distributed in the hope that it will be useful, " but WITHOUT ANY WARRANTY; without even the implied warranty of " MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the " GNU General Public License for more details. " " You should have received a copy of the GNU General Public License " along with this program. If not, see . " " }}} " Script Varables {{{ let s:command_constructor = \ '-command java_constructor -p "" -f "" -o -e ' let s:command_properties = \ '-command java_bean_properties -p "" -f "" ' . \ '-o -e -t -r ' let s:command_impl = \ '-command java_impl -p "" -f "" -o -e ' let s:command_impl_insert = \ '-command java_impl -p "" -f "" -t "" ' . \ '-s "" ' let s:command_delegate = \ '-command java_delegate -p "" -f "" -o -e ' let s:command_delegate_insert = \ '-command java_delegate -p "" -f "" -v "" ' . \ '-s "" ' let s:no_properties = \ 'Unable to find property at current cursor position: ' . \ 'Not on a field declaration or possible java syntax error.' let s:cross_type_selection = "Visual selection is currently limited to methods of one super type at a time." " }}} function! eclim#java#impl#Constructor(first, last, bang) " {{{ if !eclim#project#util#IsCurrentFileInProject() return endif call eclim#lang#SilentUpdate() let properties = a:last == 1 ? [] : \ eclim#java#util#GetSelectedFields(a:first, a:last) let project = eclim#project#util#GetCurrentProjectName() let file = eclim#project#util#GetProjectRelativeFilePath() let command = s:command_constructor let command = substitute(command, '', project, '') let command = substitute(command, '', file, '') let command = substitute(command, '', eclim#util#GetOffset(), '') let command = substitute(command, '', eclim#util#GetEncoding(), '') if a:bang == '' let command .= ' -s' endif if len(properties) > 0 let json = substitute(string(properties), "'", '"', 'g') if has('win32') || has('win64') let command .= ' -r "' . json . '"' else let command .= " -r '" . json . "'" endif endif let result = eclim#Execute(command) if type(result) == g:STRING_TYPE && result != '' call eclim#util#EchoError(result) return endif if result != "0" call eclim#util#Reload({'retab': 1}) write endif endfunction " }}} function! eclim#java#impl#GetterSetter(first, last, bang, type) " {{{ if !eclim#project#util#IsCurrentFileInProject() return endif call eclim#lang#SilentUpdate() let properties = eclim#java#util#GetSelectedFields(a:first, a:last) if len(properties) == 0 call eclim#util#EchoError(s:no_properties) return endif let project = eclim#project#util#GetCurrentProjectName() let file = eclim#project#util#GetProjectRelativeFilePath() let indexed = a:bang != '' ? '-i' : '' let command = s:command_properties let command = substitute(command, '', project, '') let command = substitute(command, '', file, '') let command = substitute(command, '', eclim#util#GetOffset(), '') let command = substitute(command, '', eclim#util#GetEncoding(), '') let command = substitute(command, '', a:type, '') let command = substitute(command, '', join(properties, ','), '') let command = substitute(command, '', indexed, '') let result = eclim#Execute(command) if result != "0" call eclim#util#Reload({'retab': 1}) write endif endfunction " }}} function! eclim#java#impl#Impl() " {{{ if !eclim#project#util#IsCurrentFileInProject() return endif call eclim#lang#SilentUpdate() let project = eclim#project#util#GetCurrentProjectName() let file = eclim#project#util#GetProjectRelativeFilePath() let offset = eclim#util#GetCurrentElementOffset() let command = s:command_impl let command = substitute(command, '', project, '') let command = substitute(command, '', file, '') let command = substitute(command, '', offset, '') let command = substitute(command, '', eclim#util#GetEncoding(), '') call eclim#java#impl#ImplWindow(command) endfunction " }}} function! eclim#java#impl#ImplWindow(command) " {{{ if (eclim#java#impl#Window(a:command, "impl")) nnoremap :call AddImpl(0) vnoremap :call AddImpl(1) endif endfunction " }}} function! eclim#java#impl#ImplWindowFolding() " {{{ setlocal foldmethod=syntax setlocal foldlevel=99 endfunction " }}} function! eclim#java#impl#Delegate() " {{{ if !eclim#project#util#IsCurrentFileInProject() return endif call eclim#lang#SilentUpdate() let project = eclim#project#util#GetCurrentProjectName() let file = eclim#project#util#GetProjectRelativeFilePath() let offset = eclim#util#GetCurrentElementOffset() let encoding = eclim#util#GetEncoding() let command = s:command_delegate let command = substitute(command, '', project, '') let command = substitute(command, '', file, '') let command = substitute(command, '', offset, '') let command = substitute(command, '', encoding, '') call eclim#java#impl#DelegateWindow(command) endfunction " }}} function! eclim#java#impl#DelegateWindow(command) " {{{ if (eclim#java#impl#Window(a:command, "delegate")) nnoremap :call AddDelegate(0) vnoremap :call AddDelegate(1) endif endfunction " }}} function! eclim#java#impl#Add(command, function, visual) " {{{ let winnr = bufwinnr(bufnr('^' . b:filename)) " src window is not longer open. if winnr == -1 call eclim#util#EchoError(b:filename . ' no longer found in an open window.') return endif if a:visual let start = line("'<") let end = line("'>") endif let superType = "" let methods = [] " non-visual mode or only one line selected if !a:visual || start == end " not a valid selection if line('.') == 1 || getline('.') =~ '^\(\s*//\|package\|$\|}\)' return endif let line = getline('.') if line =~ '^\s*throws' let line = getline(line('.') - 1) endif " on a method line if line =~ '^\s\+' call add(methods, s:MethodSig(line)) let ln = search('^\w', 'bWn') if ln > 0 let superType = substitute(getline(ln), '.*\s\(.*\) {', '\1', '') endif " on a type line else let superType = substitute(line, '.*\s\(.*\) {', '\1', '') endif " visual mode else let pos = getpos('.') let index = start while index <= end let line = getline(index) if line =~ '^\s*\($\|throws\|package\)' " do nothing " on a method line elseif line =~ '^\s\+' call add(methods, s:MethodSig(line)) call cursor(index, 1) let ln = search('^\w', 'bWn') if ln > 0 let super = substitute(getline(ln), '.*\s\(.*\) {', '\1', '') if superType != "" && super != superType call eclim#util#EchoError(s:cross_type_selection) call setpos('.', pos) return endif let superType = super endif " on a type line else let super = substitute(line, '.*\s\(.*\) {', '\1', '') if superType != "" && super != superType call eclim#util#EchoError(s:cross_type_selection) call setpos('.', pos) return endif let superType = super endif call setpos('.', pos) let index += 1 endwhile if superType == "" return endif endif " search up for the nearest package let ln = search('^package', 'bWn') if ln > 0 let package = substitute(getline(ln), '.*\s\(.*\);', '\1', '') let superType = package . '.' . substitute(superType, '<.\{-}>', '', 'g') endif let type = getline(1) let impl_winnr = winnr() exec winnr . "winc w" call eclim#lang#SilentUpdate() let project = eclim#project#util#GetCurrentProjectName() let file = eclim#project#util#GetProjectRelativeFilePath() let command = a:command let command = substitute(command, '', project, '') let command = substitute(command, '', file, '') let command = substitute(command, '', type, '') let command = substitute(command, '', superType, '') if len(methods) let json = substitute(string(methods), "'", '"', 'g') let command = substitute(command, '', '-m ''' . json . '''', '') else let command = substitute(command, '', '', '') endif call a:function(command) noautocmd exec winnr . "winc w" call eclim#util#Reload({'retab': 1}) write noautocmd exec impl_winnr . "winc w" endfunction " }}} function! eclim#java#impl#Window(command, name) " {{{ let matches = matchlist(a:command, '-o \([0-9]*\)') let offset = len(matches) > 1 ? matches[1] : 0 let name = eclim#project#util#GetProjectRelativeFilePath() . '_' . a:name let project = eclim#project#util#GetCurrentProjectName() let result = eclim#Execute(a:command, {'project': project}) if type(result) == g:STRING_TYPE call eclim#util#EchoError(result) return endif if type(result) != g:DICT_TYPE return endif let content = [result.type] for super in result.superTypes call add(content, '') call add(content, 'package ' . super.packageName . ';') call add(content, super.signature . ' {') for method in super.methods let signature = split(method, '\n') let content += map(signature, '"\t" . v:val') endfor call add(content, '}') endfor call eclim#util#TempWindow(name, content, {'preserveCursor': 1}) setlocal ft=java call eclim#java#impl#ImplWindowFolding() let b:eclim_offset = offset return 1 endfunction " }}} function! s:AddImpl(visual) " {{{ let command = s:command_impl_insert if g:EclimJavaImplInsertAtCursor let command .= ' -o ' . b:eclim_offset endif call eclim#java#impl#Add \ (command, function("eclim#java#impl#ImplWindow"), a:visual) endfunction " }}} function! s:AddDelegate(visual) " {{{ call eclim#java#impl#Add \ (s:command_delegate_insert, function("eclim#java#impl#DelegateWindow"), a:visual) endfunction " }}} function! s:MethodSig(line) " {{{ let sig = substitute(a:line, '.*\s\(\w\+(.*\)', '\1', '') let sig = substitute(sig, ',\s', ',', 'g') let sig = substitute(sig, '<.\{-}>', '', 'g') return sig endfunction " }}} " vim:ft=vim:fdm=marker