Update vital
This commit is contained in:
parent
3929abc353
commit
c179a51f02
@ -26,8 +26,10 @@
|
|||||||
let s:save_cpo = &cpo
|
let s:save_cpo = &cpo
|
||||||
set cpo&vim
|
set cpo&vim
|
||||||
|
|
||||||
let s:V = vital#neosnippet#of()
|
|
||||||
function! neosnippet#util#get_vital() abort "{{{
|
function! neosnippet#util#get_vital() abort "{{{
|
||||||
|
if !exists('s:V')
|
||||||
|
let s:V = vital#neosnippet#new()
|
||||||
|
endif
|
||||||
return s:V
|
return s:V
|
||||||
endfunction"}}}
|
endfunction"}}}
|
||||||
function! s:get_prelude() abort "{{{
|
function! s:get_prelude() abort "{{{
|
||||||
@ -74,7 +76,7 @@ function! neosnippet#util#get_last_status(...) abort "{{{
|
|||||||
return call(s:get_process().get_last_status, a:000)
|
return call(s:get_process().get_last_status, a:000)
|
||||||
endfunction"}}}
|
endfunction"}}}
|
||||||
function! neosnippet#util#escape_pattern(...) abort "{{{
|
function! neosnippet#util#escape_pattern(...) abort "{{{
|
||||||
return call(s:get_prelude().escape_pattern, a:000)
|
return call(s:get_string().escape_pattern, a:000)
|
||||||
endfunction"}}}
|
endfunction"}}}
|
||||||
function! neosnippet#util#iconv(...) abort "{{{
|
function! neosnippet#util#iconv(...) abort "{{{
|
||||||
return call(s:get_process().iconv, a:000)
|
return call(s:get_process().iconv, a:000)
|
||||||
|
@ -1,5 +1,5 @@
|
|||||||
function! vital#of(name) abort
|
function! vital#of(name) abort
|
||||||
let files = globpath(&runtimepath, 'autoload/vital/' . a:name . '.vital')
|
let files = globpath(&runtimepath, 'autoload/vital/' . a:name . '.vital', 1)
|
||||||
let file = split(files, "\n")
|
let file = split(files, "\n")
|
||||||
if empty(file)
|
if empty(file)
|
||||||
throw 'vital: version file not found: ' . a:name
|
throw 'vital: version file not found: ' . a:name
|
||||||
|
@ -1,5 +1,5 @@
|
|||||||
let s:_plugin_name = expand('<sfile>:t:r')
|
let s:_plugin_name = expand('<sfile>:t:r')
|
||||||
|
|
||||||
function! vital#{s:_plugin_name}#new() abort
|
function! vital#{s:_plugin_name}#new() abort
|
||||||
return vital#{s:_plugin_name[1:]}#of()
|
return vital#{s:_plugin_name[1:]}#new()
|
||||||
endfunction
|
endfunction
|
||||||
|
@ -3,13 +3,13 @@
|
|||||||
" Do not mofidify the code nor insert new lines before '" ___vital___'
|
" Do not mofidify the code nor insert new lines before '" ___vital___'
|
||||||
if v:version > 703 || v:version == 703 && has('patch1170')
|
if v:version > 703 || v:version == 703 && has('patch1170')
|
||||||
function! vital#_neosnippet#Data#String#import() abort
|
function! vital#_neosnippet#Data#String#import() abort
|
||||||
return map({'trim': '', 'chomp': '', 'starts_with': '', 'truncate_skipping': '', 'pad_left': '', 'hash': '', 'trim_end': '', 'nr2enc_char': '', '_vital_depends': '', 'wrap': '', 'split3': '', 'strwidthpart_reverse': '', 'pad_both_sides': '', 'chop': '', 'lines': '', 'contains_multibyte': '', 'nr2byte': '', 'dstring': '', 'replace': '', 'scan': '', 'diffidx': '', 'strchars': '', 'pad_between_letters': '', 'ends_with': '', 'nsplit': '', 'justify_equal_spacing': '', 'strwidthpart': '', 'split_leftright': '', 'truncate': '', 'substitute_last': '', 'pad_right': '', 'replace_first': '', 'split_by_displaywidth': '', 'wcswidth': '', 'common_head': '', 'levenshtein_distance': '', 'reverse': '', 'trim_start': '', 'nr2hex': '', 'padding_by_displaywidth': '', '_vital_loaded': ''}, 'function("s:" . v:key)')
|
return map({'starts_with': '', 'split3': '', 'replace_first': '', 'chop': '', 'unescape': '', 'split_posix_text': '', 'replace': '', 'scan': '', 'strwidthpart': '', 'common_head': '', 'reverse': '', 'escape_pattern': '', 'trim_end': '', '_vital_depends': '', 'wrap': '', 'join_posix_lines': '', 'contains_multibyte': '', 'truncate_skipping': '', 'split_leftright': '', 'ends_with': '', 'nsplit': '', 'strwidthpart_reverse': '', 'unescape_pattern': '', 'levenshtein_distance': '', 'trim_start': '', 'justify_equal_spacing': '', 'nr2hex': '', 'iconv': '', 'pad_left': '', 'nr2enc_char': '', 'lines': '', 'repair_posix_text': '', 'nr2byte': '', 'trim': '', 'diffidx': '', 'truncate': '', 'split_by_displaywidth': '', '_vital_created': '', 'padding_by_displaywidth': '', 'hash': '', 'chomp': '', 'pad_between_letters': '', 'dstring': '', 'pad_both_sides': '', 'substitute_last': '', 'pad_right': '', 'remove_ansi_sequences': '', '_vital_loaded': ''}, 'function("s:" . v:key)')
|
||||||
endfunction
|
endfunction
|
||||||
else
|
else
|
||||||
function! s:_SID() abort
|
function! s:_SID() abort
|
||||||
return matchstr(expand('<sfile>'), '<SNR>\zs\d\+\ze__SID$')
|
return matchstr(expand('<sfile>'), '<SNR>\zs\d\+\ze__SID$')
|
||||||
endfunction
|
endfunction
|
||||||
execute join(['function! vital#_neosnippet#Data#String#import() abort', printf("return map({'trim': '', 'chomp': '', 'starts_with': '', 'truncate_skipping': '', 'pad_left': '', 'hash': '', 'trim_end': '', 'nr2enc_char': '', '_vital_depends': '', 'wrap': '', 'split3': '', 'strwidthpart_reverse': '', 'pad_both_sides': '', 'chop': '', 'lines': '', 'contains_multibyte': '', 'nr2byte': '', 'dstring': '', 'replace': '', 'scan': '', 'diffidx': '', 'strchars': '', 'pad_between_letters': '', 'ends_with': '', 'nsplit': '', 'justify_equal_spacing': '', 'strwidthpart': '', 'split_leftright': '', 'truncate': '', 'substitute_last': '', 'pad_right': '', 'replace_first': '', 'split_by_displaywidth': '', 'wcswidth': '', 'common_head': '', 'levenshtein_distance': '', 'reverse': '', 'trim_start': '', 'nr2hex': '', 'padding_by_displaywidth': '', '_vital_loaded': ''}, \"function('<SNR>%s_' . v:key)\")", s:_SID()), 'endfunction'], "\n")
|
execute join(['function! vital#_neosnippet#Data#String#import() abort', printf("return map({'starts_with': '', 'split3': '', 'replace_first': '', 'chop': '', 'unescape': '', 'split_posix_text': '', 'replace': '', 'scan': '', 'strwidthpart': '', 'common_head': '', 'reverse': '', 'escape_pattern': '', 'trim_end': '', '_vital_depends': '', 'wrap': '', 'join_posix_lines': '', 'contains_multibyte': '', 'truncate_skipping': '', 'split_leftright': '', 'ends_with': '', 'nsplit': '', 'strwidthpart_reverse': '', 'unescape_pattern': '', 'levenshtein_distance': '', 'trim_start': '', 'justify_equal_spacing': '', 'nr2hex': '', 'iconv': '', 'pad_left': '', 'nr2enc_char': '', 'lines': '', 'repair_posix_text': '', 'nr2byte': '', 'trim': '', 'diffidx': '', 'truncate': '', 'split_by_displaywidth': '', '_vital_created': '', 'padding_by_displaywidth': '', 'hash': '', 'chomp': '', 'pad_between_letters': '', 'dstring': '', 'pad_both_sides': '', 'substitute_last': '', 'pad_right': '', 'remove_ansi_sequences': '', '_vital_loaded': ''}, \"function('<SNR>%s_' . v:key)\")", s:_SID()), 'endfunction'], "\n")
|
||||||
delfunction s:_SID
|
delfunction s:_SID
|
||||||
endif
|
endif
|
||||||
" ___vital___
|
" ___vital___
|
||||||
@ -20,12 +20,21 @@ set cpo&vim
|
|||||||
|
|
||||||
function! s:_vital_loaded(V) abort
|
function! s:_vital_loaded(V) abort
|
||||||
let s:V = a:V
|
let s:V = a:V
|
||||||
let s:P = s:V.import('Prelude')
|
|
||||||
let s:L = s:V.import('Data.List')
|
let s:L = s:V.import('Data.List')
|
||||||
endfunction
|
endfunction
|
||||||
|
|
||||||
function! s:_vital_depends() abort
|
function! s:_vital_depends() abort
|
||||||
return ['Prelude', 'Data.List']
|
return ['Data.List']
|
||||||
|
endfunction
|
||||||
|
|
||||||
|
function! s:_vital_created(module) abort
|
||||||
|
" Expose script-local funcref
|
||||||
|
if exists('s:strchars')
|
||||||
|
let a:module.strchars = s:strchars
|
||||||
|
endif
|
||||||
|
if exists('s:wcswidth')
|
||||||
|
let a:module.wcswidth = s:wcswidth
|
||||||
|
endif
|
||||||
endfunction
|
endfunction
|
||||||
|
|
||||||
" Substitute a:from => a:to by string.
|
" Substitute a:from => a:to by string.
|
||||||
@ -143,9 +152,7 @@ endfunction
|
|||||||
" even if a:str contains multibyte character(s).
|
" even if a:str contains multibyte character(s).
|
||||||
" s:strchars(str) {{{
|
" s:strchars(str) {{{
|
||||||
if exists('*strchars')
|
if exists('*strchars')
|
||||||
function! s:strchars(str) abort
|
let s:strchars = function('strchars')
|
||||||
return strchars(a:str)
|
|
||||||
endfunction
|
|
||||||
else
|
else
|
||||||
function! s:strchars(str) abort
|
function! s:strchars(str) abort
|
||||||
return strlen(substitute(copy(a:str), '.', 'x', 'g'))
|
return strlen(substitute(copy(a:str), '.', 'x', 'g'))
|
||||||
@ -331,7 +338,7 @@ function! s:levenshtein_distance(str1, str2) abort
|
|||||||
let letters2 = split(a:str2, '\zs')
|
let letters2 = split(a:str2, '\zs')
|
||||||
let length1 = len(letters1)
|
let length1 = len(letters1)
|
||||||
let length2 = len(letters2)
|
let length2 = len(letters2)
|
||||||
let distances = map(range(1, length1 + 1), 'map(range(1, length2 + 1), "0")')
|
let distances = map(range(1, length1 + 1), 'map(range(1, length2 + 1), ''0'')')
|
||||||
|
|
||||||
for i1 in range(0, length1)
|
for i1 in range(0, length1)
|
||||||
let distances[i1][0] = i1
|
let distances[i1][0] = i1
|
||||||
@ -453,8 +460,9 @@ function! s:truncate(str, width) abort
|
|||||||
" http://github.com/mattn/googlereader-vim/tree/master
|
" http://github.com/mattn/googlereader-vim/tree/master
|
||||||
|
|
||||||
if a:str =~# '^[\x00-\x7f]*$'
|
if a:str =~# '^[\x00-\x7f]*$'
|
||||||
return len(a:str) < a:width ?
|
return len(a:str) < a:width
|
||||||
\ printf('%-'.a:width.'s', a:str) : strpart(a:str, 0, a:width)
|
\ ? printf('%-' . a:width . 's', a:str)
|
||||||
|
\ : strpart(a:str, 0, a:width)
|
||||||
endif
|
endif
|
||||||
|
|
||||||
let ret = a:str
|
let ret = a:str
|
||||||
@ -484,57 +492,20 @@ function! s:truncate_skipping(str, max, footer_width, separator) abort
|
|||||||
endfunction
|
endfunction
|
||||||
|
|
||||||
function! s:strwidthpart(str, width) abort
|
function! s:strwidthpart(str, width) abort
|
||||||
if a:width <= 0
|
let str = tr(a:str, "\t", ' ')
|
||||||
return ''
|
let vcol = a:width + 2
|
||||||
endif
|
return matchstr(str, '.*\%<' . (vcol < 0 ? 0 : vcol) . 'v')
|
||||||
let strarr = split(a:str, '\zs')
|
|
||||||
let width = s:wcswidth(a:str)
|
|
||||||
let index = len(strarr)
|
|
||||||
let diff = (index + 1) / 2
|
|
||||||
let rightindex = index - 1
|
|
||||||
while width > a:width
|
|
||||||
let index = max([rightindex - diff + 1, 0])
|
|
||||||
let partwidth = s:wcswidth(join(strarr[(index):(rightindex)], ''))
|
|
||||||
if width - partwidth >= a:width || diff <= 1
|
|
||||||
let width -= partwidth
|
|
||||||
let rightindex = index - 1
|
|
||||||
endif
|
|
||||||
if diff > 1
|
|
||||||
let diff = diff / 2
|
|
||||||
endif
|
|
||||||
endwhile
|
|
||||||
return index ? join(strarr[:index - 1], '') : ''
|
|
||||||
endfunction
|
endfunction
|
||||||
|
|
||||||
function! s:strwidthpart_reverse(str, width) abort
|
function! s:strwidthpart_reverse(str, width) abort
|
||||||
if a:width <= 0
|
let str = tr(a:str, "\t", ' ')
|
||||||
return ''
|
let vcol = s:wcswidth(str) - a:width
|
||||||
endif
|
return matchstr(str, '\%>' . (vcol < 0 ? 0 : vcol) . 'v.*')
|
||||||
let strarr = split(a:str, '\zs')
|
|
||||||
let width = s:wcswidth(a:str)
|
|
||||||
let strlen = len(strarr)
|
|
||||||
let diff = (strlen + 1) / 2
|
|
||||||
let leftindex = 0
|
|
||||||
let index = -1
|
|
||||||
while width > a:width
|
|
||||||
let index = min([leftindex + diff, strlen]) - 1
|
|
||||||
let partwidth = s:wcswidth(join(strarr[(leftindex):(index)], ''))
|
|
||||||
if width - partwidth >= a:width || diff <= 1
|
|
||||||
let width -= partwidth
|
|
||||||
let leftindex = index + 1
|
|
||||||
endif
|
|
||||||
if diff > 1
|
|
||||||
let diff = diff / 2
|
|
||||||
endif
|
|
||||||
endwhile
|
|
||||||
return index < strlen ? join(strarr[(index + 1):], '') : ''
|
|
||||||
endfunction
|
endfunction
|
||||||
|
|
||||||
if v:version >= 703
|
if v:version >= 703
|
||||||
" Use builtin function.
|
" Use builtin function.
|
||||||
function! s:wcswidth(str) abort
|
let s:wcswidth = function('strwidth')
|
||||||
return strwidth(a:str)
|
|
||||||
endfunction
|
|
||||||
else
|
else
|
||||||
function! s:wcswidth(str) abort
|
function! s:wcswidth(str) abort
|
||||||
if a:str =~# '^[\x00-\x7f]*$'
|
if a:str =~# '^[\x00-\x7f]*$'
|
||||||
@ -577,7 +548,86 @@ else
|
|||||||
endfunction
|
endfunction
|
||||||
endif
|
endif
|
||||||
|
|
||||||
|
function! s:remove_ansi_sequences(text) abort
|
||||||
|
return substitute(a:text, '\e\[\%(\%(\d\+;\)*\d\+\)\?[mK]', '', 'g')
|
||||||
|
endfunction
|
||||||
|
|
||||||
|
function! s:escape_pattern(str) abort
|
||||||
|
" escape characters for no-magic
|
||||||
|
return escape(a:str, '^$~.*[]\')
|
||||||
|
endfunction
|
||||||
|
|
||||||
|
function! s:unescape_pattern(str) abort
|
||||||
|
" unescape characters for no-magic
|
||||||
|
return s:unescape(a:str, '^$~.*[]\')
|
||||||
|
endfunction
|
||||||
|
|
||||||
|
function! s:unescape(str, chars) abort
|
||||||
|
let chars = map(split(a:chars, '\zs'), 'escape(v:val, ''^$~.*[]\'')')
|
||||||
|
return substitute(a:str, '\\\(' . join(chars, '\|') . '\)', '\1', 'g')
|
||||||
|
endfunction
|
||||||
|
|
||||||
|
function! s:iconv(expr, from, to) abort
|
||||||
|
if a:from ==# '' || a:to ==# '' || a:from ==? a:to
|
||||||
|
return a:expr
|
||||||
|
endif
|
||||||
|
let result = iconv(a:expr, a:from, a:to)
|
||||||
|
return empty(result) ? a:expr : result
|
||||||
|
endfunction
|
||||||
|
|
||||||
|
" NOTE:
|
||||||
|
" A definition of a TEXT file is "A file that contains characters organized
|
||||||
|
" into one or more lines."
|
||||||
|
" A definition of a LINE is "A sequence of zero or more non- <newline>s
|
||||||
|
" plus a terminating <newline>"
|
||||||
|
" That's why {stdin} always ends with <newline> ideally. However, there are
|
||||||
|
" some programs which does not follow the POSIX rule and a Vim's way to join
|
||||||
|
" List into TEXT; join({text}, "\n"); does not add <newline> to the end of
|
||||||
|
" the last line.
|
||||||
|
" That's why add a trailing <newline> if it does not exist.
|
||||||
|
" REF:
|
||||||
|
" http://pubs.opengroup.org/onlinepubs/000095399/basedefs/xbd_chap03.html#tag_03_392
|
||||||
|
" http://pubs.opengroup.org/onlinepubs/000095399/basedefs/xbd_chap03.html#tag_03_205
|
||||||
|
" :help split()
|
||||||
|
" NOTE:
|
||||||
|
" it does nothing if the text is a correct POSIX text
|
||||||
|
function! s:repair_posix_text(text, ...) abort
|
||||||
|
let newline = get(a:000, 0, "\n")
|
||||||
|
return a:text =~# '\n$' ? a:text : a:text . newline
|
||||||
|
endfunction
|
||||||
|
|
||||||
|
" NOTE:
|
||||||
|
" A definition of a TEXT file is "A file that contains characters organized
|
||||||
|
" into one or more lines."
|
||||||
|
" A definition of a LINE is "A sequence of zero or more non- <newline>s
|
||||||
|
" plus a terminating <newline>"
|
||||||
|
" REF:
|
||||||
|
" http://pubs.opengroup.org/onlinepubs/000095399/basedefs/xbd_chap03.html#tag_03_392
|
||||||
|
" http://pubs.opengroup.org/onlinepubs/000095399/basedefs/xbd_chap03.html#tag_03_205
|
||||||
|
function! s:join_posix_lines(lines, ...) abort
|
||||||
|
let newline = get(a:000, 0, "\n")
|
||||||
|
return join(a:lines, newline) . newline
|
||||||
|
endfunction
|
||||||
|
|
||||||
|
" NOTE:
|
||||||
|
" A definition of a TEXT file is "A file that contains characters organized
|
||||||
|
" into one or more lines."
|
||||||
|
" A definition of a LINE is "A sequence of zero or more non- <newline>s
|
||||||
|
" plus a terminating <newline>"
|
||||||
|
" TEXT into List; split({text}, '\r\?\n', 1); add an extra empty line at the
|
||||||
|
" end of List because the end of TEXT ends with <newline> and keepempty=1 is
|
||||||
|
" specified. (btw. keepempty=0 cannot be used because it will remove
|
||||||
|
" emptylines in the head and the tail).
|
||||||
|
" That's why removing a trailing <newline> before proceeding to 'split' is required
|
||||||
|
" REF:
|
||||||
|
" http://pubs.opengroup.org/onlinepubs/000095399/basedefs/xbd_chap03.html#tag_03_392
|
||||||
|
" http://pubs.opengroup.org/onlinepubs/000095399/basedefs/xbd_chap03.html#tag_03_205
|
||||||
|
function! s:split_posix_text(text, ...) abort
|
||||||
|
let newline = get(a:000, 0, '\r\?\n')
|
||||||
|
let text = substitute(a:text, newline . '$', '', '')
|
||||||
|
return split(text, newline, 1)
|
||||||
|
endfunction
|
||||||
|
|
||||||
let &cpo = s:save_cpo
|
let &cpo = s:save_cpo
|
||||||
unlet s:save_cpo
|
unlet s:save_cpo
|
||||||
|
|
||||||
" vim:set et ts=2 sts=2 sw=2 tw=0:
|
" vim:set et ts=2 sts=2 sw=2 tw=0:
|
||||||
|
@ -16,39 +16,60 @@ endif
|
|||||||
let s:save_cpo = &cpo
|
let s:save_cpo = &cpo
|
||||||
set cpo&vim
|
set cpo&vim
|
||||||
|
|
||||||
if v:version ># 703 ||
|
if v:version > 703 ||
|
||||||
\ (v:version is 703 && has('patch465'))
|
\ (v:version == 703 && has('patch465'))
|
||||||
function! s:glob(expr) abort
|
function! s:glob(expr) abort
|
||||||
return glob(a:expr, 1, 1)
|
return glob(a:expr, 1, 1)
|
||||||
endfunction
|
endfunction
|
||||||
else
|
else
|
||||||
function! s:glob(expr) abort
|
function! s:glob(expr) abort
|
||||||
let R = glob(a:expr, 1)
|
return split(glob(a:expr, 1), '\n')
|
||||||
return split(R, '\n')
|
|
||||||
endfunction
|
endfunction
|
||||||
endif
|
endif
|
||||||
|
|
||||||
function! s:globpath(path, expr) abort
|
if v:version > 704 ||
|
||||||
let R = globpath(a:path, a:expr, 1)
|
\ (v:version == 704 && has('patch279'))
|
||||||
return split(R, '\n')
|
function! s:globpath(path, expr) abort
|
||||||
endfunction
|
return globpath(a:path, a:expr, 1, 1)
|
||||||
|
endfunction
|
||||||
|
else
|
||||||
|
function! s:globpath(path, expr) abort
|
||||||
|
return split(globpath(a:path, a:expr, 1), '\n')
|
||||||
|
endfunction
|
||||||
|
endif
|
||||||
|
|
||||||
" Wrapper functions for type().
|
" Wrapper functions for type().
|
||||||
let [
|
" NOTE: __TYPE_FLOAT = -1 when -float.
|
||||||
\ s:__TYPE_NUMBER,
|
" this doesn't match to anything.
|
||||||
\ s:__TYPE_STRING,
|
if has('patch-7.4.2071')
|
||||||
\ s:__TYPE_FUNCREF,
|
let [
|
||||||
\ s:__TYPE_LIST,
|
\ s:__TYPE_NUMBER,
|
||||||
\ s:__TYPE_DICT,
|
\ s:__TYPE_STRING,
|
||||||
\ s:__TYPE_FLOAT] = [
|
\ s:__TYPE_FUNCREF,
|
||||||
|
\ s:__TYPE_LIST,
|
||||||
|
\ s:__TYPE_DICT,
|
||||||
|
\ s:__TYPE_FLOAT] = [
|
||||||
|
\ v:t_number,
|
||||||
|
\ v:t_string,
|
||||||
|
\ v:t_func,
|
||||||
|
\ v:t_list,
|
||||||
|
\ v:t_dict,
|
||||||
|
\ v:t_float]
|
||||||
|
else
|
||||||
|
let [
|
||||||
|
\ s:__TYPE_NUMBER,
|
||||||
|
\ s:__TYPE_STRING,
|
||||||
|
\ s:__TYPE_FUNCREF,
|
||||||
|
\ s:__TYPE_LIST,
|
||||||
|
\ s:__TYPE_DICT,
|
||||||
|
\ s:__TYPE_FLOAT] = [
|
||||||
\ type(3),
|
\ type(3),
|
||||||
\ type(''),
|
\ type(''),
|
||||||
\ type(function('tr')),
|
\ type(function('tr')),
|
||||||
\ type([]),
|
\ type([]),
|
||||||
\ type({}),
|
\ type({}),
|
||||||
\ has('float') ? type(str2float('0')) : -1]
|
\ has('float') ? type(str2float('0')) : -1]
|
||||||
" __TYPE_FLOAT = -1 when -float
|
endif
|
||||||
" This doesn't match to anything.
|
|
||||||
|
|
||||||
" Number or Float
|
" Number or Float
|
||||||
function! s:is_numeric(Value) abort
|
function! s:is_numeric(Value) abort
|
||||||
@ -62,27 +83,32 @@ function! s:is_number(Value) abort
|
|||||||
return type(a:Value) ==# s:__TYPE_NUMBER
|
return type(a:Value) ==# s:__TYPE_NUMBER
|
||||||
endfunction
|
endfunction
|
||||||
|
|
||||||
" Float
|
|
||||||
function! s:is_float(Value) abort
|
|
||||||
return type(a:Value) ==# s:__TYPE_FLOAT
|
|
||||||
endfunction
|
|
||||||
" String
|
" String
|
||||||
function! s:is_string(Value) abort
|
function! s:is_string(Value) abort
|
||||||
return type(a:Value) ==# s:__TYPE_STRING
|
return type(a:Value) ==# s:__TYPE_STRING
|
||||||
endfunction
|
endfunction
|
||||||
|
|
||||||
" Funcref
|
" Funcref
|
||||||
function! s:is_funcref(Value) abort
|
function! s:is_funcref(Value) abort
|
||||||
return type(a:Value) ==# s:__TYPE_FUNCREF
|
return type(a:Value) ==# s:__TYPE_FUNCREF
|
||||||
endfunction
|
endfunction
|
||||||
|
|
||||||
" List
|
" List
|
||||||
function! s:is_list(Value) abort
|
function! s:is_list(Value) abort
|
||||||
return type(a:Value) ==# s:__TYPE_LIST
|
return type(a:Value) ==# s:__TYPE_LIST
|
||||||
endfunction
|
endfunction
|
||||||
|
|
||||||
" Dictionary
|
" Dictionary
|
||||||
function! s:is_dict(Value) abort
|
function! s:is_dict(Value) abort
|
||||||
return type(a:Value) ==# s:__TYPE_DICT
|
return type(a:Value) ==# s:__TYPE_DICT
|
||||||
endfunction
|
endfunction
|
||||||
|
|
||||||
|
" Float
|
||||||
|
function! s:is_float(Value) abort
|
||||||
|
return type(a:Value) ==# s:__TYPE_FLOAT
|
||||||
|
endfunction
|
||||||
|
|
||||||
|
|
||||||
function! s:truncate_skipping(str, max, footer_width, separator) abort
|
function! s:truncate_skipping(str, max, footer_width, separator) abort
|
||||||
call s:_warn_deprecated('truncate_skipping', 'Data.String.truncate_skipping')
|
call s:_warn_deprecated('truncate_skipping', 'Data.String.truncate_skipping')
|
||||||
|
|
||||||
@ -248,6 +274,10 @@ function! s:escape_file_searching(buffer_name) abort
|
|||||||
endfunction
|
endfunction
|
||||||
|
|
||||||
function! s:escape_pattern(str) abort
|
function! s:escape_pattern(str) abort
|
||||||
|
call s:_warn_deprecated(
|
||||||
|
\ 'escape_pattern',
|
||||||
|
\ 'Data.String.escape_pattern',
|
||||||
|
\)
|
||||||
return escape(a:str, '~"\.^$[]*')
|
return escape(a:str, '~"\.^$[]*')
|
||||||
endfunction
|
endfunction
|
||||||
|
|
||||||
|
@ -1,8 +1,7 @@
|
|||||||
let s:plugin_name = expand('<sfile>:t:r')
|
let s:plugin_name = expand('<sfile>:t:r')
|
||||||
let s:vital_base_dir = expand('<sfile>:h')
|
let s:vital_base_dir = expand('<sfile>:h')
|
||||||
let s:project_root = expand('<sfile>:h:h:h')
|
let s:project_root = expand('<sfile>:h:h:h')
|
||||||
let s:has_latest_module = isdirectory(expand('<sfile>:h') . '/__latest__')
|
let s:is_vital_vim = s:plugin_name is# 'vital'
|
||||||
let s:is_vital_vim = s:plugin_name is# '_latest__'
|
|
||||||
|
|
||||||
let s:loaded = {}
|
let s:loaded = {}
|
||||||
let s:cache_sid = {}
|
let s:cache_sid = {}
|
||||||
@ -22,15 +21,22 @@ else
|
|||||||
endfunction
|
endfunction
|
||||||
endif
|
endif
|
||||||
|
|
||||||
function! vital#{s:plugin_name}#of() abort
|
function! vital#{s:plugin_name}#new() abort
|
||||||
return s:new(s:plugin_name)
|
return s:new(s:plugin_name)
|
||||||
endfunction
|
endfunction
|
||||||
|
|
||||||
|
function! vital#{s:plugin_name}#import(...) abort
|
||||||
|
if !exists('s:V')
|
||||||
|
let s:V = s:new(s:plugin_name)
|
||||||
|
endif
|
||||||
|
return call(s:V.import, a:000, s:V)
|
||||||
|
endfunction
|
||||||
|
|
||||||
let s:Vital = {}
|
let s:Vital = {}
|
||||||
|
|
||||||
function! s:new(plugin_name) abort
|
function! s:new(plugin_name) abort
|
||||||
let base = deepcopy(s:Vital)
|
let base = deepcopy(s:Vital)
|
||||||
let base.plugin_name = a:plugin_name
|
let base._plugin_name = a:plugin_name
|
||||||
return base
|
return base
|
||||||
endfunction
|
endfunction
|
||||||
|
|
||||||
@ -104,18 +110,10 @@ endfunction
|
|||||||
let s:Vital.unload = s:_function('s:unload')
|
let s:Vital.unload = s:_function('s:unload')
|
||||||
|
|
||||||
function! s:exists(name) abort dict
|
function! s:exists(name) abort dict
|
||||||
let b = exists(printf('*vital#_%s#%s#import', self.plugin_name, substitute(a:name, '\.', '#', 'g')))
|
if a:name !~# '\v^\u\w*%(\.\u\w*)*$'
|
||||||
if b
|
throw 'vital: Invalid module name: ' . a:name
|
||||||
return b
|
|
||||||
endif
|
endif
|
||||||
let name_path = substitute(a:name, '\.', '/', 'g')
|
return s:_module_path(a:name) isnot# ''
|
||||||
let path = printf('%s/_%s/%s.vim', s:vital_base_dir, self.plugin_name, name_path)
|
|
||||||
let b = filereadable(path)
|
|
||||||
if b
|
|
||||||
return b
|
|
||||||
endif
|
|
||||||
let path = printf('%s/_%s/%s.vim', s:vital_base_dir, '_latest__', name_path)
|
|
||||||
let b = filereadable(path)
|
|
||||||
endfunction
|
endfunction
|
||||||
let s:Vital.exists = s:_function('s:exists')
|
let s:Vital.exists = s:_function('s:exists')
|
||||||
|
|
||||||
@ -126,13 +124,20 @@ function! s:search(pattern) abort dict
|
|||||||
endfunction
|
endfunction
|
||||||
let s:Vital.search = s:_function('s:search')
|
let s:Vital.search = s:_function('s:search')
|
||||||
|
|
||||||
|
function! s:plugin_name() abort dict
|
||||||
|
return self._plugin_name
|
||||||
|
endfunction
|
||||||
|
let s:Vital.plugin_name = s:_function('s:plugin_name')
|
||||||
|
|
||||||
function! s:_self_vital_files() abort
|
function! s:_self_vital_files() abort
|
||||||
let base = s:vital_base_dir . '/*/**/*.vim'
|
let builtin = printf('%s/__%s__/', s:vital_base_dir, s:plugin_name)
|
||||||
return split(glob(base, 1), "\n")
|
let installed = printf('%s/_%s/', s:vital_base_dir, s:plugin_name)
|
||||||
|
let base = builtin . ',' . installed
|
||||||
|
return split(globpath(base, '**/*.vim', 1), "\n")
|
||||||
endfunction
|
endfunction
|
||||||
|
|
||||||
function! s:_global_vital_files() abort
|
function! s:_global_vital_files() abort
|
||||||
let pattern = 'autoload/vital/__latest__/**/*.vim'
|
let pattern = 'autoload/vital/__*__/**/*.vim'
|
||||||
return split(globpath(&runtimepath, pattern, 1), "\n")
|
return split(globpath(&runtimepath, pattern, 1), "\n")
|
||||||
endfunction
|
endfunction
|
||||||
|
|
||||||
@ -165,7 +170,7 @@ function! s:_import(name) abort dict
|
|||||||
let s:loaded[a:name] = export_module
|
let s:loaded[a:name] = export_module
|
||||||
if has_key(module, '_vital_loaded')
|
if has_key(module, '_vital_loaded')
|
||||||
try
|
try
|
||||||
call module._vital_loaded(vital#{s:plugin_name}#of())
|
call module._vital_loaded(vital#{s:plugin_name}#new())
|
||||||
catch
|
catch
|
||||||
unlet s:loaded[a:name]
|
unlet s:loaded[a:name]
|
||||||
throw 'vital: fail to call ._vital_loaded(): ' . v:exception
|
throw 'vital: fail to call ._vital_loaded(): ' . v:exception
|
||||||
@ -177,60 +182,92 @@ let s:Vital._import = s:_function('s:_import')
|
|||||||
|
|
||||||
" s:_get_module() returns module object wihch has all script local functions.
|
" s:_get_module() returns module object wihch has all script local functions.
|
||||||
function! s:_get_module(name) abort dict
|
function! s:_get_module(name) abort dict
|
||||||
try
|
let funcname = s:_import_func_name(self.plugin_name(), a:name)
|
||||||
let module = vital#_{self.plugin_name}#{substitute(a:name, '\.', '#', 'g')}#import()
|
if s:_exists_autoload_func_with_source(funcname)
|
||||||
catch /E117: Unknown function:/
|
return call(funcname, [])
|
||||||
if !s:has_latest_module
|
else
|
||||||
throw 'vital: module not found: ' . a:name
|
return s:_get_builtin_module(a:name)
|
||||||
endif
|
endif
|
||||||
" Retry to support loading self modules.
|
|
||||||
let module = s:_get_latest_module(a:name)
|
|
||||||
endtry
|
|
||||||
return module
|
|
||||||
endfunction
|
endfunction
|
||||||
let s:Vital._get_module = s:_function('s:_get_module')
|
|
||||||
|
|
||||||
function! s:_get_latest_module(name) abort
|
function! s:_get_builtin_module(name) abort
|
||||||
return s:sid2sfuncs(s:_module_sid(a:name))
|
return s:sid2sfuncs(s:_module_sid(a:name))
|
||||||
endfunction
|
endfunction
|
||||||
|
|
||||||
|
if s:is_vital_vim
|
||||||
|
" For vital.vim, we can use s:_get_builtin_module directly
|
||||||
|
let s:Vital._get_module = s:_function('s:_get_builtin_module')
|
||||||
|
else
|
||||||
|
let s:Vital._get_module = s:_function('s:_get_module')
|
||||||
|
endif
|
||||||
|
|
||||||
|
function! s:_import_func_name(plugin_name, module_name) abort
|
||||||
|
return printf('vital#_%s#%s#import', a:plugin_name, s:_dot_to_sharp(a:module_name))
|
||||||
|
endfunction
|
||||||
|
|
||||||
function! s:_module_sid(name) abort
|
function! s:_module_sid(name) abort
|
||||||
let module_rel_path = 'autoload/vital/__latest__/' . substitute(a:name, '\.', '/', 'g') . '.vim'
|
let path = s:_module_path(a:name)
|
||||||
let module_full_path = s:_unify_path(get(split(globpath(s:_module_sid_base_dir(), module_rel_path, 0), "\n"), 0, ''))
|
if !filereadable(path)
|
||||||
if !filereadable(module_full_path)
|
|
||||||
throw 'vital: module not found: ' . a:name
|
throw 'vital: module not found: ' . a:name
|
||||||
endif
|
endif
|
||||||
let p = substitute(module_rel_path, '/', '[/\\\\]\\+', 'g')
|
let vital_dir = s:is_vital_vim ? '__\w\+__' : printf('_\{1,2}%s\%%(__\)\?', s:plugin_name)
|
||||||
let sid = s:_sid(module_full_path, p)
|
let base = join([vital_dir, ''], '[/\\]\+')
|
||||||
|
let p = base . substitute('' . a:name, '\.', '[/\\\\]\\+', 'g')
|
||||||
|
let sid = s:_sid(path, p)
|
||||||
if !sid
|
if !sid
|
||||||
call s:_source(module_full_path)
|
call s:_source(path)
|
||||||
let sid = s:_sid(module_full_path, p)
|
let sid = s:_sid(path, p)
|
||||||
if !sid
|
if !sid
|
||||||
throw 'vital: cannot get <SID> from path'
|
throw printf('vital: cannot get <SID> from path: %s', path)
|
||||||
endif
|
endif
|
||||||
endif
|
endif
|
||||||
return sid
|
return sid
|
||||||
endfunction
|
endfunction
|
||||||
|
|
||||||
|
function! s:_module_path(name) abort
|
||||||
|
return get(s:_extract_files(a:name, s:vital_files()), 0, '')
|
||||||
|
endfunction
|
||||||
|
|
||||||
function! s:_module_sid_base_dir() abort
|
function! s:_module_sid_base_dir() abort
|
||||||
return s:is_vital_vim ? &rtp : s:project_root
|
return s:is_vital_vim ? &rtp : s:project_root
|
||||||
endfunction
|
endfunction
|
||||||
|
|
||||||
|
function! s:_dot_to_sharp(name) abort
|
||||||
|
return substitute(a:name, '\.', '#', 'g')
|
||||||
|
endfunction
|
||||||
|
|
||||||
|
" It will sources autoload file if a given func is not already defined.
|
||||||
|
function! s:_exists_autoload_func_with_source(funcname) abort
|
||||||
|
if exists('*' . a:funcname)
|
||||||
|
" Return true if a given func is already defined
|
||||||
|
return 1
|
||||||
|
endif
|
||||||
|
" source a file which may include a given func definition and try again.
|
||||||
|
let path = 'autoload/' . substitute(substitute(a:funcname, '#[^#]*$', '.vim', ''), '#', '/', 'g')
|
||||||
|
call s:_runtime(path)
|
||||||
|
return exists('*' . a:funcname)
|
||||||
|
endfunction
|
||||||
|
|
||||||
|
function! s:_runtime(path) abort
|
||||||
|
execute 'runtime' fnameescape(a:path)
|
||||||
|
endfunction
|
||||||
|
|
||||||
function! s:_source(path) abort
|
function! s:_source(path) abort
|
||||||
execute 'source' fnameescape(a:path)
|
execute 'source' fnameescape(a:path)
|
||||||
endfunction
|
endfunction
|
||||||
|
|
||||||
" @vimlint(EVL102, 1, l:_)
|
" @vimlint(EVL102, 1, l:_)
|
||||||
" @vimlint(EVL102, 1, l:__)
|
" @vimlint(EVL102, 1, l:__)
|
||||||
function! s:_sid(fullpath, filter_pattern) abort
|
function! s:_sid(path, filter_pattern) abort
|
||||||
if has_key(s:cache_sid, a:fullpath)
|
let unified_path = s:_unify_path(a:path)
|
||||||
return s:cache_sid[a:fullpath]
|
if has_key(s:cache_sid, unified_path)
|
||||||
|
return s:cache_sid[unified_path]
|
||||||
endif
|
endif
|
||||||
for line in filter(split(s:_redir(':scriptnames'), "\n"), 'v:val =~# a:filter_pattern')
|
for line in filter(split(s:_redir(':scriptnames'), "\n"), 'v:val =~# a:filter_pattern')
|
||||||
let [_, sid, path; __] = matchlist(line, '^\s*\(\d\+\):\s\+\(.\+\)\s*$')
|
let [_, sid, path; __] = matchlist(line, '^\s*\(\d\+\):\s\+\(.\+\)\s*$')
|
||||||
if s:_unify_path(path) is# a:fullpath
|
if s:_unify_path(path) is# unified_path
|
||||||
let s:cache_sid[a:fullpath] = sid
|
let s:cache_sid[unified_path] = sid
|
||||||
return s:cache_sid[a:fullpath]
|
return s:cache_sid[unified_path]
|
||||||
endif
|
endif
|
||||||
endfor
|
endfor
|
||||||
return 0
|
return 0
|
||||||
@ -246,7 +283,7 @@ function! s:_redir(cmd) abort
|
|||||||
return res
|
return res
|
||||||
endfunction
|
endfunction
|
||||||
|
|
||||||
if filereadable(expand('<sfile>:r') . '.VIM')
|
if filereadable(expand('<sfile>:r') . '.VIM') " is case-insensitive or not
|
||||||
let s:_unify_path_cache = {}
|
let s:_unify_path_cache = {}
|
||||||
" resolve() is slow, so we cache results.
|
" resolve() is slow, so we cache results.
|
||||||
" Note: On windows, vim can't expand path names from 8.3 formats.
|
" Note: On windows, vim can't expand path names from 8.3 formats.
|
||||||
|
@ -1,5 +1,5 @@
|
|||||||
neosnippet
|
neosnippet
|
||||||
024411ba1a5f3d545899c1be6eaa40bba036ae0d
|
645fe7142afdf5ef90e07cd275a15657c3328f53
|
||||||
|
|
||||||
Prelude
|
Prelude
|
||||||
Data.List
|
Data.List
|
||||||
|
Loading…
Reference in New Issue
Block a user