36 Commits
2.7 ... master

Author SHA1 Message Date
Israel Chauca Fuentes
becbd2d353 Merge pull request #308 from kevinhwang91/master
fix: &sw may be a zero
2024-08-06 01:02:38 -05:00
kevinhwang91
382c36bf57 fix: &sw may be a zero
E41: Out of memory!
2024-08-06 12:56:21 +08:00
Israel Chauca Fuentes
537a1da0fa Merge pull request #295 from ypid/fix/python-defaults
Set delimitMate_nesting_quotes for Python by default
2020-12-13 22:12:48 -06:00
Robin Schneider
055978491a Set delimitMate_nesting_quotes for Python by default
Closes: #173
2020-12-13 17:49:44 +01:00
Israel Chauca F
16687aec24 Clean s:get() and s:set() up. Force s:set() to take a default value. Closes #287 2020-07-29 11:50:21 -05:00
Israel Chauca Fuentes
728b57a656 Merge pull request #260 from aschrab/command-window
Do setup for command windows
2017-06-19 00:53:36 -04:00
Aaron Schrab
98143957cf Do setup for command windows 2017-06-18 18:35:29 -04:00
Israel Chauca Fuentes
b5719054be Merge pull request #246 from Atcold/patch-1
Fix doc
2016-07-19 16:19:28 -04:00
Alfredo Canziani
39d8f522f7 Fix doc
Fix unusual formatting in section 3.1
2016-07-19 14:11:06 -04:00
Israel Chauca Fuentes
8bc47fd1c4 Merge pull request #227 from wellle/fix-repeat-and-undo
Fix repeat and undo
2015-09-07 14:58:42 -04:00
Christian Wellenbrock
bc97837c71 Don't break undo sequence when moving in insert mode
Since Vim version 7.4.849 [1] we can move in insert mode without
breaking the undo sequence by inserting <C-G>U before the movement key.

Add s:joinUndo which returns "\<C-G>U" if available.
Use s:joinUndo before doing any <Left> or <Right> movements in insert
mode to keep a single undo point which can be repeated and undone
with a single command.

[1] https://github.com/vim/vim/releases/tag/v7.4.849
2015-09-06 15:42:30 +02:00
Israel Chauca Fuentes
d24ad6b301 Merge pull request #210 from codebeige/fix_expand_cr_for_excluded_ft
Prevent errors inside excluded filetype
2015-05-18 13:24:02 -04:00
Israel Chauca Fuentes
81de76fe52 Update help. 2015-05-17 19:42:50 -04:00
Israel Chauca Fuentes
5945fdfd14 Consider more characters in smart_matchpairs default value. 2015-05-17 19:34:11 -04:00
Israel Chauca Fuentes
9a77c3aee6 Merge branch 'RGBD-fix-maparg-typo' 2015-05-01 22:35:56 -04:00
Oleg Zubchenko
342a04b427 fix maparg typo 2015-04-27 21:11:57 +03:00
Tibor Claassen
03e94587ae Add a guard clause to disable expansion for excluded filetypes 2015-03-28 15:48:40 +02:00
Israel Chauca Fuentes
c78a6e6d93 Allow using commas and colons in matchpairs. Fix #208. 2015-02-12 09:09:48 -05:00
Israel Chauca Fuentes
470c053a3b Better handling of insert_eol_marker. Should fix #195. 2015-01-17 14:03:48 -05:00
Israel Chauca Fuentes
254a89d67c Call s:setup() directly in the plugin. Should fix #202.
- Move 'call s:setup()' out of the autocmd.
- Add a test for the first buffer without filetype set.
2015-01-15 11:21:09 -05:00
Israel Chauca Fuentes
e7b4dedb84 Add option delimitMate_insert_eol_marker. Closes #195. 2015-01-08 17:14:27 -05:00
Israel Chauca Fuentes
21a3ade90c Use s:get() and s:set() instead of the abbreviated forms. 2015-01-06 08:50:17 -05:00
Israel Chauca Fuentes
8e30e70bcd Refactor reporting code. 2015-01-05 02:16:09 -05:00
Israel Chauca Fuentes
ac792c01b6 Indent with spaces. 2015-01-04 20:25:50 -05:00
Israel Chauca Fuentes
c23ef684e3 Add :DelimitMateOn, :DelimitMateOff & remove s:DelimitMateSwitch(). 2015-01-04 20:13:11 -05:00
Israel Chauca Fuentes
b63924f2b2 Update doc. 2015-01-04 20:09:00 -05:00
Israel Chauca Fuentes
07b7cc969f Merge pull request #201 from kballard/mappings-user-event
Add 2 User events when mapping and unmapping
2015-01-02 20:32:18 -05:00
Israel Chauca Fuentes
13e52d42ae Do not consider quotes for smart_matchpairs. Closes #200. 2015-01-02 12:08:16 -05:00
Israel Chauca Fuentes
aa9d737763 Rename functions. 2015-01-02 12:07:31 -05:00
Daniel Hahler
bf2b68edab Remove call to s:option_init("excluded_ft"): it is a global setting only 2015-01-01 14:58:41 -05:00
Israel Chauca Fuentes
fe9022433d Use :unlet only when necessary. 2015-01-01 09:41:32 -05:00
Israel Chauca Fuentes
6f7e6413ce Fix doco. 2014-12-30 21:02:44 -05:00
Kevin Ballard
a9a37854da Minor documentation tweaks
Fix a typo in a hyperlink, and change the sample code for
delimitMate#JumpAny() to use an <expr> mapping instead of <C-R>=.
2014-12-29 19:33:24 -08:00
Kevin Ballard
0739792d01 Add 2 User events when mapping and unmapping
delimitMate has some nice logic for doing per-filetype mappings, but
this logic can't be used when users provide mappings directly. To remedy
this, add two User events `delimitMate_map` and `delimitMate_unmap` that
are fired at the appropriate times. Users can use these events to define
per-filetype mappings just as delimitMate does.
2014-12-29 19:33:15 -08:00
Kevin Ballard
6f4f1b06d3 Be more conservative about unmapping
Restrict unmapping to check for '^<Plug>delimitMate' (case sensitive)
instead of 'delimitMate' (case insensitive). This should make it less
likely to accidentally trigger on custom user keybinds that reference
delimitMate.
2014-12-29 18:37:51 -08:00
Israel Chauca Fuentes
0049b07a1c Fix Makefile and gitignore. 2014-12-03 17:06:37 -05:00
9 changed files with 1064 additions and 972 deletions

1
.gitignore vendored
View File

@@ -1,6 +1,7 @@
*.sw?
*.un?
*.vba
*.vmb
*.zip
*.gz
vimball.txt

View File

@@ -4,7 +4,6 @@ LIB = $(wildcard autoload/*.vim)
SOURCES += $(LIB)
DOC = $(wildcard doc/*.txt)
SOURCES += $(DOC)
#NAME = $(shell basename "$$PWD")
NAME = delimitMate
VERSION = $(shell $(SED) -n -e '/Current \+release/{s/^ \+\([0-9.]\+\).*/\1/;p;}' $(firstword $(DOC)))
FILENAME = $(NAME)-$(VERSION)
@@ -28,8 +27,8 @@ clean:
rm -f */*.orig *.~* .VimballRecord *.zip *.gz *.vmb
distclean: clean
-zsh -c 'setopt extendedglob; rm -f ^(README.md|Makefile)'
-zsh -c 'setopt extendedglob; rm -f .^(git|README.md|Makefile)*'
-zsh -c 'setopt extendedglob; rm -f ^(README.md|Makefile|basic_vimrc)(.)'
-zsh -c 'setopt extendedglob; rm -f .^(git|README.md|Makefile|basic_vimrc)*'
undo:
for i in */*.orig; do mv -f "$$i" "$${i%.*}"; done
@@ -74,7 +73,7 @@ done;
zip $@ $^
%.vmb.gz: vimball
gzip -f $(basename $@)
gzip -f < $(basename $@) > $@
%.tar.gz: $(SOURCES)
tar -cvzf $@ $^

View File

