utils 0.0.0
Sign up to get free protection for your applications and to get access to all the features.
- data/Rakefile +68 -0
- data/VERSION +1 -0
- data/bin/chroot-exec +12 -0
- data/bin/chroot-libs +18 -0
- data/bin/classify +37 -0
- data/bin/discover +137 -0
- data/bin/edit +74 -0
- data/bin/errf +32 -0
- data/bin/git-empty +8 -0
- data/bin/myex +90 -0
- data/bin/number_files +26 -0
- data/bin/same_files +37 -0
- data/bin/search +205 -0
- data/bin/sedit +3 -0
- data/bin/sshscreen +68 -0
- data/bin/term +21 -0
- data/bin/unquarantine_apps +8 -0
- data/bin/untest +17 -0
- data/bin/utils-install-config +10 -0
- data/bin/vacuum_firefox_sqlite +22 -0
- data/bin/xmp +74 -0
- data/lib/utils.rb +8 -0
- data/lib/utils/config.rb +23 -0
- data/lib/utils/config/gdb/asm +179 -0
- data/lib/utils/config/gdb/ruby +528 -0
- data/lib/utils/config/gdbinit +8 -0
- data/lib/utils/config/irbrc +455 -0
- data/lib/utils/config/rdebugrc +2 -0
- data/lib/utils/config/screenrc +143 -0
- data/lib/utils/config/vim/autoload/Align.vim +1029 -0
- data/lib/utils/config/vim/autoload/AlignMaps.vim +330 -0
- data/lib/utils/config/vim/autoload/rails.vim +4744 -0
- data/lib/utils/config/vim/autoload/rubycomplete.vim +801 -0
- data/lib/utils/config/vim/autoload/sqlcomplete.vim +741 -0
- data/lib/utils/config/vim/autoload/vimball.vim +750 -0
- data/lib/utils/config/vim/colors/flori.vim +113 -0
- data/lib/utils/config/vim/compiler/eruby.vim +40 -0
- data/lib/utils/config/vim/compiler/ruby.vim +67 -0
- data/lib/utils/config/vim/compiler/rubyunit.vim +34 -0
- data/lib/utils/config/vim/ftdetect/ragel.vim +2 -0
- data/lib/utils/config/vim/ftdetect/ruby.vim +17 -0
- data/lib/utils/config/vim/ftplugin/eruby.vim +100 -0
- data/lib/utils/config/vim/ftplugin/ruby.vim +260 -0
- data/lib/utils/config/vim/ftplugin/xml.vim +941 -0
- data/lib/utils/config/vim/indent/IndentAnything_html.vim +35 -0
- data/lib/utils/config/vim/indent/eruby.vim +77 -0
- data/lib/utils/config/vim/indent/javascript.vim +116 -0
- data/lib/utils/config/vim/indent/ruby.vim +377 -0
- data/lib/utils/config/vim/plugin/AlignMapsPlugin.vim +242 -0
- data/lib/utils/config/vim/plugin/AlignPlugin.vim +41 -0
- data/lib/utils/config/vim/plugin/Decho.vim +592 -0
- data/lib/utils/config/vim/plugin/IndentAnything.vim +675 -0
- data/lib/utils/config/vim/plugin/bufexplorer.vim +1144 -0
- data/lib/utils/config/vim/plugin/cecutil.vim +482 -0
- data/lib/utils/config/vim/plugin/fugitive.vim +1703 -0
- data/lib/utils/config/vim/plugin/lusty-explorer.vim +1509 -0
- data/lib/utils/config/vim/plugin/rails.vim +340 -0
- data/lib/utils/config/vim/plugin/rubyextra.vim +193 -0
- data/lib/utils/config/vim/plugin/surround.vim +628 -0
- data/lib/utils/config/vim/plugin/taglist.vim +4546 -0
- data/lib/utils/config/vim/plugin/test/IndentAnything/test.js +131 -0
- data/lib/utils/config/vim/plugin/vimballPlugin.vim +40 -0
- data/lib/utils/config/vim/syntax/Decho.vim +101 -0
- data/lib/utils/config/vim/syntax/eruby.vim +73 -0
- data/lib/utils/config/vim/syntax/javascript.vim +246 -0
- data/lib/utils/config/vim/syntax/ragel.vim +165 -0
- data/lib/utils/config/vim/syntax/ruby.vim +367 -0
- data/lib/utils/config/vimrc +461 -0
- data/lib/utils/file.rb +49 -0
- data/lib/utils/find.rb +54 -0
- data/lib/utils/md5.rb +23 -0
- data/lib/utils/patterns.rb +34 -0
- data/lib/utils/version.rb +8 -0
- data/utils.gemspec +33 -0
- metadata +183 -0
@@ -0,0 +1,143 @@
|
|
1
|
+
#
|
2
|
+
# Example of a user's .screenrc file
|
3
|
+
#
|
4
|
+
|
5
|
+
# This is how one can set a reattach password:
|
6
|
+
# password ODSJQf.4IJN7E # "1234"
|
7
|
+
|
8
|
+
# no annoying audible bell, please
|
9
|
+
vbell on
|
10
|
+
|
11
|
+
# detach on hangup
|
12
|
+
autodetach on
|
13
|
+
|
14
|
+
# don't display the copyright page
|
15
|
+
startup_message off
|
16
|
+
|
17
|
+
# emulate .logout message
|
18
|
+
pow_detach_msg "Screen session of \$LOGNAME \$:cr:\$:nl:ended."
|
19
|
+
|
20
|
+
# advertise hardstatus support to $TERMCAP
|
21
|
+
# termcapinfo * '' 'hs:ts=\E_:fs=\E\\:ds=\E_\E\\'
|
22
|
+
|
23
|
+
# make the shell in every window a login shell
|
24
|
+
#shell -$SHELL
|
25
|
+
shell -$SHELL
|
26
|
+
|
27
|
+
# autoaka testing
|
28
|
+
# shellaka '> |tcsh'
|
29
|
+
# shellaka '$ |sh'
|
30
|
+
|
31
|
+
# set every new windows hardstatus line to somenthing descriptive
|
32
|
+
# defhstatus "screen: ^En (^Et)"
|
33
|
+
|
34
|
+
defscrollback 1000
|
35
|
+
|
36
|
+
# don't kill window after the process died
|
37
|
+
# zombie "^["
|
38
|
+
|
39
|
+
################
|
40
|
+
#
|
41
|
+
# xterm tweaks
|
42
|
+
#
|
43
|
+
|
44
|
+
#xterm understands both im/ic and doesn't have a status line.
|
45
|
+
#Note: Do not specify im and ic in the real termcap/info file as
|
46
|
+
#some programs (e.g. vi) will not work anymore.
|
47
|
+
termcap xterm hs@:cs=\E[%i%d;%dr:im=\E[4h:ei=\E[4l
|
48
|
+
terminfo xterm hs@:cs=\E[%i%p1%d;%p2%dr:im=\E[4h:ei=\E[4l
|
49
|
+
|
50
|
+
#80/132 column switching must be enabled for ^AW to work
|
51
|
+
#change init sequence to not switch width
|
52
|
+
termcapinfo xterm Z0=\E[?3h:Z1=\E[?3l:is=\E[r\E[m\E[2J\E[H\E[?7h\E[?1;4;6l
|
53
|
+
|
54
|
+
# Make the output buffer large for (fast) xterms.
|
55
|
+
termcapinfo xterm* OL=10000
|
56
|
+
|
57
|
+
# tell screen that xterm can switch to dark background and has function
|
58
|
+
# keys.
|
59
|
+
termcapinfo xterm 'VR=\E[?5h:VN=\E[?5l'
|
60
|
+
termcapinfo xterm 'k1=\E[11~:k2=\E[12~:k3=\E[13~:k4=\E[14~'
|
61
|
+
termcapinfo xterm 'kh=\E[1~:kI=\E[2~:kD=\E[3~:kH=\E[4~:kP=\E[H:kN=\E[6~'
|
62
|
+
|
63
|
+
# special xterm hardstatus: use the window title.
|
64
|
+
termcapinfo xterm 'hs:ts=\E]2;:fs=\007:ds=\E]2;screen\007'
|
65
|
+
|
66
|
+
#terminfo xterm 'vb=\E[?5h$<200/>\E[?5l'
|
67
|
+
termcapinfo xterm 'vi=\E[?25l:ve=\E[34h\E[?25h:vs=\E[34l'
|
68
|
+
|
69
|
+
# emulate part of the 'K' charset
|
70
|
+
termcapinfo xterm 'XC=K%,%\E(B,[\304,\\\\\326,]\334,{\344,|\366,}\374,~\337'
|
71
|
+
|
72
|
+
# xterm-52 tweaks:
|
73
|
+
# - uses background color for delete operations
|
74
|
+
termcapinfo xterm ut
|
75
|
+
|
76
|
+
################
|
77
|
+
#
|
78
|
+
# wyse terminals
|
79
|
+
#
|
80
|
+
|
81
|
+
#wyse-75-42 must have flow control (xo = "terminal uses xon/xoff")
|
82
|
+
#essential to have it here, as this is a slow terminal.
|
83
|
+
termcapinfo wy75-42 xo:hs@
|
84
|
+
|
85
|
+
# New termcap sequences for cursor application mode.
|
86
|
+
termcapinfo wy* CS=\E[?1h:CE=\E[?1l:vi=\E[?25l:ve=\E[?25h:VR=\E[?5h:VN=\E[?5l:cb=\E[1K:CD=\E[1J
|
87
|
+
|
88
|
+
################
|
89
|
+
#
|
90
|
+
# other terminals
|
91
|
+
#
|
92
|
+
|
93
|
+
#make hp700 termcap/info better
|
94
|
+
termcapinfo hp700 'Z0=\E[?3h:Z1=\E[?3l:hs:ts=\E[62"p\E[0$~\E[2$~\E[1$}:fs=\E[0}\E[61"p:ds=\E[62"p\E[1$~\E[61"p:ic@'
|
95
|
+
|
96
|
+
# Extend the vt100 desciption by some sequences.
|
97
|
+
termcap vt100* ms:AL=\E[%dL:DL=\E[%dM:UP=\E[%dA:DO=\E[%dB:LE=\E[%dD:RI=\E[%dC
|
98
|
+
terminfo vt100* ms:AL=\E[%p1%dL:DL=\E[%p1%dM:UP=\E[%p1%dA:DO=\E[%p1%dB:LE=\E[%p1%dD:RI=\E[%p1%dC
|
99
|
+
|
100
|
+
|
101
|
+
################
|
102
|
+
#
|
103
|
+
# keybindings
|
104
|
+
#
|
105
|
+
|
106
|
+
#remove some stupid / dangerous key bindings
|
107
|
+
bind k
|
108
|
+
bind ^k
|
109
|
+
bind .
|
110
|
+
bind ^\
|
111
|
+
bind \\
|
112
|
+
bind ^h
|
113
|
+
bind h
|
114
|
+
#make them better
|
115
|
+
bind 'K' kill
|
116
|
+
bind 'I' login on
|
117
|
+
bind 'O' login off
|
118
|
+
bind '}' history
|
119
|
+
|
120
|
+
# Yet another hack:
|
121
|
+
# Prepend/append register [/] to the paste if ^a^] is pressed.
|
122
|
+
# This lets me have autoindent mode in vi.
|
123
|
+
register [ "\033:se noai\015a"
|
124
|
+
register ] "\033:se ai\015a"
|
125
|
+
bind ^] paste [.]
|
126
|
+
|
127
|
+
################
|
128
|
+
#
|
129
|
+
# default windows
|
130
|
+
#
|
131
|
+
|
132
|
+
# screen -t local 0
|
133
|
+
# screen -t mail 1 elm
|
134
|
+
# screen -t 40 2 rlogin faui40
|
135
|
+
|
136
|
+
# caption always "%3n %t%? @%u%?%? [%h]%?"
|
137
|
+
# hardstatus alwaysignore
|
138
|
+
# hardstatus alwayslastline "%w"
|
139
|
+
|
140
|
+
hardstatus on
|
141
|
+
hardstatus alwayslastline
|
142
|
+
hardstatus string "%{.bw}%-w%{.wr}%n %t%{-}%+w %=%{..g} %H %{..y}%l"
|
143
|
+
|
@@ -0,0 +1,1029 @@
|
|
1
|
+
" Align: tool to align multiple fields based on one or more separators
|
2
|
+
" Author: Charles E. Campbell, Jr.
|
3
|
+
" Date: Mar 03, 2009
|
4
|
+
" Version: 35
|
5
|
+
" GetLatestVimScripts: 294 1 :AutoInstall: Align.vim
|
6
|
+
" GetLatestVimScripts: 1066 1 :AutoInstall: cecutil.vim
|
7
|
+
" Copyright: Copyright (C) 1999-2007 Charles E. Campbell, Jr. {{{1
|
8
|
+
" Permission is hereby granted to use and distribute this code,
|
9
|
+
" with or without modifications, provided that this copyright
|
10
|
+
" notice is copied with it. Like anything else that's free,
|
11
|
+
" Align.vim is provided *as is* and comes with no warranty
|
12
|
+
" of any kind, either expressed or implied. By using this
|
13
|
+
" plugin, you agree that in no event will the copyright
|
14
|
+
" holder be liable for any damages resulting from the use
|
15
|
+
" of this software.
|
16
|
+
"
|
17
|
+
" Romans 1:16,17a : For I am not ashamed of the gospel of Christ, for it is {{{1
|
18
|
+
" the power of God for salvation for everyone who believes; for the Jew first,
|
19
|
+
" and also for the Greek. For in it is revealed God's righteousness from
|
20
|
+
" faith to faith.
|
21
|
+
|
22
|
+
" ---------------------------------------------------------------------
|
23
|
+
" Load Once: {{{1
|
24
|
+
if exists("g:loaded_Align") || &cp
|
25
|
+
finish
|
26
|
+
endif
|
27
|
+
let g:loaded_Align = "v35"
|
28
|
+
if v:version < 700
|
29
|
+
echohl WarningMsg
|
30
|
+
echo "***warning*** this version of Align needs vim 7.0"
|
31
|
+
echohl Normal
|
32
|
+
finish
|
33
|
+
endif
|
34
|
+
let s:keepcpo= &cpo
|
35
|
+
set cpo&vim
|
36
|
+
"DechoTabOn
|
37
|
+
|
38
|
+
" ---------------------------------------------------------------------
|
39
|
+
" Debugging Support: {{{1
|
40
|
+
"if !exists("g:loaded_Decho") | runtime plugin/Decho.vim | endif
|
41
|
+
|
42
|
+
" ---------------------------------------------------------------------
|
43
|
+
" Options: {{{1
|
44
|
+
if !exists("g:Align_xstrlen")
|
45
|
+
if &enc == "latin1" || $LANG == "en_US.UTF-8" || !has("multi_byte")
|
46
|
+
let g:Align_xstrlen= 0
|
47
|
+
else
|
48
|
+
let g:Align_xstrlen= 1
|
49
|
+
endif
|
50
|
+
endif
|
51
|
+
|
52
|
+
" ---------------------------------------------------------------------
|
53
|
+
" Align#AlignCtrl: enter alignment patterns here {{{1
|
54
|
+
"
|
55
|
+
" Styles = all alignment-break patterns are equivalent
|
56
|
+
" C cycle through alignment-break pattern(s)
|
57
|
+
" l left-justified alignment
|
58
|
+
" r right-justified alignment
|
59
|
+
" c center alignment
|
60
|
+
" - skip separator, treat as part of field
|
61
|
+
" : treat rest of line as field
|
62
|
+
" + repeat previous [lrc] style
|
63
|
+
" < left justify separators
|
64
|
+
" > right justify separators
|
65
|
+
" | center separators
|
66
|
+
"
|
67
|
+
" Builds = s:AlignPat s:AlignCtrl s:AlignPatQty
|
68
|
+
" C s:AlignPat s:AlignCtrl s:AlignPatQty
|
69
|
+
" p s:AlignPrePad
|
70
|
+
" P s:AlignPostPad
|
71
|
+
" w s:AlignLeadKeep
|
72
|
+
" W s:AlignLeadKeep
|
73
|
+
" I s:AlignLeadKeep
|
74
|
+
" l s:AlignStyle
|
75
|
+
" r s:AlignStyle
|
76
|
+
" - s:AlignStyle
|
77
|
+
" + s:AlignStyle
|
78
|
+
" : s:AlignStyle
|
79
|
+
" c s:AlignStyle
|
80
|
+
" g s:AlignGPat
|
81
|
+
" v s:AlignVPat
|
82
|
+
" < s:AlignSep
|
83
|
+
" > s:AlignSep
|
84
|
+
" | s:AlignSep
|
85
|
+
fun! Align#AlignCtrl(...)
|
86
|
+
|
87
|
+
" call Dfunc("AlignCtrl(...) a:0=".a:0)
|
88
|
+
|
89
|
+
" save options that will be changed
|
90
|
+
let keep_search = @/
|
91
|
+
let keep_ic = &ic
|
92
|
+
|
93
|
+
" turn ignorecase off
|
94
|
+
set noic
|
95
|
+
|
96
|
+
" clear visual mode so that old visual-mode selections don't
|
97
|
+
" get applied to new invocations of Align().
|
98
|
+
if v:version < 602
|
99
|
+
if !exists("s:Align_gavemsg")
|
100
|
+
let s:Align_gavemsg= 1
|
101
|
+
echomsg "Align needs at least Vim version 6.2 to clear visual-mode selection"
|
102
|
+
endif
|
103
|
+
elseif exists("s:dovisclear")
|
104
|
+
" call Decho("clearing visual mode a:0=".a:0." a:1<".a:1.">")
|
105
|
+
let clearvmode= visualmode(1)
|
106
|
+
endif
|
107
|
+
|
108
|
+
" set up a list akin to an argument list
|
109
|
+
if a:0 > 0
|
110
|
+
let A= s:QArgSplitter(a:1)
|
111
|
+
else
|
112
|
+
let A=[0]
|
113
|
+
endif
|
114
|
+
|
115
|
+
if A[0] > 0
|
116
|
+
let style = A[1]
|
117
|
+
|
118
|
+
" Check for bad separator patterns (zero-length matches)
|
119
|
+
" (but zero-length patterns for g/v is ok)
|
120
|
+
if style !~# '[gv]'
|
121
|
+
let ipat= 2
|
122
|
+
while ipat <= A[0]
|
123
|
+
if "" =~ A[ipat]
|
124
|
+
echoerr "AlignCtrl: separator<".A[ipat]."> matches zero-length string"
|
125
|
+
let &ic= keep_ic
|
126
|
+
" call Dret("AlignCtrl")
|
127
|
+
return
|
128
|
+
endif
|
129
|
+
let ipat= ipat + 1
|
130
|
+
endwhile
|
131
|
+
endif
|
132
|
+
endif
|
133
|
+
|
134
|
+
" call Decho("AlignCtrl() A[0]=".A[0])
|
135
|
+
if !exists("s:AlignStyle")
|
136
|
+
let s:AlignStyle= "l"
|
137
|
+
endif
|
138
|
+
if !exists("s:AlignPrePad")
|
139
|
+
let s:AlignPrePad= 0
|
140
|
+
endif
|
141
|
+
if !exists("s:AlignPostPad")
|
142
|
+
let s:AlignPostPad= 0
|
143
|
+
endif
|
144
|
+
if !exists("s:AlignLeadKeep")
|
145
|
+
let s:AlignLeadKeep= 'w'
|
146
|
+
endif
|
147
|
+
|
148
|
+
if A[0] == 0
|
149
|
+
" ----------------------
|
150
|
+
" List current selection
|
151
|
+
" ----------------------
|
152
|
+
if !exists("s:AlignPatQty")
|
153
|
+
let s:AlignPatQty= 0
|
154
|
+
endif
|
155
|
+
echo "AlignCtrl<".s:AlignCtrl."> qty=".s:AlignPatQty." AlignStyle<".s:AlignStyle."> Padding<".s:AlignPrePad."|".s:AlignPostPad."> LeadingWS=".s:AlignLeadKeep." AlignSep=".s:AlignSep
|
156
|
+
" call Decho("AlignCtrl<".s:AlignCtrl."> qty=".s:AlignPatQty." AlignStyle<".s:AlignStyle."> Padding<".s:AlignPrePad."|".s:AlignPostPad."> LeadingWS=".s:AlignLeadKeep." AlignSep=".s:AlignSep)
|
157
|
+
if exists("s:AlignGPat") && !exists("s:AlignVPat")
|
158
|
+
echo "AlignGPat<".s:AlignGPat.">"
|
159
|
+
elseif !exists("s:AlignGPat") && exists("s:AlignVPat")
|
160
|
+
echo "AlignVPat<".s:AlignVPat.">"
|
161
|
+
elseif exists("s:AlignGPat") && exists("s:AlignVPat")
|
162
|
+
echo "AlignGPat<".s:AlignGPat."> AlignVPat<".s:AlignVPat.">"
|
163
|
+
endif
|
164
|
+
let ipat= 1
|
165
|
+
while ipat <= s:AlignPatQty
|
166
|
+
echo "Pat".ipat."<".s:AlignPat_{ipat}.">"
|
167
|
+
" call Decho("Pat".ipat."<".s:AlignPat_{ipat}.">")
|
168
|
+
let ipat= ipat + 1
|
169
|
+
endwhile
|
170
|
+
|
171
|
+
else
|
172
|
+
" ----------------------------------
|
173
|
+
" Process alignment control settings
|
174
|
+
" ----------------------------------
|
175
|
+
" call Decho("process the alignctrl settings")
|
176
|
+
" call Decho("style<".style.">")
|
177
|
+
|
178
|
+
if style ==? "default"
|
179
|
+
" Default: preserve initial leading whitespace, left-justified,
|
180
|
+
" alignment on '=', one space padding on both sides
|
181
|
+
if exists("s:AlignCtrlStackQty")
|
182
|
+
" clear AlignCtrl stack
|
183
|
+
while s:AlignCtrlStackQty > 0
|
184
|
+
call Align#AlignPop()
|
185
|
+
endwhile
|
186
|
+
unlet s:AlignCtrlStackQty
|
187
|
+
endif
|
188
|
+
" Set AlignCtrl to its default value
|
189
|
+
call Align#AlignCtrl("Ilp1P1=<",'=')
|
190
|
+
call Align#AlignCtrl("g")
|
191
|
+
call Align#AlignCtrl("v")
|
192
|
+
let s:dovisclear = 1
|
193
|
+
let &ic = keep_ic
|
194
|
+
let @/ = keep_search
|
195
|
+
" call Dret("AlignCtrl")
|
196
|
+
return
|
197
|
+
endif
|
198
|
+
|
199
|
+
if style =~# 'm'
|
200
|
+
" map support: Do an AlignPush now and the next call to Align()
|
201
|
+
" will do an AlignPop at exit
|
202
|
+
" call Decho("style case m: do AlignPush")
|
203
|
+
call Align#AlignPush()
|
204
|
+
let s:DoAlignPop= 1
|
205
|
+
endif
|
206
|
+
|
207
|
+
" = : record a list of alignment patterns that are equivalent
|
208
|
+
if style =~# "="
|
209
|
+
" call Decho("style case =: record list of equiv alignment patterns")
|
210
|
+
let s:AlignCtrl = '='
|
211
|
+
if A[0] >= 2
|
212
|
+
let s:AlignPatQty= 1
|
213
|
+
let s:AlignPat_1 = A[2]
|
214
|
+
let ipat = 3
|
215
|
+
while ipat <= A[0]
|
216
|
+
let s:AlignPat_1 = s:AlignPat_1.'\|'.A[ipat]
|
217
|
+
let ipat = ipat + 1
|
218
|
+
endwhile
|
219
|
+
let s:AlignPat_1= '\('.s:AlignPat_1.'\)'
|
220
|
+
" call Decho("AlignCtrl<".s:AlignCtrl."> AlignPat<".s:AlignPat_1.">")
|
221
|
+
endif
|
222
|
+
|
223
|
+
"c : cycle through alignment pattern(s)
|
224
|
+
elseif style =~# 'C'
|
225
|
+
" call Decho("style case C: cycle through alignment pattern(s)")
|
226
|
+
let s:AlignCtrl = 'C'
|
227
|
+
if A[0] >= 2
|
228
|
+
let s:AlignPatQty= A[0] - 1
|
229
|
+
let ipat = 1
|
230
|
+
while ipat < A[0]
|
231
|
+
let s:AlignPat_{ipat}= A[ipat+1]
|
232
|
+
" call Decho("AlignCtrl<".s:AlignCtrl."> AlignQty=".s:AlignPatQty." AlignPat_".ipat."<".s:AlignPat_{ipat}.">")
|
233
|
+
let ipat= ipat + 1
|
234
|
+
endwhile
|
235
|
+
endif
|
236
|
+
endif
|
237
|
+
|
238
|
+
if style =~# 'p'
|
239
|
+
let s:AlignPrePad= substitute(style,'^.*p\(\d\+\).*$','\1','')
|
240
|
+
" call Decho("style case p".s:AlignPrePad.": pre-separator padding")
|
241
|
+
if s:AlignPrePad == ""
|
242
|
+
echoerr "AlignCtrl: 'p' needs to be followed by a numeric argument'
|
243
|
+
let @/ = keep_search
|
244
|
+
let &ic= keep_ic
|
245
|
+
" call Dret("AlignCtrl")
|
246
|
+
return
|
247
|
+
endif
|
248
|
+
endif
|
249
|
+
|
250
|
+
if style =~# 'P'
|
251
|
+
let s:AlignPostPad= substitute(style,'^.*P\(\d\+\).*$','\1','')
|
252
|
+
" call Decho("style case P".s:AlignPostPad.": post-separator padding")
|
253
|
+
if s:AlignPostPad == ""
|
254
|
+
echoerr "AlignCtrl: 'P' needs to be followed by a numeric argument'
|
255
|
+
let @/ = keep_search
|
256
|
+
let &ic= keep_ic
|
257
|
+
" call Dret("AlignCtrl")
|
258
|
+
return
|
259
|
+
endif
|
260
|
+
endif
|
261
|
+
|
262
|
+
if style =~# 'w'
|
263
|
+
" call Decho("style case w: ignore leading whitespace")
|
264
|
+
let s:AlignLeadKeep= 'w'
|
265
|
+
elseif style =~# 'W'
|
266
|
+
" call Decho("style case w: keep leading whitespace")
|
267
|
+
let s:AlignLeadKeep= 'W'
|
268
|
+
elseif style =~# 'I'
|
269
|
+
" call Decho("style case w: retain initial leading whitespace")
|
270
|
+
let s:AlignLeadKeep= 'I'
|
271
|
+
endif
|
272
|
+
|
273
|
+
if style =~# 'g'
|
274
|
+
" first list item is a "g" selector pattern
|
275
|
+
" call Decho("style case g: global selector pattern")
|
276
|
+
if A[0] < 2
|
277
|
+
if exists("s:AlignGPat")
|
278
|
+
unlet s:AlignGPat
|
279
|
+
" call Decho("unlet s:AlignGPat")
|
280
|
+
endif
|
281
|
+
else
|
282
|
+
let s:AlignGPat= A[2]
|
283
|
+
" call Decho("s:AlignGPat<".s:AlignGPat.">")
|
284
|
+
endif
|
285
|
+
elseif style =~# 'v'
|
286
|
+
" first list item is a "v" selector pattern
|
287
|
+
" call Decho("style case v: global selector anti-pattern")
|
288
|
+
if A[0] < 2
|
289
|
+
if exists("s:AlignVPat")
|
290
|
+
unlet s:AlignVPat
|
291
|
+
" call Decho("unlet s:AlignVPat")
|
292
|
+
endif
|
293
|
+
else
|
294
|
+
let s:AlignVPat= A[2]
|
295
|
+
" call Decho("s:AlignVPat<".s:AlignVPat.">")
|
296
|
+
endif
|
297
|
+
endif
|
298
|
+
|
299
|
+
"[-lrc+:] : set up s:AlignStyle
|
300
|
+
if style =~# '[-lrc+:]'
|
301
|
+
" call Decho("style case [-lrc+:]: field justification")
|
302
|
+
let s:AlignStyle= substitute(style,'[^-lrc:+]','','g')
|
303
|
+
" call Decho("AlignStyle<".s:AlignStyle.">")
|
304
|
+
endif
|
305
|
+
|
306
|
+
"[<>|] : set up s:AlignSep
|
307
|
+
if style =~# '[<>|]'
|
308
|
+
" call Decho("style case [-lrc+:]: separator justification")
|
309
|
+
let s:AlignSep= substitute(style,'[^<>|]','','g')
|
310
|
+
" call Decho("AlignSep ".s:AlignSep)
|
311
|
+
endif
|
312
|
+
endif
|
313
|
+
|
314
|
+
" sanity
|
315
|
+
if !exists("s:AlignCtrl")
|
316
|
+
let s:AlignCtrl= '='
|
317
|
+
endif
|
318
|
+
|
319
|
+
" restore search and options
|
320
|
+
let @/ = keep_search
|
321
|
+
let &ic= keep_ic
|
322
|
+
|
323
|
+
" call Dret("AlignCtrl ".s:AlignCtrl.'p'.s:AlignPrePad.'P'.s:AlignPostPad.s:AlignLeadKeep.s:AlignStyle)
|
324
|
+
return s:AlignCtrl.'p'.s:AlignPrePad.'P'.s:AlignPostPad.s:AlignLeadKeep.s:AlignStyle
|
325
|
+
endfun
|
326
|
+
|
327
|
+
" ---------------------------------------------------------------------
|
328
|
+
" s:MakeSpace: returns a string with spacecnt blanks {{{1
|
329
|
+
fun! s:MakeSpace(spacecnt)
|
330
|
+
" call Dfunc("MakeSpace(spacecnt=".a:spacecnt.")")
|
331
|
+
let str = ""
|
332
|
+
let spacecnt = a:spacecnt
|
333
|
+
while spacecnt > 0
|
334
|
+
let str = str . " "
|
335
|
+
let spacecnt = spacecnt - 1
|
336
|
+
endwhile
|
337
|
+
" call Dret("MakeSpace <".str.">")
|
338
|
+
return str
|
339
|
+
endfun
|
340
|
+
|
341
|
+
" ---------------------------------------------------------------------
|
342
|
+
" Align#Align: align selected text based on alignment pattern(s) {{{1
|
343
|
+
fun! Align#Align(hasctrl,...) range
|
344
|
+
" call Dfunc("Align#Align(hasctrl=".a:hasctrl.",...) a:0=".a:0)
|
345
|
+
|
346
|
+
" sanity checks
|
347
|
+
if string(a:hasctrl) != "0" && string(a:hasctrl) != "1"
|
348
|
+
echohl Error|echo 'usage: Align#Align(hasctrl<'.a:hasctrl.'> (should be 0 or 1),"separator(s)" (you have '.a:0.') )'|echohl None
|
349
|
+
" call Dret("Align#Align")
|
350
|
+
return
|
351
|
+
endif
|
352
|
+
if exists("s:AlignStyle") && s:AlignStyle == ":"
|
353
|
+
echohl Error |echo '(Align#Align) your AlignStyle is ":", which implies "do-no-alignment"!'|echohl None
|
354
|
+
" call Dret("Align#Align")
|
355
|
+
return
|
356
|
+
endif
|
357
|
+
|
358
|
+
" set up a list akin to an argument list
|
359
|
+
if a:0 > 0
|
360
|
+
let A= s:QArgSplitter(a:1)
|
361
|
+
else
|
362
|
+
let A=[0]
|
363
|
+
endif
|
364
|
+
|
365
|
+
" if :Align! was used, then the first argument is (should be!) an AlignCtrl string
|
366
|
+
" Note that any alignment control set this way will be temporary.
|
367
|
+
let hasctrl= a:hasctrl
|
368
|
+
" call Decho("hasctrl=".hasctrl)
|
369
|
+
if a:hasctrl && A[0] >= 1
|
370
|
+
" call Decho("Align! : using A[1]<".A[1]."> for AlignCtrl")
|
371
|
+
if A[1] =~ '[gv]'
|
372
|
+
let hasctrl= hasctrl + 1
|
373
|
+
call Align#AlignCtrl('m')
|
374
|
+
call Align#AlignCtrl(A[1],A[2])
|
375
|
+
" call Decho("Align! : also using A[2]<".A[2]."> for AlignCtrl")
|
376
|
+
elseif A[1] !~ 'm'
|
377
|
+
call Align#AlignCtrl(A[1]."m")
|
378
|
+
else
|
379
|
+
call Align#AlignCtrl(A[1])
|
380
|
+
endif
|
381
|
+
endif
|
382
|
+
|
383
|
+
" Check for bad separator patterns (zero-length matches)
|
384
|
+
let ipat= 1 + hasctrl
|
385
|
+
while ipat <= A[0]
|
386
|
+
if "" =~ A[ipat]
|
387
|
+
echoerr "Align: separator<".A[ipat]."> matches zero-length string"
|
388
|
+
" call Dret("Align#Align")
|
389
|
+
return
|
390
|
+
endif
|
391
|
+
let ipat= ipat + 1
|
392
|
+
endwhile
|
393
|
+
|
394
|
+
" record current search pattern for subsequent restoration
|
395
|
+
let keep_search= @/
|
396
|
+
let keep_ic = &ic
|
397
|
+
let keep_report= &report
|
398
|
+
set noic report=10000
|
399
|
+
|
400
|
+
if A[0] > hasctrl
|
401
|
+
" Align will accept a list of separator regexps
|
402
|
+
" call Decho("A[0]=".A[0].": accepting list of separator regexp")
|
403
|
+
|
404
|
+
if s:AlignCtrl =~# "="
|
405
|
+
"= : consider all separators to be equivalent
|
406
|
+
" call Decho("AlignCtrl: record list of equivalent alignment patterns")
|
407
|
+
let s:AlignCtrl = '='
|
408
|
+
let s:AlignPat_1 = A[1 + hasctrl]
|
409
|
+
let s:AlignPatQty= 1
|
410
|
+
let ipat = 2 + hasctrl
|
411
|
+
while ipat <= A[0]
|
412
|
+
let s:AlignPat_1 = s:AlignPat_1.'\|'.A[ipat]
|
413
|
+
let ipat = ipat + 1
|
414
|
+
endwhile
|
415
|
+
let s:AlignPat_1= '\('.s:AlignPat_1.'\)'
|
416
|
+
" call Decho("AlignCtrl<".s:AlignCtrl."> AlignPat<".s:AlignPat_1.">")
|
417
|
+
|
418
|
+
elseif s:AlignCtrl =~# 'C'
|
419
|
+
"c : cycle through alignment pattern(s)
|
420
|
+
" call Decho("AlignCtrl: cycle through alignment pattern(s)")
|
421
|
+
let s:AlignCtrl = 'C'
|
422
|
+
let s:AlignPatQty= A[0] - hasctrl
|
423
|
+
let ipat = 1
|
424
|
+
while ipat <= s:AlignPatQty
|
425
|
+
let s:AlignPat_{ipat}= A[(ipat + hasctrl)]
|
426
|
+
" call Decho("AlignCtrl<".s:AlignCtrl."> AlignQty=".s:AlignPatQty." AlignPat_".ipat."<".s:AlignPat_{ipat}.">")
|
427
|
+
let ipat= ipat + 1
|
428
|
+
endwhile
|
429
|
+
endif
|
430
|
+
endif
|
431
|
+
|
432
|
+
" Initialize so that begline<endline and begcol<endcol.
|
433
|
+
" Ragged right: check if the column associated with '< or '>
|
434
|
+
" is greater than the line's string length -> ragged right.
|
435
|
+
" Have to be careful about visualmode() -- it returns the last visual
|
436
|
+
" mode used whether or not it was used currently.
|
437
|
+
let begcol = virtcol("'<")-1
|
438
|
+
let endcol = virtcol("'>")-1
|
439
|
+
if begcol > endcol
|
440
|
+
let begcol = virtcol("'>")-1
|
441
|
+
let endcol = virtcol("'<")-1
|
442
|
+
endif
|
443
|
+
" call Decho("begcol=".begcol." endcol=".endcol)
|
444
|
+
let begline = a:firstline
|
445
|
+
let endline = a:lastline
|
446
|
+
if begline > endline
|
447
|
+
let begline = a:lastline
|
448
|
+
let endline = a:firstline
|
449
|
+
endif
|
450
|
+
" call Decho("begline=".begline." endline=".endline)
|
451
|
+
let fieldcnt = 0
|
452
|
+
if (begline == line("'>") && endline == line("'<")) || (begline == line("'<") && endline == line("'>"))
|
453
|
+
let vmode= visualmode()
|
454
|
+
" call Decho("vmode=".vmode)
|
455
|
+
if vmode == "\<c-v>"
|
456
|
+
if exists("g:Align_xstrlen") && g:Align_xstrlen
|
457
|
+
let ragged = ( col("'>") > s:Strlen(getline("'>")) || col("'<") > s:Strlen(getline("'<")) )
|
458
|
+
else
|
459
|
+
let ragged = ( col("'>") > strlen(getline("'>")) || col("'<") > strlen(getline("'<")) )
|
460
|
+
endif
|
461
|
+
else
|
462
|
+
let ragged= 1
|
463
|
+
endif
|
464
|
+
else
|
465
|
+
let ragged= 1
|
466
|
+
endif
|
467
|
+
if ragged
|
468
|
+
let begcol= 0
|
469
|
+
endif
|
470
|
+
" call Decho("lines[".begline.",".endline."] col[".begcol.",".endcol."] ragged=".ragged." AlignCtrl<".s:AlignCtrl.">")
|
471
|
+
|
472
|
+
" Keep user options
|
473
|
+
let etkeep = &l:et
|
474
|
+
let pastekeep= &l:paste
|
475
|
+
setlocal et paste
|
476
|
+
|
477
|
+
" convert selected range of lines to use spaces instead of tabs
|
478
|
+
" but if first line's initial white spaces are to be retained
|
479
|
+
" then use 'em
|
480
|
+
if begcol <= 0 && s:AlignLeadKeep == 'I'
|
481
|
+
" retain first leading whitespace for all subsequent lines
|
482
|
+
let bgntxt= substitute(getline(begline),'^\(\s*\).\{-}$','\1','')
|
483
|
+
" call Decho("retaining 1st leading whitespace: bgntxt<".bgntxt.">")
|
484
|
+
set noet
|
485
|
+
endif
|
486
|
+
exe begline.",".endline."ret"
|
487
|
+
|
488
|
+
" Execute two passes
|
489
|
+
" First pass: collect alignment data (max field sizes)
|
490
|
+
" Second pass: perform alignment
|
491
|
+
let pass= 1
|
492
|
+
while pass <= 2
|
493
|
+
" call Decho(" ")
|
494
|
+
" call Decho("---- Pass ".pass.": ----")
|
495
|
+
|
496
|
+
let line= begline
|
497
|
+
while line <= endline
|
498
|
+
" Process each line
|
499
|
+
let txt = getline(line)
|
500
|
+
" call Decho(" ")
|
501
|
+
" call Decho("Pass".pass.": Line ".line." <".txt.">")
|
502
|
+
|
503
|
+
" AlignGPat support: allows a selector pattern (akin to g/selector/cmd )
|
504
|
+
if exists("s:AlignGPat")
|
505
|
+
" call Decho("Pass".pass.": AlignGPat<".s:AlignGPat.">")
|
506
|
+
if match(txt,s:AlignGPat) == -1
|
507
|
+
" call Decho("Pass".pass.": skipping")
|
508
|
+
let line= line + 1
|
509
|
+
continue
|
510
|
+
endif
|
511
|
+
endif
|
512
|
+
|
513
|
+
" AlignVPat support: allows a selector pattern (akin to v/selector/cmd )
|
514
|
+
if exists("s:AlignVPat")
|
515
|
+
" call Decho("Pass".pass.": AlignVPat<".s:AlignVPat.">")
|
516
|
+
if match(txt,s:AlignVPat) != -1
|
517
|
+
" call Decho("Pass".pass.": skipping")
|
518
|
+
let line= line + 1
|
519
|
+
continue
|
520
|
+
endif
|
521
|
+
endif
|
522
|
+
|
523
|
+
" Always skip blank lines
|
524
|
+
if match(txt,'^\s*$') != -1
|
525
|
+
" call Decho("Pass".pass.": skipping")
|
526
|
+
let line= line + 1
|
527
|
+
continue
|
528
|
+
endif
|
529
|
+
|
530
|
+
" Extract visual-block selected text (init bgntxt, endtxt)
|
531
|
+
if exists("g:Align_xstrlen") && g:Align_xstrlen
|
532
|
+
let txtlen= s:Strlen(txt)
|
533
|
+
else
|
534
|
+
let txtlen= strlen(txt)
|
535
|
+
endif
|
536
|
+
if begcol > 0
|
537
|
+
" Record text to left of selected area
|
538
|
+
let bgntxt= strpart(txt,0,begcol)
|
539
|
+
" call Decho("Pass".pass.": record text to left: bgntxt<".bgntxt.">")
|
540
|
+
elseif s:AlignLeadKeep == 'W'
|
541
|
+
let bgntxt= substitute(txt,'^\(\s*\).\{-}$','\1','')
|
542
|
+
" call Decho("Pass".pass.": retaining all leading ws: bgntxt<".bgntxt.">")
|
543
|
+
elseif s:AlignLeadKeep == 'w' || !exists("bgntxt")
|
544
|
+
" No beginning text
|
545
|
+
let bgntxt= ""
|
546
|
+
" call Decho("Pass".pass.": no beginning text")
|
547
|
+
endif
|
548
|
+
if ragged
|
549
|
+
let endtxt= ""
|
550
|
+
else
|
551
|
+
" Elide any text lying outside selected columnar region
|
552
|
+
let endtxt= strpart(txt,endcol+1,txtlen-endcol)
|
553
|
+
let txt = strpart(txt,begcol,endcol-begcol+1)
|
554
|
+
endif
|
555
|
+
" call Decho(" ")
|
556
|
+
" call Decho("Pass".pass.": bgntxt<".bgntxt.">")
|
557
|
+
" call Decho("Pass".pass.": txt<". txt .">")
|
558
|
+
" call Decho("Pass".pass.": endtxt<".endtxt.">")
|
559
|
+
if !exists("s:AlignPat_{1}")
|
560
|
+
echohl Error|echo "no separators specified!"|echohl None
|
561
|
+
" call Dret("Align#Align")
|
562
|
+
return
|
563
|
+
endif
|
564
|
+
|
565
|
+
" Initialize for both passes
|
566
|
+
let seppat = s:AlignPat_{1}
|
567
|
+
let ifield = 1
|
568
|
+
let ipat = 1
|
569
|
+
let bgnfield = 0
|
570
|
+
let endfield = 0
|
571
|
+
let alignstyle = s:AlignStyle
|
572
|
+
let doend = 1
|
573
|
+
let newtxt = ""
|
574
|
+
let alignprepad = s:AlignPrePad
|
575
|
+
let alignpostpad= s:AlignPostPad
|
576
|
+
let alignsep = s:AlignSep
|
577
|
+
let alignophold = " "
|
578
|
+
let alignop = "l"
|
579
|
+
" call Decho("Pass".pass.": initial alignstyle<".alignstyle."> seppat<".seppat.">")
|
580
|
+
|
581
|
+
" Process each field on the line
|
582
|
+
while doend > 0
|
583
|
+
|
584
|
+
" C-style: cycle through pattern(s)
|
585
|
+
if s:AlignCtrl == 'C' && doend == 1
|
586
|
+
let seppat = s:AlignPat_{ipat}
|
587
|
+
" call Decho("Pass".pass.": processing field: AlignCtrl=".s:AlignCtrl." ipat=".ipat." seppat<".seppat.">")
|
588
|
+
let ipat = ipat + 1
|
589
|
+
if ipat > s:AlignPatQty
|
590
|
+
let ipat = 1
|
591
|
+
endif
|
592
|
+
endif
|
593
|
+
|
594
|
+
" cyclic alignment/justification operator handling
|
595
|
+
let alignophold = alignop
|
596
|
+
let alignop = strpart(alignstyle,0,1)
|
597
|
+
if alignop == '+' || doend == 2
|
598
|
+
let alignop= alignophold
|
599
|
+
else
|
600
|
+
let alignstyle = strpart(alignstyle,1).strpart(alignstyle,0,1)
|
601
|
+
let alignopnxt = strpart(alignstyle,0,1)
|
602
|
+
if alignop == ':'
|
603
|
+
let seppat = '$'
|
604
|
+
let doend = 2
|
605
|
+
" call Decho("Pass".pass.": alignop<:> case: setting seppat<$> doend==2")
|
606
|
+
endif
|
607
|
+
endif
|
608
|
+
|
609
|
+
" cylic separator alignment specification handling
|
610
|
+
let alignsepop= strpart(alignsep,0,1)
|
611
|
+
let alignsep = strpart(alignsep,1).alignsepop
|
612
|
+
|
613
|
+
" mark end-of-field and the subsequent end-of-separator.
|
614
|
+
" Extend field if alignop is '-'
|
615
|
+
let endfield = match(txt,seppat,bgnfield)
|
616
|
+
let sepfield = matchend(txt,seppat,bgnfield)
|
617
|
+
let skipfield= sepfield
|
618
|
+
" call Decho("Pass".pass.": endfield=match(txt<".txt.">,seppat<".seppat.">,bgnfield=".bgnfield.")=".endfield)
|
619
|
+
while alignop == '-' && endfield != -1
|
620
|
+
let endfield = match(txt,seppat,skipfield)
|
621
|
+
let sepfield = matchend(txt,seppat,skipfield)
|
622
|
+
let skipfield = sepfield
|
623
|
+
let alignop = strpart(alignstyle,0,1)
|
624
|
+
let alignstyle= strpart(alignstyle,1).strpart(alignstyle,0,1)
|
625
|
+
" call Decho("Pass".pass.": extend field: endfield<".strpart(txt,bgnfield,endfield-bgnfield)."> alignop<".alignop."> alignstyle<".alignstyle.">")
|
626
|
+
endwhile
|
627
|
+
let seplen= sepfield - endfield
|
628
|
+
" call Decho("Pass".pass.": seplen=[sepfield=".sepfield."] - [endfield=".endfield."]=".seplen)
|
629
|
+
|
630
|
+
if endfield != -1
|
631
|
+
if pass == 1
|
632
|
+
" ---------------------------------------------------------------------
|
633
|
+
" Pass 1: Update FieldSize to max
|
634
|
+
" call Decho("Pass".pass.": before lead/trail remove: field<".strpart(txt,bgnfield,endfield-bgnfield).">")
|
635
|
+
let field = substitute(strpart(txt,bgnfield,endfield-bgnfield),'^\s*\(.\{-}\)\s*$','\1','')
|
636
|
+
if s:AlignLeadKeep == 'W'
|
637
|
+
let field = bgntxt.field
|
638
|
+
let bgntxt= ""
|
639
|
+
endif
|
640
|
+
if exists("g:Align_xstrlen") && g:Align_xstrlen
|
641
|
+
let fieldlen = s:Strlen(field)
|
642
|
+
else
|
643
|
+
let fieldlen = strlen(field)
|
644
|
+
endif
|
645
|
+
let sFieldSize = "FieldSize_".ifield
|
646
|
+
if !exists(sFieldSize)
|
647
|
+
let FieldSize_{ifield}= fieldlen
|
648
|
+
" call Decho("Pass".pass.": set FieldSize_{".ifield."}=".FieldSize_{ifield}." <".field.">")
|
649
|
+
elseif fieldlen > FieldSize_{ifield}
|
650
|
+
let FieldSize_{ifield}= fieldlen
|
651
|
+
" call Decho("Pass".pass.": oset FieldSize_{".ifield."}=".FieldSize_{ifield}." <".field.">")
|
652
|
+
endif
|
653
|
+
let sSepSize= "SepSize_".ifield
|
654
|
+
if !exists(sSepSize)
|
655
|
+
let SepSize_{ifield}= seplen
|
656
|
+
" call Decho(" set SepSize_{".ifield."}=".SepSize_{ifield}." <".field.">")
|
657
|
+
elseif seplen > SepSize_{ifield}
|
658
|
+
let SepSize_{ifield}= seplen
|
659
|
+
" call Decho("Pass".pass.": oset SepSize_{".ifield."}=".SepSize_{ifield}." <".field.">")
|
660
|
+
endif
|
661
|
+
|
662
|
+
else
|
663
|
+
" ---------------------------------------------------------------------
|
664
|
+
" Pass 2: Perform Alignment
|
665
|
+
let prepad = strpart(alignprepad,0,1)
|
666
|
+
let postpad = strpart(alignpostpad,0,1)
|
667
|
+
let alignprepad = strpart(alignprepad,1).strpart(alignprepad,0,1)
|
668
|
+
let alignpostpad = strpart(alignpostpad,1).strpart(alignpostpad,0,1)
|
669
|
+
let field = substitute(strpart(txt,bgnfield,endfield-bgnfield),'^\s*\(.\{-}\)\s*$','\1','')
|
670
|
+
if s:AlignLeadKeep == 'W'
|
671
|
+
let field = bgntxt.field
|
672
|
+
let bgntxt= ""
|
673
|
+
endif
|
674
|
+
if doend == 2
|
675
|
+
let prepad = 0
|
676
|
+
let postpad= 0
|
677
|
+
endif
|
678
|
+
if exists("g:Align_xstrlen") && g:Align_xstrlen
|
679
|
+
let fieldlen = s:Strlen(field)
|
680
|
+
else
|
681
|
+
let fieldlen = strlen(field)
|
682
|
+
endif
|
683
|
+
let sep = s:MakeSpace(prepad).strpart(txt,endfield,sepfield-endfield).s:MakeSpace(postpad)
|
684
|
+
if seplen < SepSize_{ifield}
|
685
|
+
if alignsepop == "<"
|
686
|
+
" left-justify separators
|
687
|
+
let sep = sep.s:MakeSpace(SepSize_{ifield}-seplen)
|
688
|
+
elseif alignsepop == ">"
|
689
|
+
" right-justify separators
|
690
|
+
let sep = s:MakeSpace(SepSize_{ifield}-seplen).sep
|
691
|
+
else
|
692
|
+
" center-justify separators
|
693
|
+
let sepleft = (SepSize_{ifield} - seplen)/2
|
694
|
+
let sepright = SepSize_{ifield} - seplen - sepleft
|
695
|
+
let sep = s:MakeSpace(sepleft).sep.s:MakeSpace(sepright)
|
696
|
+
endif
|
697
|
+
endif
|
698
|
+
let spaces = FieldSize_{ifield} - fieldlen
|
699
|
+
" call Decho("Pass".pass.": Field #".ifield."<".field."> spaces=".spaces." be[".bgnfield.",".endfield."] pad=".prepad.','.postpad." FS_".ifield."<".FieldSize_{ifield}."> sep<".sep."> ragged=".ragged." doend=".doend." alignop<".alignop.">")
|
700
|
+
|
701
|
+
" Perform alignment according to alignment style justification
|
702
|
+
if spaces > 0
|
703
|
+
if alignop == 'c'
|
704
|
+
" center the field
|
705
|
+
let spaceleft = spaces/2
|
706
|
+
let spaceright= FieldSize_{ifield} - spaceleft - fieldlen
|
707
|
+
let newtxt = newtxt.s:MakeSpace(spaceleft).field.s:MakeSpace(spaceright).sep
|
708
|
+
elseif alignop == 'r'
|
709
|
+
" right justify the field
|
710
|
+
let newtxt= newtxt.s:MakeSpace(spaces).field.sep
|
711
|
+
elseif ragged && doend == 2
|
712
|
+
" left justify rightmost field (no trailing blanks needed)
|
713
|
+
let newtxt= newtxt.field
|
714
|
+
else
|
715
|
+
" left justfiy the field
|
716
|
+
let newtxt= newtxt.field.s:MakeSpace(spaces).sep
|
717
|
+
endif
|
718
|
+
elseif ragged && doend == 2
|
719
|
+
" field at maximum field size and no trailing blanks needed
|
720
|
+
let newtxt= newtxt.field
|
721
|
+
else
|
722
|
+
" field is at maximum field size already
|
723
|
+
let newtxt= newtxt.field.sep
|
724
|
+
endif
|
725
|
+
" call Decho("Pass".pass.": newtxt<".newtxt.">")
|
726
|
+
endif " pass 1/2
|
727
|
+
|
728
|
+
" bgnfield indexes to end of separator at right of current field
|
729
|
+
" Update field counter
|
730
|
+
let bgnfield= sepfield
|
731
|
+
let ifield = ifield + 1
|
732
|
+
if doend == 2
|
733
|
+
let doend= 0
|
734
|
+
endif
|
735
|
+
" handle end-of-text as end-of-field
|
736
|
+
elseif doend == 1
|
737
|
+
let seppat = '$'
|
738
|
+
let doend = 2
|
739
|
+
else
|
740
|
+
let doend = 0
|
741
|
+
endif " endfield != -1
|
742
|
+
endwhile " doend loop (as well as regularly separated fields)
|
743
|
+
|
744
|
+
if pass == 2
|
745
|
+
" Write altered line to buffer
|
746
|
+
" call Decho("Pass".pass.": bgntxt<".bgntxt."> line=".line)
|
747
|
+
" call Decho("Pass".pass.": newtxt<".newtxt.">")
|
748
|
+
" call Decho("Pass".pass.": endtxt<".endtxt.">")
|
749
|
+
call setline(line,bgntxt.newtxt.endtxt)
|
750
|
+
endif
|
751
|
+
|
752
|
+
let line = line + 1
|
753
|
+
endwhile " line loop
|
754
|
+
|
755
|
+
let pass= pass + 1
|
756
|
+
endwhile " pass loop
|
757
|
+
" call Decho("end of two pass loop")
|
758
|
+
|
759
|
+
" Restore user options
|
760
|
+
let &l:et = etkeep
|
761
|
+
let &l:paste = pastekeep
|
762
|
+
|
763
|
+
if exists("s:DoAlignPop")
|
764
|
+
" AlignCtrl Map support
|
765
|
+
call Align#AlignPop()
|
766
|
+
unlet s:DoAlignPop
|
767
|
+
endif
|
768
|
+
|
769
|
+
" restore current search pattern
|
770
|
+
let @/ = keep_search
|
771
|
+
let &ic = keep_ic
|
772
|
+
let &report = keep_report
|
773
|
+
|
774
|
+
" call Dret("Align#Align")
|
775
|
+
return
|
776
|
+
endfun
|
777
|
+
|
778
|
+
" ---------------------------------------------------------------------
|
779
|
+
" Align#AlignPush: this command/function pushes an alignment control string onto a stack {{{1
|
780
|
+
fun! Align#AlignPush()
|
781
|
+
" call Dfunc("AlignPush()")
|
782
|
+
|
783
|
+
" initialize the stack
|
784
|
+
if !exists("s:AlignCtrlStackQty")
|
785
|
+
let s:AlignCtrlStackQty= 1
|
786
|
+
else
|
787
|
+
let s:AlignCtrlStackQty= s:AlignCtrlStackQty + 1
|
788
|
+
endif
|
789
|
+
|
790
|
+
" construct an AlignCtrlStack entry
|
791
|
+
if !exists("s:AlignSep")
|
792
|
+
let s:AlignSep= ''
|
793
|
+
endif
|
794
|
+
let s:AlignCtrlStack_{s:AlignCtrlStackQty}= s:AlignCtrl.'p'.s:AlignPrePad.'P'.s:AlignPostPad.s:AlignLeadKeep.s:AlignStyle.s:AlignSep
|
795
|
+
" call Decho("AlignPush: AlignCtrlStack_".s:AlignCtrlStackQty."<".s:AlignCtrlStack_{s:AlignCtrlStackQty}.">")
|
796
|
+
|
797
|
+
" push [GV] patterns onto their own stack
|
798
|
+
if exists("s:AlignGPat")
|
799
|
+
let s:AlignGPat_{s:AlignCtrlStackQty}= s:AlignGPat
|
800
|
+
else
|
801
|
+
let s:AlignGPat_{s:AlignCtrlStackQty}= ""
|
802
|
+
endif
|
803
|
+
if exists("s:AlignVPat")
|
804
|
+
let s:AlignVPat_{s:AlignCtrlStackQty}= s:AlignVPat
|
805
|
+
else
|
806
|
+
let s:AlignVPat_{s:AlignCtrlStackQty}= ""
|
807
|
+
endif
|
808
|
+
|
809
|
+
" call Dret("AlignPush")
|
810
|
+
endfun
|
811
|
+
|
812
|
+
" ---------------------------------------------------------------------
|
813
|
+
" Align#AlignPop: this command/function pops an alignment pattern from a stack {{{1
|
814
|
+
" and into the AlignCtrl variables.
|
815
|
+
fun! Align#AlignPop()
|
816
|
+
" call Dfunc("Align#AlignPop()")
|
817
|
+
|
818
|
+
" sanity checks
|
819
|
+
if !exists("s:AlignCtrlStackQty")
|
820
|
+
echoerr "AlignPush needs to be used prior to AlignPop"
|
821
|
+
" call Dret("Align#AlignPop <> : AlignPush needs to have been called first")
|
822
|
+
return ""
|
823
|
+
endif
|
824
|
+
if s:AlignCtrlStackQty <= 0
|
825
|
+
unlet s:AlignCtrlStackQty
|
826
|
+
echoerr "AlignPush needs to be used prior to AlignPop"
|
827
|
+
" call Dret("Align#AlignPop <> : AlignPop needs to have been called first")
|
828
|
+
return ""
|
829
|
+
endif
|
830
|
+
|
831
|
+
" pop top of AlignCtrlStack and pass value to AlignCtrl
|
832
|
+
let retval=s:AlignCtrlStack_{s:AlignCtrlStackQty}
|
833
|
+
unlet s:AlignCtrlStack_{s:AlignCtrlStackQty}
|
834
|
+
call Align#AlignCtrl(retval)
|
835
|
+
|
836
|
+
" pop G pattern stack
|
837
|
+
if s:AlignGPat_{s:AlignCtrlStackQty} != ""
|
838
|
+
call Align#AlignCtrl('g',s:AlignGPat_{s:AlignCtrlStackQty})
|
839
|
+
else
|
840
|
+
call Align#AlignCtrl('g')
|
841
|
+
endif
|
842
|
+
unlet s:AlignGPat_{s:AlignCtrlStackQty}
|
843
|
+
|
844
|
+
" pop V pattern stack
|
845
|
+
if s:AlignVPat_{s:AlignCtrlStackQty} != ""
|
846
|
+
call Align#AlignCtrl('v',s:AlignVPat_{s:AlignCtrlStackQty})
|
847
|
+
else
|
848
|
+
call Align#AlignCtrl('v')
|
849
|
+
endif
|
850
|
+
|
851
|
+
unlet s:AlignVPat_{s:AlignCtrlStackQty}
|
852
|
+
let s:AlignCtrlStackQty= s:AlignCtrlStackQty - 1
|
853
|
+
|
854
|
+
" call Dret("Align#AlignPop <".retval."> : AlignCtrlStackQty=".s:AlignCtrlStackQty)
|
855
|
+
return retval
|
856
|
+
endfun
|
857
|
+
|
858
|
+
" ---------------------------------------------------------------------
|
859
|
+
" Align#AlignReplaceQuotedSpaces: {{{1
|
860
|
+
fun! Align#AlignReplaceQuotedSpaces()
|
861
|
+
" call Dfunc("AlignReplaceQuotedSpaces()")
|
862
|
+
|
863
|
+
let l:line = getline(line("."))
|
864
|
+
if exists("g:Align_xstrlen") && g:Align_xstrlen
|
865
|
+
let l:linelen = s:Strlen(l:line)
|
866
|
+
else
|
867
|
+
let l:linelen = strlen(l:line)
|
868
|
+
endif
|
869
|
+
let l:startingPos = 0
|
870
|
+
let l:startQuotePos = 0
|
871
|
+
let l:endQuotePos = 0
|
872
|
+
let l:spacePos = 0
|
873
|
+
let l:quoteRe = '\\\@<!"'
|
874
|
+
|
875
|
+
" "call Decho("in replace spaces. line=" . line('.'))
|
876
|
+
while (1)
|
877
|
+
let l:startQuotePos = match(l:line, l:quoteRe, l:startingPos)
|
878
|
+
if (l:startQuotePos < 0)
|
879
|
+
" "call Decho("No more quotes to the end of line")
|
880
|
+
break
|
881
|
+
endif
|
882
|
+
let l:endQuotePos = match(l:line, l:quoteRe, l:startQuotePos + 1)
|
883
|
+
if (l:endQuotePos < 0)
|
884
|
+
" "call Decho("Mismatched quotes")
|
885
|
+
break
|
886
|
+
endif
|
887
|
+
let l:spaceReplaceRe = '^.\{' . (l:startQuotePos + 1) . '}.\{-}\zs\s\ze.*.\{' . (linelen - l:endQuotePos) . '}$'
|
888
|
+
" "call Decho('spaceReplaceRe="' . l:spaceReplaceRe . '"')
|
889
|
+
let l:newStr = substitute(l:line, l:spaceReplaceRe, '%', '')
|
890
|
+
while (l:newStr != l:line)
|
891
|
+
" "call Decho('newstr="' . l:newStr . '"')
|
892
|
+
let l:line = l:newStr
|
893
|
+
let l:newStr = substitute(l:line, l:spaceReplaceRe, '%', '')
|
894
|
+
endwhile
|
895
|
+
let l:startingPos = l:endQuotePos + 1
|
896
|
+
endwhile
|
897
|
+
call setline(line('.'), l:line)
|
898
|
+
|
899
|
+
" call Dret("AlignReplaceQuotedSpaces")
|
900
|
+
endfun
|
901
|
+
|
902
|
+
" ---------------------------------------------------------------------
|
903
|
+
" s:QArgSplitter: to avoid \ processing by <f-args>, <q-args> is needed. {{{1
|
904
|
+
" However, <q-args> doesn't split at all, so this function returns a list
|
905
|
+
" of arguments which has been:
|
906
|
+
" * split at whitespace
|
907
|
+
" * unless inside "..."s. One may escape characters with a backslash inside double quotes.
|
908
|
+
" along with a leading length-of-list.
|
909
|
+
"
|
910
|
+
" Examples: %Align "\"" will align on "s
|
911
|
+
" %Align " " will align on spaces
|
912
|
+
"
|
913
|
+
" The resulting list: qarglist[0] corresponds to a:0
|
914
|
+
" qarglist[i] corresponds to a:{i}
|
915
|
+
fun! s:QArgSplitter(qarg)
|
916
|
+
" call Dfunc("s:QArgSplitter(qarg<".a:qarg.">)")
|
917
|
+
|
918
|
+
if a:qarg =~ '".*"'
|
919
|
+
" handle "..." args, which may include whitespace
|
920
|
+
let qarglist = []
|
921
|
+
let args = a:qarg
|
922
|
+
" call Decho("handle quoted arguments: args<".args.">")
|
923
|
+
while args != ""
|
924
|
+
let iarg = 0
|
925
|
+
let arglen = strlen(args)
|
926
|
+
" call Decho("args[".iarg."]<".args[iarg]."> arglen=".arglen)
|
927
|
+
" find index to first not-escaped '"'
|
928
|
+
while args[iarg] != '"' && iarg < arglen
|
929
|
+
if args[iarg] == '\'
|
930
|
+
let args= strpart(args,1)
|
931
|
+
endif
|
932
|
+
let iarg= iarg + 1
|
933
|
+
endwhile
|
934
|
+
" call Decho("args<".args."> iarg=".iarg." arglen=".arglen)
|
935
|
+
|
936
|
+
if iarg > 0
|
937
|
+
" handle left of quote or remaining section
|
938
|
+
" call Decho("handle left of quote or remaining section")
|
939
|
+
if args[iarg] == '"'
|
940
|
+
let qarglist= qarglist + split(strpart(args,0,iarg-1))
|
941
|
+
else
|
942
|
+
let qarglist= qarglist + split(strpart(args,0,iarg))
|
943
|
+
endif
|
944
|
+
let args = strpart(args,iarg)
|
945
|
+
let arglen = strlen(args)
|
946
|
+
|
947
|
+
elseif iarg < arglen && args[0] == '"'
|
948
|
+
" handle "quoted" section
|
949
|
+
" call Decho("handle quoted section")
|
950
|
+
let iarg= 1
|
951
|
+
while args[iarg] != '"' && iarg < arglen
|
952
|
+
if args[iarg] == '\'
|
953
|
+
let args= strpart(args,1)
|
954
|
+
endif
|
955
|
+
let iarg= iarg + 1
|
956
|
+
endwhile
|
957
|
+
" call Decho("args<".args."> iarg=".iarg." arglen=".arglen)
|
958
|
+
if args[iarg] == '"'
|
959
|
+
call add(qarglist,strpart(args,1,iarg-1))
|
960
|
+
let args= strpart(args,iarg+1)
|
961
|
+
else
|
962
|
+
let qarglist = qarglist + split(args)
|
963
|
+
let args = ""
|
964
|
+
endif
|
965
|
+
endif
|
966
|
+
" call Decho("qarglist".string(qarglist)." iarg=".iarg." args<".args.">")
|
967
|
+
endwhile
|
968
|
+
|
969
|
+
else
|
970
|
+
" split at all whitespace
|
971
|
+
let qarglist= split(a:qarg)
|
972
|
+
endif
|
973
|
+
|
974
|
+
let qarglistlen= len(qarglist)
|
975
|
+
let qarglist = insert(qarglist,qarglistlen)
|
976
|
+
" call Dret("s:QArgSplitter ".string(qarglist))
|
977
|
+
return qarglist
|
978
|
+
endfun
|
979
|
+
|
980
|
+
" ---------------------------------------------------------------------
|
981
|
+
" s:Strlen: this function returns the length of a string, even if its {{{1
|
982
|
+
" using two-byte etc characters.
|
983
|
+
" Currently, its only used if g:Align_xstrlen is set to a
|
984
|
+
" nonzero value. Solution from Nicolai Weibull, vim docs
|
985
|
+
" (:help strlen()), Tony Mechelynck, and my own invention.
|
986
|
+
fun! s:Strlen(x)
|
987
|
+
" call Dfunc("s:Strlen(x<".a:x.">")
|
988
|
+
if g:Align_xstrlen == 1
|
989
|
+
" number of codepoints (Latin a + combining circumflex is two codepoints)
|
990
|
+
" (comment from TM, solution from NW)
|
991
|
+
let ret= strlen(substitute(a:x,'.','c','g'))
|
992
|
+
|
993
|
+
elseif g:Align_xstrlen == 2
|
994
|
+
" number of spacing codepoints (Latin a + combining circumflex is one spacing
|
995
|
+
" codepoint; a hard tab is one; wide and narrow CJK are one each; etc.)
|
996
|
+
" (comment from TM, solution from TM)
|
997
|
+
let ret=strlen(substitute(a:x, '.\Z', 'x', 'g'))
|
998
|
+
|
999
|
+
elseif g:Align_xstrlen == 3
|
1000
|
+
" virtual length (counting, for instance, tabs as anything between 1 and
|
1001
|
+
" 'tabstop', wide CJK as 2 rather than 1, Arabic alif as zero when immediately
|
1002
|
+
" preceded by lam, one otherwise, etc.)
|
1003
|
+
" (comment from TM, solution from me)
|
1004
|
+
let modkeep= &l:mod
|
1005
|
+
exe "norm! o\<esc>"
|
1006
|
+
call setline(line("."),a:x)
|
1007
|
+
let ret= virtcol("$") - 1
|
1008
|
+
d
|
1009
|
+
let &l:mod= modkeep
|
1010
|
+
|
1011
|
+
else
|
1012
|
+
" at least give a decent default
|
1013
|
+
ret= strlen(a:x)
|
1014
|
+
endif
|
1015
|
+
" call Dret("s:Strlen ".ret)
|
1016
|
+
return ret
|
1017
|
+
endfun
|
1018
|
+
|
1019
|
+
" ---------------------------------------------------------------------
|
1020
|
+
" Set up default values: {{{1
|
1021
|
+
"call Decho("-- Begin AlignCtrl Initialization --")
|
1022
|
+
call Align#AlignCtrl("default")
|
1023
|
+
"call Decho("-- End AlignCtrl Initialization --")
|
1024
|
+
|
1025
|
+
" ---------------------------------------------------------------------
|
1026
|
+
" Restore: {{{1
|
1027
|
+
let &cpo= s:keepcpo
|
1028
|
+
unlet s:keepcpo
|
1029
|
+
" vim: ts=4 fdm=marker
|