@@ -6,37 +6,26 @@
" Manual: Read ":help delimitMate".
" ============================================================================
" Utilities {{{
"let delimitMate_loaded = 1
if !exists('s:options')
let s:options = {}
endif
function! s:s(name, value, ...) "{{{
let scope = a:0 ? a:1 : 's'
function! s:set(name, value) "{{{
let bufnr = bufnr('%')
if !exists('s:options[bufnr]')
if !has_key(s:options, bufnr)
let s:options[bufnr] = {}
endif
if scope == 's'
let name = 's:options.' . bufnr . '.' . a:name
else
let name = scope . ':delimitMate_' . a:name
endif
exec 'silent! unlet! ' . name
exec 'let ' . name . ' = a:value'
let s:options[bufnr][a:name] = a:value
endfunction "}}}
function! s:g(name, ...) "{{{
if a:0 == 2
return deepcopy(get(a:2, 'delimitMate_' . a:name, a:1))
elseif a:0 == 1
let bufoptions = get(s:options, bufnr('%'), {})
return deepcopy(get(bufoptions, a:name, a:1))
else
return deepcopy(eval('s:options.' . bufnr('%') . '.' . a:name))
function! s:get(...) "{{{
let options = deepcopy(eval('s:options.' . bufnr('%')))
if a:0
return options[a:1]
endif
return options
endfunction "}}}
function! s:exists(name, ...) "{{{
@@ -50,18 +39,10 @@ function! s:exists(name, ...) "{{{
return exists(scope . ':' . name)
endfunction "}}}
function! delimitMate#Set(...) "{{{
return call('s:s', a:000)
endfunction "}}}
function! delimitMate#Get(...) "{{{
return call('s:g', a:000)
endfunction "}}}
function! delimitMate#ShouldJump(...) "{{{
function! s:is_jump(...) "{{{
" Returns 1 if the next character is a closing delimiter.
let char = delimitMate#GetCharFromCursor(0)
let list = s:g('right_delims') + s:g('quotes_list')
let char = s:get_char(0)
let list = s:get('right_delims') + s:get('quotes_list')
" Closing delimiter on the right.
if (!a:0 && index(list, char) > -1)
@@ -70,65 +51,49 @@ function! delimitMate#ShouldJump(...) "{{{
endif
" Closing delimiter with space expansion.
let nchar = delimitMate#GetCharFromCursor(1)
if !a:0 && s:g('expand_space') && char == " "
let nchar = s:get_char(1)
if !a:0 && s:get('expand_space') && char == " "
if index(list, nchar) > -1
return 2
endif
elseif a:0 && s:g('expand_space') && nchar == a:1 && char == ' '
elseif a:0 && s:get('expand_space') && nchar == a:1 && char == ' '
return 3
endif
if !s:g('jump_expansion')
if !s:get('jump_expansion')
return 0
endif
" Closing delimiter with CR expansion.
let uchar = matchstr(getline(line('.') + 1), '^\s*\zs\S')
if !a:0 && s:g('expand_cr') && char == ""
if !a:0 && s:get('expand_cr') && char == ""
if index(list, uchar) > -1
return 4
endif
elseif a:0 && s:g('expand_cr') && uchar == a:1
elseif a:0 && s:get('expand_cr') && uchar == a:1
return 5
endif
return 0
endfunction "}}}
function! delimitMate#IsEmptyPair(str) "{{{
if strlen(substitute(a:str, ".", "x", "g")) != 2
return 0
endif
let idx = index(s:g('left_delims'), matchstr(a:str, '^.'))
if idx > -1 &&
\ s:g('right_delims')[idx] == matchstr(a:str, '.$')
return 1
endif
let idx = index(s:g('quotes_list'), matchstr(a:str, '^.'))
if idx > -1 &&
\ s:g('quotes_list')[idx] == matchstr(a:str, '.$')
return 1
endif
return 0
endfunction "}}}
function! delimitMate#RightQ(char) "{{{
function! s:rquote(char) "{{{
let pos = matchstr(getline('.')[col('.') : ], escape(a:char, '[]*.^$\'), 1)
let i = 0
while delimitMate#GetCharFromCursor(i) ==# a:char
while s:get_char(i) ==# a:char
let i += 1
endwhile
return i
endfunction "}}}
function! delimitMate#LeftQ(char) "{{{
function! s:lquote(char) "{{{
let i = 0
while delimitMate#GetCharFromCursor(i - 1) ==# a:char
while s:get_char(i - 1) ==# a:char
let i -= 1
endwhile
return i * -1
endfunction "}}}
function! delimitMate#GetCharFromCursor(...) "{{{
function! s:get_char(...) "{{{
let idx = col('.') - 1
if !a:0 || (a:0 && a:1 >= 0)
" Get char from cursor.
@@ -140,44 +105,44 @@ function! delimitMate#GetCharFromCursor(...) "{{{
let line = getline('.')[: idx - 1]
let pos = 0 - (1 + a:1)
return matchstr(line, '.\ze'.repeat('.', pos).'$')
endfunction "delimitMate#GetCharFromCursor }}}
endfunction "s:get_char }}}
function! delimitMate#IsCRExpansion(...) " {{{
function! s:is_cr_expansion(...) " {{{
let nchar = getline(line('.')-1)[-1:]
let schar = matchstr(getline(line('.')+1), '^\s*\zs\S')
let isEmpty = a:0 ? getline('.') =~ '^\s*$' : empty(getline('.'))
if index(s:g('left_delims'), nchar) > -1
\ && index(s:g('left_delims'), nchar)
\ == index(s:g('right_delims'), schar)
if index(s:get('left_delims'), nchar) > -1
\ && index(s:get('left_delims'), nchar)
\ == index(s:get('right_delims'), schar)
\ && isEmpty
return 1
elseif index(s:g('quotes_list'), nchar) > -1
\ && index(s:g('quotes_list'), nchar)
\ == index(s:g('quotes_list'), schar)
elseif index(s:get('quotes_list'), nchar) > -1
\ && index(s:get('quotes_list'), nchar)
\ == index(s:get('quotes_list'), schar)
\ && isEmpty
return 1
else
return 0
endif
endfunction " }}} delimitMate#IsCRExpansion()
endfunction " }}} s:is_cr_expansion()
function! delimitMate#IsSpaceExpansion() " {{{
function! s:is_space_expansion() " {{{
if col('.') > 2
let pchar = delimitMate#GetCharFromCursor(-2)
let nchar = delimitMate#GetCharFromCursor(1)
let pchar = s:get_char(-2)
let nchar = s:get_char(1)
let isSpaces =
\ (delimitMate#GetCharFromCursor(-1)
\ == delimitMate#GetCharFromCursor(0)
\ && delimitMate#GetCharFromCursor(-1) == " ")
\ (s:get_char(-1)
\ == s:get_char(0)
\ && s:get_char(-1) == " ")
if index(s:g('left_delims'), pchar) > -1 &&
\ index(s:g('left_delims'), pchar)
\ == index(s:g('right_delims'), nchar) &&
if index(s:get('left_delims'), pchar) > -1 &&
\ index(s:get('left_delims'), pchar)
\ == index(s:get('right_delims'), nchar) &&
\ isSpaces
return 1
elseif index(s:g('quotes_list'), pchar) > -1 &&
\ index(s:g('quotes_list'), pchar)
\ == index(s:g('quotes_list'), nchar) &&
elseif index(s:get('quotes_list'), pchar) > -1 &&
\ index(s:get('quotes_list'), pchar)
\ == index(s:get('quotes_list'), nchar) &&
\ isSpaces
return 1
endif
@@ -185,92 +150,69 @@ function! delimitMate#IsSpaceExpansion() " {{{
return 0
endfunction " }}} IsSpaceExpansion()
function! delimitMate#WithinEmptyPair() "{{{
" if cursor is at column 1 return 0
if col('.') == 1
return 0
endif
function! s:is_empty_matchpair() "{{{
" get char before the cursor.
let char1 = delimitMate#GetCharFromCursor(-1)
" get char under the cursor.
let char2 = delimitMate#GetCharFromCursor(0)
return delimitMate#IsEmptyPair( char1.char2 )
endfunction "}}}
function! delimitMate#WithinEmptyMatchpair() "{{{
" get char before the cursor.
let open = delimitMate#GetCharFromCursor(-1)
let idx = index(s:g('left_delims'), open)
let open = s:get_char(-1)
let idx = index(s:get('left_delims'), open)
if idx == -1
return 0
endif
let close = get(s:g('right_delims'), idx, '')
return close ==# delimitMate#GetCharFromCursor(0)
let close = get(s:get('right_delims'), idx, '')
return close ==# s:get_char(0)
endfunction "}}}
function! delimitMate#WithinEmptyQuotes() "{{{
function! s:is_empty_quotes() "{{{
" get char before the cursor.
let quote = delimitMate#GetCharFromCursor(-1)
let idx = index(s:g('quotes_list'), quote)
let quote = s:get_char(-1)
let idx = index(s:get('quotes_list'), quote)
if idx == -1
return 0
endif
return quote ==# delimitMate#GetCharFromCursor(0)
return quote ==# s:get_char(0)
endfunction "}}}
function! delimitMate#CursorIdx() "{{{
function! s:cursor_idx() "{{{
let idx = len(split(getline('.')[: col('.') - 1], '\zs')) - 1
return idx
endfunction "delimitMate#CursorCol }}}
function! delimitMate#GetSyntaxRegion(line, col) "{{{
return synIDattr(synIDtrans(synID(a:line, a:col, 1)), 'name')
endfunction " }}}
function! delimitMate#GetCurrentSyntaxRegion() "{{{
function! s:get_syn_name() "{{{
let col = col('.')
if col == col('$')
let col = col - 1
endif
return delimitMate#GetSyntaxRegion(line('.'), col)
return synIDattr(synIDtrans(synID(line('.'), col, 1)), 'name')
endfunction " }}}
function! delimitMate#GetCurrentSyntaxRegionIf(char) "{{{
let col = col('.')
let origin_line = getline('.')
let changed_line = strpart(origin_line, 0, col - 1) . a:char
\ . strpart(origin_line, col - 1)
call setline('.', changed_line)
let region = delimitMate#GetSyntaxRegion(line('.'), col)
call setline('.', origin_line)
return region
endfunction "}}}
function! delimitMate#IsForbidden(char) "{{{
if !s:g('excluded_regions_enabled')
function! s:is_excluded_ft(ft) "{{{
if !exists("g:delimitMate_excluded_ft")
return 0
endif
let region = delimitMate#GetCurrentSyntaxRegion()
"if index(s:g('excluded_regions_list'), region) >= 0
" "echom "Forbidden 1!"
" return 1
"endif
"let region = delimitMate#GetCurrentSyntaxRegionIf(a:char)
"echom "Forbidden 2!"
return index(s:g('excluded_regions_list'), region) >= 0
return index(split(g:delimitMate_excluded_ft, ','), a:ft, 0, 1) >= 0
endfunction "}}}
function! delimitMate#BalancedParens(char) "{{{
function! s:is_forbidden(char) "{{{
if s:is_excluded_ft(&filetype)
return 1
endif
if !s:get('excluded_regions_enabled')
return 0
endif
let region = s:get_syn_name()
return index(s:get('excluded_regions_list'), region) >= 0
endfunction "}}}
function! s:balance_matchpairs(char) "{{{
" Returns:
" = 0 => Parens balanced.
" > 0 => More opening parens.
" < 0 => More closing parens.
let line = getline('.')
let col = delimitMate#CursorIdx() - 1
let col = s:cursor_idx() - 1
let col = col >= 0 ? col : 0
let list = split(line, '\zs')
let left = s:g('left_delims')[index(s:g('right_delims'), a:char)]
let left = s:get('left_delims')[index(s:get('right_delims'), a:char)]
let right = a:char
let opening = 0
let closing = 0
@@ -297,9 +239,9 @@ function! delimitMate#BalancedParens(char) "{{{
return opening - closing
endfunction "}}}
function! delimitMate#IsSmartQuote(char) "{{{
function! s:is_smart_quote(char) "{{{
" TODO: Allow using a:char in the pattern.
let tmp = s:g('smart_quotes')
let tmp = s:get('smart_quotes')
if empty(tmp)
return 0
endif
@@ -313,20 +255,58 @@ function! delimitMate#IsSmartQuote(char) "{{{
return result
endfunction "delimitMate#SmartQuote }}}
" }}}
function! delimitMate#Set(...) "{{{
return call('s:set', a:000)
endfunction "}}}
function! delimitMate#Get(...) "{{{
return call('s:get', a:000)
endfunction "}}}
function! delimitMate#ShouldJump(...) "{{{
return call('s:is_jump', a:000)
endfunction "}}}
function! delimitMate#IsEmptyPair(str) "{{{
if strlen(substitute(a:str, ".", "x", "g")) != 2
return 0
endif
let idx = index(s:get('left_delims'), matchstr(a:str, '^.'))
if idx > -1 &&
\ s:get('right_delims')[idx] == matchstr(a:str, '.$')
return 1
endif
let idx = index(s:get('quotes_list'), matchstr(a:str, '^.'))
if idx > -1 &&
\ s:get('quotes_list')[idx] == matchstr(a:str, '.$')
return 1
endif
return 0
endfunction "}}}
function! delimitMate#WithinEmptyPair() "{{{
" if cursor is at column 1 return 0
if col('.') == 1
return 0
endif
" get char before the cursor.
let char1 = s:get_char(-1)
" get char under the cursor.
let char2 = s:get_char(0)
return delimitMate#IsEmptyPair( char1.char2 )
endfunction "}}}
" Doers {{{
function! delimitMate#SkipDelim(char) "{{{
if delimitMate#IsForbidden(a:char)
if s:is_forbidden(a:char)
return a:char
endif
let col = col('.') - 1
let line = getline('.')
if col > 0
let cur = delimitMate#GetCharFromCursor(0)
let pre = delimitMate#GetCharFromCursor(-1)
let cur = s:get_char(0)
let pre = s:get_char(-1)
else
let cur = delimitMate#GetCharFromCursor(0)
let cur = s:get_char(0)
let pre = ""
endif
if pre == "\\"
@@ -337,7 +317,7 @@ function! delimitMate#SkipDelim(char) "{{{
return a:char . "\<Del>"
elseif delimitMate#IsEmptyPair( pre . a:char )
" Add closing delimiter and jump back to the middle.
return a:char . "\<Left>"
return a:char . s:joinUndo() . "\<Left>"
else
" Nothing special here, return the same character.
return a:char
@@ -345,45 +325,46 @@ function! delimitMate#SkipDelim(char) "{{{
endfunction "}}}
function! delimitMate#ParenDelim(right) " {{{
let left = s:g('left_delims')[index(s:g('right_delims'),a:right)]
if delimitMate#IsForbidden(a:right)
let left = s:get('left_delims')[index(s:get('right_delims'),a:right)]
if s:is_forbidden(a:right)
return left
endif
" Try to balance matchpairs
if s:g('balance_matchpairs') &&
\ delimitMate#BalancedParens(a:right) < 0
if s:get('balance_matchpairs') &&
\ s:balance_matchpairs(a:right) < 0
return left
endif
let line = getline('.')
let col = col('.')-2
if s:g('smart_matchpairs') != ''
let smart_matchpairs = substitute(s:g('smart_matchpairs'), '\\!', left, 'g')
if s:get('smart_matchpairs') != ''
let smart_matchpairs = substitute(s:get('smart_matchpairs'), '\\!', left, 'g')
let smart_matchpairs = substitute(smart_matchpairs, '\\#', a:right, 'g')
if line[col+1:] =~ smart_matchpairs
return left
endif
endif
let tail = len(line) == (col + 1) ? s:g('eol_marker') : ''
"if (col) < 0
" call setline('.',a:right.line)
"endif
return left . a:right . tail . repeat("\<Left>", len(split(tail, '\zs')) + 1)
if len(line) == (col + 1) && s:get('insert_eol_marker') == 1
let tail = s:get('eol_marker')
else
let tail = ''
endif
return left . a:right . tail . repeat(s:joinUndo() . "\<Left>", len(split(tail, '\zs')) + 1)
endfunction " }}}
function! delimitMate#QuoteDelim(char) "{{{
if delimitMate#IsForbidden(a:char)
if s:is_forbidden(a:char)
return a:char
endif
let char_at = delimitMate#GetCharFromCursor(0)
let char_before = delimitMate#GetCharFromCursor(-1)
let nesting_on = index(s:g('nesting_quotes'), a:char) > -1
let left_q = nesting_on ? delimitMate#LeftQ(a:char) : 0
let char_at = s:get_char(0)
let char_before = s:get_char(-1)
let nesting_on = index(s:get('nesting_quotes'), a:char) > -1
let left_q = nesting_on ? s:lquote(a:char) : 0
if nesting_on && left_q > 1
" Nesting quotes.
let right_q = delimitMate#RightQ(a:char)
let right_q = s:rquote(a:char)
let quotes = right_q > left_q + 1 ? 0 : left_q - right_q + 2
let lefts = quotes - 1
return repeat(a:char, quotes) . repeat("\<Left>", lefts)
return repeat(a:char, quotes) . repeat(s:joinUndo() . "\<Left>", lefts)
elseif char_at == a:char
" Inside an empty pair, jump out
return a:char . "\<Del>"
@@ -391,63 +372,63 @@ function! delimitMate#QuoteDelim(char) "{{{
" If we are in a vim file and it looks like we're starting a comment, do
" not add a closing char.
return a:char
elseif delimitMate#IsSmartQuote(a:char)
elseif s:is_smart_quote(a:char)
" Seems like a smart quote, insert a single char.
return a:char
elseif (char_before == a:char && char_at != a:char)
\ && !empty(s:g('smart_quotes'))
\ && !empty(s:get('smart_quotes'))
" Seems like we have an unbalanced quote, insert one quotation
" mark and jump to the middle.
return a:char . "\<Left>"
return a:char . s:joinUndo() . "\<Left>"
else
" Insert a pair and jump to the middle.
let sufix = ''
if !empty(s:g('eol_marker')) && col('.') - 1 == len(getline('.'))
let idx = len(s:g('eol_marker')) * -1
if !empty(s:get('eol_marker')) && col('.') - 1 == len(getline('.'))
let idx = len(s:get('eol_marker')) * -1
let marker = getline('.')[idx : ]
let has_marker = marker == s:g('eol_marker')
let sufix = !has_marker ? s:g('eol_marker') : ''
let has_marker = marker == s:get('eol_marker')
let sufix = !has_marker ? s:get('eol_marker') : ''
endif
return a:char . a:char . "\<Left>"
return a:char . a:char . s:joinUndo() . "\<Left>"
endif
endfunction "}}}
function! delimitMate#JumpOut(char) "{{{
if delimitMate#IsForbidden(a:char)
if s:is_forbidden(a:char)
return a:char
endif
let jump = delimitMate#ShouldJump(a:char)
let jump = s:is_jump(a:char)
if jump == 1
" HACK: Instead of <Right>, we remove the char to be jumped over and
" insert it again. This will trigger re-indenting via 'indentkeys'.
" Ref: https://github.com/Raimondi/delimitMate/issues/168
return "\<Del>".a:char
elseif jump == 3
return "\<Right>\<Right>"
return s:joinUndo() . "\<Right>" . s:joinUndo() . "\<Right>"
elseif jump == 5
return "\<Down>\<C-O>I\<Right>"
return "\<Down>\<C-O>I" . s:joinUndo() . "\<Right>"
else
return a:char
endif
endfunction " }}}
function! delimitMate#JumpAny(...) " {{{
if delimitMate#IsForbidden('')
if s:is_forbidden('')
return ''
endif
if !delimitMate#ShouldJump()
if !s:is_jump()
return ''
endif
" Let's get the character on the right.
let char = delimitMate#GetCharFromCursor(0)
let char = s:get_char(0)
if char == " "
" Space expansion.
return "\<Right>\<Right>"
return s:joinUndo() . "\<Right>" . s:joinUndo() . "\<Right>"
elseif char == ""
" CR expansion.
return "\<CR>" . getline(line('.') + 1)[0] . "\<Del>\<Del>"
else
return "\<Right>"
return s:joinUndo() . "\<Right>"
endif
endfunction " delimitMate#JumpAny() }}}
@@ -456,12 +437,12 @@ function! delimitMate#JumpMany() " {{{
let rights = ""
let found = 0
for char in line
if index(s:g('quotes_list'), char) >= 0 ||
\ index(s:g('right_delims'), char) >= 0
let rights .= "\<Right>"
if index(s:get('quotes_list'), char) >= 0 ||
\ index(s:get('right_delims'), char) >= 0
let rights .= s:joinUndo() . "\<Right>"
let found = 1
elseif found == 0
let rights .= "\<Right>"
let rights .= s:joinUndo() . "\<Right>"
else
break
endif
@@ -474,28 +455,37 @@ function! delimitMate#JumpMany() " {{{
endfunction " delimitMate#JumpMany() }}}
function! delimitMate#ExpandReturn() "{{{
if delimitMate#IsForbidden("")
if s:is_forbidden("")
return "\<CR>"
endif
let escaped = delimitMate#CursorIdx() >= 2
\ && delimitMate#GetCharFromCursor(-2) == '\'
let expand_right_matchpair = s:g('expand_cr') == 2
\ && index(s:g('right_delims'), delimitMate#GetCharFromCursor(0)) > -1
let expand_inside_quotes = s:g('expand_inside_quotes')
\ && delimitMate#WithinEmptyQuotes()
let escaped = s:cursor_idx() >= 2
\ && s:get_char(-2) == '\'
let expand_right_matchpair = s:get('expand_cr') == 2
\ && index(s:get('right_delims'), s:get_char(0)) > -1
let expand_inside_quotes = s:get('expand_inside_quotes')
\ && s:is_empty_quotes()
\ && !escaped
let is_empty_matchpair = s:is_empty_matchpair()
if !pumvisible( )
\ && (delimitMate#WithinEmptyMatchpair()
\ && ( is_empty_matchpair
\ || expand_right_matchpair
\ || expand_inside_quotes)
let val = "\<Esc>a\<CR>"
let val = "\<Esc>a"
if is_empty_matchpair && s:get('insert_eol_marker') == 2
\ && !search(escape(s:get('eol_marker'), '[]\.*^$').'$', 'cnW', '.')
let tail = getline('.')[col('.') - 1 : ]
let times = len(split(tail, '\zs'))
let val .= repeat(s:joinUndo() . "\<Right>", times) . s:get('eol_marker') . repeat(s:joinUndo() . "\<Left>", times + 1)
endif
let val .= "\<CR>"
if &smartindent && !&cindent && !&indentexpr
\ && delimitMate#GetCharFromCursor(0) == '}'
\ && s:get_char(0) == '}'
" indentation is controlled by 'smartindent', and the first character on
" the new line is '}'. If this were typed manually it would reindent to
" match the current line. Let's reproduce that behavior.
let shifts = indent('.') / &sw
let spaces = indent('.') - (shifts * &sw)
let sw = &sw == 0 ? &ts : &sw
let shifts = indent('.') / sw
let spaces = indent('.') - (shifts * sw)
let val .= "^\<C-D>".repeat("\<C-T>", shifts).repeat(' ', spaces)
endif
" Expand:
@@ -509,32 +499,32 @@ function! delimitMate#ExpandReturn() "{{{
endfunction "}}}
function! delimitMate#ExpandSpace() "{{{
if delimitMate#IsForbidden("\<Space>")
if s:is_forbidden("\<Space>")
return "\<Space>"
endif
let escaped = delimitMate#CursorIdx() >= 2
\ && delimitMate#GetCharFromCursor(-2) == '\'
let expand_inside_quotes = s:g('expand_inside_quotes')
\ && delimitMate#WithinEmptyQuotes()
let escaped = s:cursor_idx() >= 2
\ && s:get_char(-2) == '\'
let expand_inside_quotes = s:get('expand_inside_quotes')
\ && s:is_empty_quotes()
\ && !escaped
if delimitMate#WithinEmptyMatchpair() || expand_inside_quotes
if s:is_empty_matchpair() || expand_inside_quotes
" Expand:
return "\<Space>\<Space>\<Left>"
return "\<Space>\<Space>" . s:joinUndo() . "\<Left>"
else
return "\<Space>"
endif
endfunction "}}}
function! delimitMate#BS() " {{{
if delimitMate#IsForbidden("")
if s:is_forbidden("")
let extra = ''
elseif &bs !~ 'start\|2'
let extra = ''
elseif delimitMate#WithinEmptyPair()
let extra = "\<Del>"
elseif delimitMate#IsSpaceExpansion()
elseif s:is_space_expansion()
let extra = "\<Del>"
elseif delimitMate#IsCRExpansion()
elseif s:is_cr_expansion()
let extra = repeat("\<Del>",
\ len(matchstr(getline(line('.') + 1), '^\s*\S')))
else
@@ -543,151 +533,124 @@ function! delimitMate#BS() " {{{
return "\<BS>" . extra
endfunction " }}} delimitMate#BS()
" }}}
" Tools: {{{
function! delimitMate#TestMappings() "{{{
echom 1
%d
let options = sort([
\ 'apostrophes',
\ 'autoclose',
\ 'balance_matchpairs',
\ 'jump_expansion',
\ 'eol_marker',
\ 'excluded_ft',
\ 'excluded_regions',
\ 'expand_cr',
\ 'expand_space',
\ 'matchpairs',
\ 'nesting_quotes',
\ 'quotes',
\ 'smart_matchpairs',
\ 'smart_quotes',
\ 'expand_inside_quotes',
\])
let optoutput = ['delimitMate Report', '==================', '',
\ '* Options: ( ) default, (g) global, (b) buffer','']
for option in options
let scope = s:exists(option, 'b') ? 'b'
\ : s:exists(option, 'g') ? 'g' : ' '
call add(optoutput,
\'(' . scope . ')' . ' delimitMate_' . option . ' = ' . string(s:g(option)))
function! delimitMate#Test() "{{{
%d _
" Check for script options:
let result = [
\ 'delimitMate Report',
\ '==================',
\ '',
\ '* Options: ( ) default, (g) global, (b) buffer',
\ '']
for option in sort(keys(s:options[bufnr('%')]))
if s:exists(option, 'b')
let scope = '(b)'
elseif s:exists(option, 'g')
let scope = '(g)'
else
let scope = '( )'
endif
call add(result,
\ scope . ' delimitMate_' . option
\ . ' = '
\ . string(s:get(option)))
endfor
call append(line('$'), optoutput + ['--------------------',''])
call add(result, '')
" Check if mappings were set. {{{
let imaps = s:g('right_delims')
let imaps += ( s:g('autoclose') ? s:g('left_delims') : [] )
let imaps +=
\ s:g('quotes_list') +
\ s:g('apostrophes_list') +
\ ['<BS>', '<S-BS>', '<S-Tab>', '<Esc>', '<C-G>g']
let imaps += ( s:g('expand_cr') ? ['<CR>'] : [] )
let imaps += ( s:g('expand_space') ? ['<Space>'] : [] )
let option = 'delimitMate_excluded_ft'
call add(result,
\(exists('g:'.option) ? '(g) ' : '( ) g:') . option . ' = '
\. string(get(g:, option, '')))
let imappings = []
for map in imaps
call add(result, '--------------------')
call add(result, '')
" Check if mappings were set.
let left_delims = s:get('autoclose') ? s:get('left_delims') : []
let special_keys = ['<BS>', '<S-BS>', '<S-Tab>', '<C-G>g']
if s:get('expand_cr')
call add(special_keys, '<CR>')
endif
if s:get('expand_space')
call add(special_keys, '<Space>')
endif
let maps =
\ s:get('right_delims')
\ + left_delims
\ + s:get('quotes_list')
\ + s:get('apostrophes_list')
\ + special_keys
call add(result, '* Mappings:')
call add(result, '')
for map in maps
let output = ''
if map == '|'
let map = '<Bar>'
endif
redir => output | execute "verbose imap ".map | redir END
let imappings += split(output, '\n')
call extend(result, split(output, '\n'))
endfor
unlet! output
let output = ['* Mappings:', ''] + imappings + ['--------------------', '']
call append('$', output+['* Showcase:', ''])
" }}}
if s:g('autoclose')
" {{{
for i in range(len(s:g('left_delims')))
exec "normal Go0\<C-D>Open: " . s:g('left_delims')[i]. "|"
exec "normal o0\<C-D>Delete: " . s:g('left_delims')[i] . "\<BS>|"
exec "normal o0\<C-D>Exit: " . s:g('left_delims')[i] . s:g('right_delims')[i] . "|"
if s:g('expand_space') == 1
exec "normal o0\<C-D>Space: " . s:g('left_delims')[i] . " |"
exec "normal o0\<C-D>Delete space: " . s:g('left_delims')[i]
\ . " \<BS>|"
endif
if s:g('expand_cr') == 1
exec "normal o0\<C-D>Car return: " . s:g('left_delims')[i] .
\ "\<CR>|"
exec "normal Go0\<C-D>Delete car return: " . s:g('left_delims')[i]
\ . "\<CR>0\<C-D>\<BS>|"
endif
call append(line('$'), '')
endfor
for i in range(len(s:g('quotes_list')))
exec "normal Go0\<C-D>Open: " . s:g('quotes_list')[i] . "|"
exec "normal o0\<C-D>Delete: " . s:g('quotes_list')[i] . "\<BS>|"
exec "normal o0\<C-D>Exit: " . s:g('quotes_list')[i] . s:g('quotes_list')[i] . "|"
if s:g('expand_space') == 1
exec "normal o0\<C-D>Space: " . s:g('quotes_list')[i] . " |"
exec "normal o0\<C-D>Delete space: " . s:g('quotes_list')[i]
\ . " \<BS>|"
endif
if s:g('expand_cr') == 1
exec "normal o0\<C-D>Car return: " . s:g('quotes_list')[i]
\ . "\<CR>|"
exec "normal Go0\<C-D>Delete car return: " . s:g('quotes_list')[i]
\ . "\<CR>\<BS>|"
endif
call append(line('$'), '')
endfor
"}}}
else
"{{{
for i in range(len(s:g('left_delims')))
exec "normal GoOpen & close: " . s:g('left_delims')[i]
\ . s:g('right_delims')[i] . "|"
exec "normal oDelete: " . s:g('left_delims')[i]
\ . s:g('right_delims')[i] . "\<BS>|"
exec "normal oExit: " . s:g('left_delims')[i] . s:g('right_delims')[i]
\ . s:g('right_delims')[i] . "|"
if s:g('expand_space') == 1
exec "normal oSpace: " . s:g('left_delims')[i]
\ . s:g('right_delims')[i] . " |"
exec "normal oDelete space: " . s:g('left_delims')[i]
\ . s:g('right_delims')[i] . " \<BS>|"
endif
if s:g('expand_cr') == 1
exec "normal oCar return: " . s:g('left_delims')[i]
\ . s:g('right_delims')[i] . "\<CR>|"
exec "normal GoDelete car return: " . s:g('left_delims')[i]
\ . s:g('right_delims')[i] . "\<CR>\<BS>|"
endif
call append(line('$'), '')
endfor
for i in range(len(s:g('quotes_list')))
exec "normal GoOpen & close: " . s:g('quotes_list')[i]
\ . s:g('quotes_list')[i] . "|"
exec "normal oDelete: " . s:g('quotes_list')[i]
\ . s:g('quotes_list')[i] . "\<BS>|"
exec "normal oExit: " . s:g('quotes_list')[i] . s:g('quotes_list')[i]
\ . s:g('quotes_list')[i] . "|"
if s:g('expand_space') == 1
exec "normal oSpace: " . s:g('quotes_list')[i]
\ . s:g('quotes_list')[i] . " |"
exec "normal oDelete space: " . s:g('quotes_list')[i]
\ . s:g('quotes_list')[i] . " \<BS>|"
endif
if s:g('expand_cr') == 1
exec "normal oCar return: " . s:g('quotes_list')[i]
\ . s:g('quotes_list')[i] . "\<CR>|"
exec "normal GoDelete car return: " . s:g('quotes_list')[i]
\ . s:g('quotes_list')[i] . "\<CR>\<BS>|"
endif
call append(line('$'), '')
endfor
endif "}}}
redir => setoptions | set | filetype | version | redir END
call append(line('$'), split(setoptions,"\n")
\ + ['--------------------'])
call add(result, '--------------------')
call add(result, '')
call add(result, '* Showcase:')
call add(result, '')
call setline(1, result)
call s:test_mappings(s:get('left_delims'), 1)
call s:test_mappings(s:get('quotes_list'), 0)
let result = []
redir => setoptions
echo " * Vim configuration:\<NL>"
filetype
echo ""
set
version
redir END
call extend(result, split(setoptions,"\n"))
call add(result, '--------------------')
setlocal nowrap
call append('$', result)
call feedkeys("\<Esc>\<Esc>", 'n')
endfunction "}}}
"}}}
function! s:test_mappings(list, is_matchpair) "{{{
let prefix = "normal Go0\<C-D>"
let last = "|"
let open = s:get('autoclose') ? 'Open: ' : 'Open & close: '
for s in a:list
if a:is_matchpair
let pair = s:get('right_delims')[index(s:get('left_delims'), s)]
else
let pair = s
endif
if !s:get('autoclose')
let s .= pair
endif
exec prefix . open . s . last
exec prefix . "Delete: " . s . "\<BS>" . last
exec prefix . "Exit: " . s . pair . last
if s:get('expand_space')
\ && (a:is_matchpair || s:get('expand_inside_quotes'))
exec prefix . "Space: " . s . " " . last
exec prefix . "Delete space: " . s . " \<BS>" . last
endif
if s:get('expand_cr')
\ && (a:is_matchpair || s:get('expand_inside_quotes'))
exec prefix . "Car return: " . s . "\<CR>" . last
exec prefix . "Delete car return: " . s . "\<CR>0\<C-D>\<BS>" . last
endif
call append('$', '')
endfor
endfunction "}}}
function! s:joinUndo() "{{{
if v:version < 704
\ || ( v:version == 704 && !has('patch849') )
return ''
endif
return "\<C-G>U"
endfunction "}}}
" vim:foldmethod=marker:foldcolumn=4:ts=2:sw=2

View File

@@ -34,10 +34,11 @@
4. Commands________________________________|delimitMateCommands|
5. Mappings________________________________|delimitMateMappings|
6. Functions_______________________________|delimitMateFunctions|
7. TODO list_______________________________|delimitMateTodo|
8. Maintainer______________________________|delimitMateMaintainer|
9. Credits_________________________________|delimitMateCredits|
10. History_________________________________|delimitMateHistory|
7. Autocommands____________________________|delimitMateAutocmds|
8. TODO list_______________________________|delimitMateTodo|
9. Maintainer______________________________|delimitMateMaintainer|
10. Credits_________________________________|delimitMateCredits|
11. History_________________________________|delimitMateHistory|
==============================================================================
1.- INTRODUCTION *delimitMateIntro*
@@ -60,7 +61,7 @@ the go.
2. CUSTOMIZATION *delimitMateOptions*
You can create your own mappings for some features using the global functions.
Read |DelimitMateFunctions| for more info.
Read |delimitMateFunctions| for more info.
------------------------------------------------------------------------------
2.1 OPTIONS SUMMARY *delimitMateOptionSummary*
@@ -190,6 +191,8 @@ e.g.: >
let delimitMate_nesting_quotes = ['"','`']
au FileType python let b:delimitMate_nesting_quotes = ['"']
<
For Python this is set by default by the plugin.
------------------------------------------------------------------------------
*'delimitMate_expand_cr'*
*'b:delimitMate_expand_cr'*
@@ -265,7 +268,7 @@ e.g.: >
*'delimitMate_smart_matchpairs'*
*'b:delimitMate_smart_matchpairs'*
Values: Regexp ~
Default: '^\%(\w\|\!\|£\|\$\|_\|["'']\s*\S\)' ~
Default: '^\%(\w\|\!\|[£$]\|[^[:space:][:punct:]]\)' ~
This regex is matched against the text to the right of cursor, if it's not
empty and there is a match delimitMate will not autoclose the pair. At the
@@ -308,6 +311,21 @@ only if you don't want any of the features it provides on those file types.
e.g.: >
let delimitMate_excluded_ft = "mail,txt"
<
------------------------------------------------------------------------------
*'delimitMate_insert_eol_marker'*
Values: Integer ~
Default: 1 ~
Whether to insert the eol marker (EM) or not. The EM is inserted following
rules:
0 -> never
1 -> when inserting any matchpair
2 -> when expanding car return in matchpair
e.g.: >
au FileType c,perl let b:delimitMate_insert_eol_marker = 2
<
------------------------------------------------------------------------------
*'delimitMate_eol_marker'*
Values: String. ~
@@ -368,11 +386,11 @@ With auto-close: >
Type | You get
=======================
( | (|)
|
-----------|-----------
() | ()|
|
-----------|-----------
(<S-Tab> | ()|
|
-----------|-----------
{("<C-G>g | {("")}|
<
Without auto-close: >
@@ -380,11 +398,11 @@ Without auto-close: >
Type | You get
=========================
() | (|)
-----|
--------------|----------
()) | ()|
-----|
--------------|----------
()<S-Tab> | ()|
|
--------------|----------
{}()""<C-G>g | {("")}|
<
NOTE: Abbreviations will not be expanded by delimiters used on delimitMate,
@@ -547,6 +565,16 @@ know about it.
Re-sets all the mappings used for this script, use it if any option has been
changed or if the filetype option hasn't been set yet.
------------------------------------------------------------------------------
:DelimitMateOn *:DelimitMateOn*
Enable delimitMate mappings.
------------------------------------------------------------------------------
:DelimitMateOff *:DelimitMateOff*
Disable delimitMate mappings.
------------------------------------------------------------------------------
:DelimitMateSwitch *:DelimitMateSwitch*
@@ -669,7 +697,7 @@ Returns 1 if the cursor is inside an empty pair, 0 otherwise.
e.g.: >
inoremap <expr> <CR> delimitMate#WithinEmptyPair() ?
\ "\<C-R>=delimitMate#ExpandReturn()\<CR>" :
\ "<Plug>delimitMateCR" :
\ "external_mapping"
<
@@ -686,17 +714,50 @@ This function returns a mapping that will make the cursor jump to the right
when delimitMate#ShouldJump() returns 1, returns the argument "key" otherwise.
e.g.: You can use this to create your own mapping to jump over any delimiter.
>
inoremap <C-Tab> <C-R>=delimitMate#JumpAny()<CR>
inoremap <expr> <C-Tab> delimitMate#JumpAny()
<
==============================================================================
7. AUTOCOMMANDS *delimitMateAutocmds*
delimitMate emits 2 |User| autocommands to make it easier for users to
leverage delimitMate's support for per-filetype customization.
------------------------------------------------------------------------------
delimitMate_map *delimitMate_map*
This |User| event is emittted just prior to delimitMate defining its
buffer-local key mappings. You can use this command to define your own
mappings that are disabled when delimitMate is turned off or excludes the
current filetype.
>
au User delimitMate_map call s:delimitMate_map()
function s:delimitMate_map()
imap <buffer><expr> <C-Tab> delimitMate#JumpAny()
endfunction
<
------------------------------------------------------------------------------
delimitMate_unmap *delimitMate_unmap*
This |User| event is emitted just after delimitMate clears its buffer-local
key mappings. You can use this command to clear your own mappings that you set
in response to |delimitMate_map|.
>
au User delimitMate_unmap call s:delimitMate_unmap()
function s:delimitMate_unmap()
silent! iunmap <buffer> <C-Tab>
endfunction
<
Note: This event may be emitted before |delimitMate_map|, and may be emitted
multiple times in a row without any intervening |delimitMate_map| events.
==============================================================================
7. TODO LIST *delimitMateTodo*
8. TODO LIST *delimitMateTodo*
- Automatic set-up by file type.
- Make block-wise visual wrapping work on un-even regions.
==============================================================================
8. MAINTAINER *delimitMateMaintainer*
9. MAINTAINER *delimitMateMaintainer*
Hi there! My name is Israel Chauca F. and I can be reached at:
mailto:israelchauca@gmail.com
@@ -705,7 +766,7 @@ Feel free to send me any suggestions and/or comments about this plugin, I'll
be very pleased to read them.
==============================================================================
9. CREDITS *delimitMateCredits*
10. CREDITS *delimitMateCredits*
Contributors: ~
@@ -741,12 +802,14 @@ copied from the following sources:
This script was inspired by the auto-completion of delimiters on TextMate.
==============================================================================
10. HISTORY *delimitMateHistory*
11. HISTORY *delimitMateHistory*
Version Date Release notes ~
|---------|------------|-----------------------------------------------------|
2.7 2013-07-15 * Current release:
- Lots of bug fixes.
2.8 2013-07-15 * Current release:
- Add :DelimitMateOn & :DelimitMateOff.
|---------|------------|-----------------------------------------------------|
2.7 2013-07-15 * - Lots of bug fixes.
- Add delimitMate_offByDefault.
- Add delimitMate_eol_marker.
- Reduce the number of mappings.

View File

@@ -22,20 +22,23 @@ if v:version < 700
endif
let s:loaded_delimitMate = 1
let delimitMate_version = "2.7"
let delimitMate_version = "2.8"
"}}}
" Functions: {{{
function! s:option_init(name, default) "{{{
let b = exists("b:delimitMate_" . a:name)
let g = exists("g:delimitMate_" . a:name)
let opt_name = "delimitMate_" . a:name
" Find value to use.
if !b && !g
if !has_key(b:, opt_name) && !has_key(g:, opt_name)
let value = a:default
elseif b
exec "let value = b:delimitMate_" . a:name
elseif has_key(b:, opt_name)
let value = b:[opt_name]
else
exec "let value = g:delimitMate_" . a:name
let value = g:[opt_name]
endif
call s:s(a:name, value)
call s:set(a:name, value)
endfunction "}}}
function! s:init() "{{{
@@ -44,8 +47,8 @@ function! s:init() "{{{
call s:option_init("autoclose", 1)
" matchpairs
call s:option_init("matchpairs", string(&matchpairs)[1:-2])
call s:option_init("matchpairs_list", map(split(s:g('matchpairs'), ','), 'split(v:val, '':'')'))
let pairs = s:g('matchpairs_list')
call s:option_init("matchpairs_list", map(split(s:get('matchpairs', ''), '.:.\zs,\ze.:.'), 'split(v:val, ''^.\zs:\ze.$'')'))
let pairs = s:get('matchpairs_list', [])
if len(filter(pairs, 'v:val[0] ==# v:val[1]'))
echohl ErrorMsg
echom 'delimitMate: each member of a pair in delimitMate_matchpairs must be different from each other.'
@@ -53,20 +56,18 @@ function! s:init() "{{{
echohl Normal
return 0
endif
call s:option_init("left_delims", map(copy(s:g('matchpairs_list')), 'v:val[0]'))
call s:option_init("right_delims", map(copy(s:g('matchpairs_list')), 'v:val[1]'))
call s:option_init("left_delims", map(copy(s:get('matchpairs_list', [])), 'v:val[0]'))
call s:option_init("right_delims", map(copy(s:get('matchpairs_list', [])), 'v:val[1]'))
" quotes
call s:option_init("quotes", "\" ' `")
call s:option_init("quotes_list",split(s:g('quotes'), '\s\+'))
call s:option_init("quotes_list",split(s:get('quotes', ''), '\s\+'))
" nesting_quotes
call s:option_init("nesting_quotes", [])
" excluded_regions
call s:option_init("excluded_regions", "Comment")
call s:option_init("excluded_regions_list", split(s:g('excluded_regions'), ',\s*'))
let enabled = len(s:g('excluded_regions_list')) > 0
call s:option_init("excluded_regions_list", split(s:get('excluded_regions', ''), ',\s*'))
let enabled = len(s:get('excluded_regions_list', [])) > 0
call s:option_init("excluded_regions_enabled", enabled)
" excluded filetypes
call s:option_init("excluded_ft", "")
" expand_space
if exists("b:delimitMate_expand_space") && type(b:delimitMate_expand_space) == type("")
echom "b:delimitMate_expand_space is '".b:delimitMate_expand_space."' but it must be either 1 or 0!"
@@ -105,10 +106,10 @@ function! s:init() "{{{
" jump_expansion
call s:option_init("jump_expansion", 0)
" smart_matchpairs
call s:option_init("smart_matchpairs", '^\%(\w\|\!\|£\|\$\|_\|["'']\s*\S\)')
call s:option_init("smart_matchpairs", '^\%(\w\|\!\|[£$]\|[^[:punct:][:space:]]\)')
" smart_quotes
" XXX: backward compatibility. Ugly, should go the way of the dodo soon.
let quotes = escape(join(s:g('quotes_list'), ''), '\-^[]')
let quotes = escape(join(s:get('quotes_list', []), ''), '\-^[]')
let default_smart_quotes = '\%(\w\|[^[:punct:][:space:]' . quotes . ']\|\%(\\\\\)*\\\)\%#\|\%#\%(\w\|[^[:space:][:punct:]' . quotes . ']\)'
if exists('g:delimitMate_smart_quotes') && type(g:delimitMate_smart_quotes) == type(0)
if g:delimitMate_smart_quotes
@@ -132,26 +133,24 @@ function! s:init() "{{{
call s:option_init("smart_quotes", default_smart_quotes)
" apostrophes
call s:option_init("apostrophes", "")
call s:option_init("apostrophes_list", split(s:g('apostrophes'), ":\s*"))
call s:option_init("apostrophes_list", split(s:get('apostrophes', ''), ":\s*"))
" tab2exit
call s:option_init("tab2exit", 1)
" balance_matchpairs
call s:option_init("balance_matchpairs", 0)
" eol marker
call s:option_init("insert_eol_marker", 1)
call s:option_init("eol_marker", "")
" Everything is fine.
return 1
endfunction "}}} Init()
"}}}
" Functions: {{{
function! s:g(...) " {{{
return call('delimitMate#Get', a:000)
function! s:get(name, default) "{{{
let bufoptions = delimitMate#Get()
return get(bufoptions, a:name, a:default)
endfunction "}}}
function! s:s(...) " {{{
function! s:set(...) " {{{
return call('delimitMate#Set', a:000)
endfunction " }}}
@@ -164,7 +163,8 @@ function! s:Map() "{{{
let save_cpo = &cpo
set keymap=
set cpo&vim
if s:g('autoclose')
silent! doautocmd <nomodeline> User delimitMate_map
if s:get('autoclose', 1)
call s:AutoClose()
else
call s:NoAutoClose()
@@ -178,32 +178,32 @@ function! s:Map() "{{{
endtry
let b:delimitMate_enabled = 1
endfunction "}}} Map()
function! s:Unmap() " {{{
let imaps =
\ s:g('right_delims', []) +
\ s:g('left_delims', []) +
\ s:g('quotes_list', []) +
\ s:g('apostrophes_list', []) +
\ s:get('right_delims', []) +
\ s:get('left_delims', []) +
\ s:get('quotes_list', []) +
\ s:get('apostrophes_list', []) +
\ ['<BS>', '<C-h>', '<S-BS>', '<Del>', '<CR>', '<Space>', '<S-Tab>', '<Esc>'] +
\ ['<Up>', '<Down>', '<Left>', '<Right>', '<LeftMouse>', '<RightMouse>'] +
\ ['<C-Left>', '<C-Right>'] +
\ ['<Home>', '<End>', '<PageUp>', '<PageDown>', '<S-Down>', '<S-Up>', '<C-G>g']
for map in imaps
if maparg(map, "i") =~? 'delimitMate'
if maparg(map, "i") =~# '^<Plug>delimitMate'
if map == '|'
let map = '<Bar>'
endif
exec 'silent! iunmap <buffer> ' . map
endif
endfor
silent! doautocmd <nomodeline> User delimitMate_unmap
let b:delimitMate_enabled = 0
endfunction " }}} s:Unmap()
function! s:TestMappingsDo() "{{{
function! s:test() "{{{
if &modified
let confirm = input("Modified buffer, type \"yes\" to write and proceed "
\ . "with test: ") ==? 'yes'
@@ -211,16 +211,29 @@ function! s:TestMappingsDo() "{{{
return
endif
endif
call delimitMate#TestMappings()
call delimitMate#Test()
g/\%^$/d
0
endfunction "}}}
function! s:DelimitMateDo(...) "{{{
function! s:setup(...) "{{{
let swap = a:0 && a:1 == 2
let enable = a:0 && a:1
let disable = a:0 && !a:1
" First, remove all magic, if needed:
if exists("b:delimitMate_enabled") && b:delimitMate_enabled == 1
if get(b:, 'delimitMate_enabled', 0)
call s:Unmap()
" Switch
if swap
echo "delimitMate is disabled."
return
endif
endif
if disable
" Just disable the mappings.
return
endif
if !a:0
" Check if this file type is excluded:
if exists("g:delimitMate_excluded_ft") &&
\ index(split(g:delimitMate_excluded_ft, ','), &filetype, 0, 1) >= 0
@@ -231,34 +244,21 @@ function! s:DelimitMateDo(...) "{{{
if exists("b:loaded_delimitMate")
return 1
endif
endif
" Initialize settings:
if ! s:init()
" Something went wrong.
return
endif
if enable || swap || !get(g:, 'delimitMate_offByDefault', 0)
" Now, add magic:
if !exists("g:delimitMate_offByDefault") || !g:delimitMate_offByDefault
call s:Map()
if a:0
echo "delimitMate is enabled."
endif
if a:0 > 0
echo "delimitMate has been reset."
endif
endfunction "}}}
function! s:DelimitMateSwitch() "{{{
if exists("b:delimitMate_enabled") && b:delimitMate_enabled
call s:Unmap()
echo "delimitMate has been disabled."
else
call s:Unmap()
call s:init()
call s:Map()
echo "delimitMate has been enabled."
endif
endfunction "}}}
"}}}
" Mappers: {{{
function! s:TriggerAbb() "{{{
if v:version < 703
\ || ( v:version == 703 && !has('patch489') )
@@ -270,7 +270,7 @@ endfunction "}}}
function! s:NoAutoClose() "{{{
" inoremap <buffer> ) <C-R>=delimitMate#SkipDelim('\)')<CR>
for delim in s:g('right_delims') + s:g('quotes_list')
for delim in s:get('right_delims', []) + s:get('quotes_list', [])
if delim == '|'
let delim = '<Bar>'
endif
@@ -283,9 +283,9 @@ function! s:AutoClose() "{{{
" Add matching pair and jump to the midle:
" inoremap <silent> <buffer> ( ()<Left>
let i = 0
while i < len(s:g('matchpairs_list'))
let ld = s:g('left_delims')[i] == '|' ? '<bar>' : s:g('left_delims')[i]
let rd = s:g('right_delims')[i] == '|' ? '<bar>' : s:g('right_delims')[i]
while i < len(s:get('matchpairs_list', []))
let ld = s:get('left_delims', [])[i] == '|' ? '<bar>' : s:get('left_delims', [])[i]
let rd = s:get('right_delims', [])[i] == '|' ? '<bar>' : s:get('right_delims', [])[i]
exec 'inoremap <expr><silent> <Plug>delimitMate' . ld
\. ' <SID>TriggerAbb().delimitMate#ParenDelim("' . escape(rd, '|') . '")'
exec 'silent! imap <unique> <buffer> '.ld
@@ -294,7 +294,7 @@ function! s:AutoClose() "{{{
endwhile
" Exit from inside the matching pair:
for delim in s:g('right_delims')
for delim in s:get('right_delims', [])
let delim = delim == '|' ? '<bar>' : delim
exec 'inoremap <expr><silent> <Plug>delimitMate' . delim
\. ' <SID>TriggerAbb().delimitMate#JumpOut("\' . delim . '")'
@@ -304,7 +304,7 @@ function! s:AutoClose() "{{{
" Add matching quote and jump to the midle, or exit if inside a pair of matching quotes:
" inoremap <silent> <buffer> " <C-R>=delimitMate#QuoteDelim("\"")<CR>
for delim in s:g('quotes_list')
for delim in s:get('quotes_list', [])
if delim == '|'
let delim = '<Bar>'
endif
@@ -316,7 +316,7 @@ function! s:AutoClose() "{{{
" Try to fix the use of apostrophes (kept for backward compatibility):
" inoremap <silent> <buffer> n't n't
for map in s:g('apostrophes_list')
for map in s:get('apostrophes_list', [])
exec "inoremap <silent> " . map . " " . map
exec 'silent! imap <unique> <buffer> ' . map . ' <Plug>delimitMate' . map
endfor
@@ -326,10 +326,10 @@ function! s:ExtraMappings() "{{{
" If pair is empty, delete both delimiters:
inoremap <silent> <Plug>delimitMateBS <C-R>=delimitMate#BS()<CR>
if !hasmapto('<Plug>delimitMateBS','i')
if maparg('<BS>'. 'i') == ''
if empty(maparg('<BS>', 'i'))
silent! imap <unique> <buffer> <BS> <Plug>delimitMateBS
endif
if maparg('<C-h>'. 'i') == ''
if empty(maparg('<C-H>', 'i'))
silent! imap <unique> <buffer> <C-h> <Plug>delimitMateBS
endif
endif
@@ -340,17 +340,17 @@ function! s:ExtraMappings() "{{{
endif
" Expand return if inside an empty pair:
inoremap <expr><silent> <Plug>delimitMateCR <SID>TriggerAbb()."\<C-R>=delimitMate#ExpandReturn()\<CR>"
if s:g('expand_cr') && !hasmapto('<Plug>delimitMateCR', 'i') && maparg('<CR>', 'i') == ''
if s:get('expand_cr', 0) && !hasmapto('<Plug>delimitMateCR', 'i') && maparg('<CR>', 'i') == ''
silent! imap <unique> <buffer> <CR> <Plug>delimitMateCR
endif
" Expand space if inside an empty pair:
inoremap <expr><silent> <Plug>delimitMateSpace <SID>TriggerAbb()."\<C-R>=delimitMate#ExpandSpace()\<CR>"
if s:g('expand_space') && !hasmapto('<Plug>delimitMateSpace', 'i') && maparg('<Space>', 'i') == ''
if s:get('expand_space', 0) && !hasmapto('<Plug>delimitMateSpace', 'i') && maparg('<Space>', 'i') == ''
silent! imap <unique> <buffer> <Space> <Plug>delimitMateSpace
endif
" Jump over any delimiter:
inoremap <expr><silent> <Plug>delimitMateS-Tab <SID>TriggerAbb()."\<C-R>=delimitMate#JumpAny()\<CR>"
if s:g('tab2exit') && !hasmapto('<Plug>delimitMateS-Tab', 'i') && maparg('<S-Tab>', 'i') == ''
if s:get('tab2exit', 0) && !hasmapto('<Plug>delimitMateS-Tab', 'i') && maparg('<S-Tab>', 'i') == ''
silent! imap <unique> <buffer> <S-Tab> <Plug>delimitMateS-Tab
endif
" Jump over next delimiters
@@ -364,16 +364,17 @@ endfunction "}}}
" Commands: {{{
call s:DelimitMateDo()
" Let me refresh without re-loading the buffer:
command! -bar DelimitMateReload call s:DelimitMateDo(1)
command! -bar DelimitMateReload call s:setup(1)
" Quick test:
command! -bar DelimitMateTest call s:TestMappingsDo()
command! -bar DelimitMateTest call s:test()
" Switch On/Off:
command! -bar DelimitMateSwitch call s:DelimitMateSwitch()
command! -bar DelimitMateSwitch call s:setup(2)
" Enable mappings:
command! -bar DelimitMateOn call s:setup(1)
" Disable mappings:
command! -bar DelimitMateOff call s:setup(0)
"}}}
" Autocommands: {{{
@@ -381,19 +382,22 @@ command! -bar DelimitMateSwitch call s:DelimitMateSwitch()
augroup delimitMate
au!
" Run on file type change.
"autocmd VimEnter * autocmd FileType * call <SID>DelimitMateDo()
autocmd FileType * call <SID>DelimitMateDo()
au FileType * call <SID>setup()
au FileType python let b:delimitMate_nesting_quotes = ['"', "'"]
" Run on new buffers.
autocmd BufNewFile,BufRead,BufEnter *
au BufNewFile,BufRead,BufEnter,CmdwinEnter *
\ if !exists('b:delimitMate_was_here') |
\ call <SID>DelimitMateDo() |
\ call <SID>setup() |
\ let b:delimitMate_was_here = 1 |
\ endif
augroup END
"}}}
" This is for the default buffer when it does not have a filetype.
call s:setup()
let &cpo = save_cpo
" GetLatestVimScripts: 2754 1 :AutoInstall: delimitMate.vim
" vim:foldmethod=marker:foldcolumn=4:ts=2:sw=2

View File

@@ -39,3 +39,13 @@ let b:delimitMate_eol_marker = ';'
unlet b:delimitMate_eol_marker
iabb def ghi
"def(" "ghi()"
iunabb def
"abc а\<Left>(" "abc (а"
"abc ñ\<Left>(" "abc (ñ"
"abc $\<Left>(" "abc ($"
"abc £\<Left>(" "abc (£"
"abc d\<Left>(" "abc (d"
"abc \<C-V>(\<Left>(" "abc (("
"abc .\<Left>(" "abc ()."
"abc \<Left>(" "abc () "

View File

@@ -1,8 +1,8 @@
let g:delimitMate_matchpairs = '(:),{:},[:],<:>,¿:?,¡:!'
let g:delimitMate_matchpairs = '(:),{:},[:],<:>,¿:?,¡:!,,::'
let lines = readfile(expand('<sfile>:t:r').'.txt')
call vimtest#StartTap()
let testsnumber = len(filter(copy(lines), 'v:val =~ ''^"'''))
let itemsnumber = len(split(g:delimitMate_matchpairs, ','))
let itemsnumber = len(split(g:delimitMate_matchpairs, '.:.\zs,\ze.:.'))
call vimtap#Plan(testsnumber * itemsnumber)
let tcount = 1
let reload = 1
@@ -24,7 +24,7 @@ for item in lines
let reload = 0
endif
let [input, output] = split(item, '"\%(\\.\|[^\\"]\)*"\zs\s*\ze"\%(\\.\|[^\\"]\)*"')
for [s:l,s:r] in map(split(g:delimitMate_matchpairs, ','), 'split(v:val, ":")')
for [s:l,s:r] in map(split(g:delimitMate_matchpairs, '.:.\zs,\ze.:.'), 'split(v:val, ''.\zs:\ze.'')')
let input2 = substitute(input, '(', s:l, 'g')
let input2 = substitute(input2, ')', s:r, 'g')
let output2 = substitute(output, '(', s:l, 'g')

44
test/eol_marker.vim Normal file
View File

@@ -0,0 +1,44 @@
let g:delimitMate_expand_cr = 1
let g:delimitMate_eol_marker = ';'
call vimtest#StartTap()
call vimtap#Plan(8)
" NOTE: Do not forget to update the plan ^
let g:delimitMate_insert_eol_marker = 0
DelimitMateReload
normal i(
call vimtap#Is(getline(1), '()', 'value = 1, case 1')
%d _
exec "normal i(\<CR>x"
call vimtap#Like(join(getline(1,line('$')), "\<NL>"),
\ '^(\n\s*x\n)$', ' "normal i(\<CR>x", Value = 2, case 2')
let g:delimitMate_insert_eol_marker = 1
DelimitMateReload
%d _
normal i(
call vimtap#Is(getline(1), '();', '"normal i(", value = 1, case 1')
%d _
exec "normal i(\<CR>x"
call vimtap#Like(join(getline(1,line('$')), "\<NL>"),
\ '^(\n\s*x\n);$', '"normal i(\<CR>x", Value = 2, case 2')
%d _
let g:delimitMate_insert_eol_marker = 2
DelimitMateReload
normal i(
call vimtap#Is(getline(1), '()', '"normal i(", Value = 2, case 1')
%d _
exec "normal i(\<CR>x"
call vimtap#Like(join(getline(1,line('$')), "\<NL>"),
\ '^(\n\s*x\n);$', '"normal i(\<CR>x", Value = 2, case 2')
%d _
exec "normal i{(\<CR>x"
call vimtap#Like(join(getline(1,line('$')), "\<NL>"),
\ '^{(\n\s*x\n)};$', ' "normal i{(\<CR>x", Value = 2, case 3')
%d _
exec "normal i;\<Esc>I{(\<CR>x"
call vimtap#Like(join(getline(1,line('$')), "\<NL>"),
\ '^{(\n\s*x\n)};$', ' "normal i{(\<CR>x", Value = 2, case 4')
" End: quit vim.
call vimtest#Quit()

View File

@@ -0,0 +1,8 @@
let g:delimitMate_expand_cr = 1
let g:delimitMate_eol_marker = ';'
call vimtest#StartTap()
call vimtap#Plan(1)
call vimtap#Like(maparg('(', 'i'), '<Plug>delimitMate(', 'Mappings defined for the first buffer without filetype set.')
call vimtest#Quit()