-
Notifications
You must be signed in to change notification settings - Fork 0
/
ZoomWin.vim
380 lines (338 loc) · 10.8 KB
/
ZoomWin.vim
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343
344
345
346
347
348
349
350
351
352
353
354
355
356
357
358
359
360
361
362
363
364
365
366
367
368
369
370
371
372
373
374
375
376
377
378
379
380
" ZoomWin: Brief-like ability to zoom into/out-of a window
" Author: Charles Campbell
" original version by Ron Aaron
" Date: Jan 26, 2009
" Version: 23
" History: see :help zoomwin-history {{{1
" GetLatestVimScripts: 508 1 :AutoInstall: ZoomWin.vim
" ---------------------------------------------------------------------
" Load Once: {{{1
if &cp || exists("g:loaded_ZoomWin")
finish
endif
if v:version < 702
echohl WarningMsg
echo "***warning*** this version of ZoomWin needs vim 7.2"
echohl Normal
finish
endif
let s:keepcpo = &cpo
let g:loaded_ZoomWin = "v23"
set cpo&vim
"DechoTabOn
" =====================================================================
" Functions: {{{1
" ---------------------------------------------------------------------
" ZoomWin#ZoomWin: toggles between a single-window and a multi-window layout {{{2
" The original version was by Ron Aaron.
fun! ZoomWin#ZoomWin()
" let g:decho_hide= 1 "Decho
" call Dfunc("ZoomWin#ZoomWin() winbufnr(2)=".winbufnr(2))
" if the vim doesn't have +mksession, only a partial zoom is available {{{3
if !has("mksession")
if !exists("s:partialzoom")
echomsg "missing the +mksession feature; only a partial zoom is available"
let s:partialzoom= 0
endif
if v:version < 630
echoerr "***sorry*** you need an updated vim, preferably with +mksession"
elseif s:partialzoom
" partial zoom out
let s:partialzoom= 0
exe s:winrestore
else
" partial zoom in
let s:partialzoom= 1
let s:winrestore = winrestcmd()
res
endif
" call Dret("ZoomWin#ZoomWin : partialzoom=".s:partialzoom)
return
endif
" Close certain windows {{{3
call s:ZoomWinPreserve(0)
" save options. Force window minimum height/width to be >= 1 {{{3
let keep_hidden = &hidden
let keep_write = &write
if v:version < 603
if &wmh == 0 || &wmw == 0
let keep_wmh = &wmh
let keep_wmw = &wmw
silent! set wmh=1 wmw=1
endif
endif
set hidden write
if winbufnr(2) == -1
" there's only one window - restore to multiple-windows mode {{{3
" call Decho("there's only one window - restore to multiple windows")
if exists("s:sessionfile") && filereadable(s:sessionfile)
" save position in current one-window-only
" call Decho("save position in current one-window-only in sponly")
let sponly = s:SavePosn(0)
let s:origline = line(".")
let s:origcol = virtcol(".")
" source session file to restore window layout
let ei_keep= &ei
set ei=all
exe 'silent! so '.fnameescape(s:sessionfile)
" Decho("@@<".@@.">")
let v:this_session= s:sesskeep
if exists("s:savedposn1")
" restore windows' positioning and buffers
" call Decho("restore windows, positions, buffers")
windo call s:RestorePosn(s:savedposn{winnr()})|unlet s:savedposn{winnr()}
call s:GotoWinNum(s:winkeep)
unlet s:winkeep
endif
if line(".") != s:origline || virtcol(".") != s:origcol
" If the cursor hasn't moved from the original position,
" then let the position remain what it was in the original
" multi-window layout.
" call Decho("restore position using sponly")
call s:RestorePosn(sponly)
endif
" delete session file and variable holding its name
" call Decho("delete session file")
call delete(s:sessionfile)
unlet s:sessionfile
let &ei=ei_keep
endif
else " there's more than one window - go to only-one-window mode {{{3
" call Decho("there's multiple windows - goto one-window-only")
let s:winkeep = winnr()
let s:sesskeep = v:this_session
" doesn't work with the command line window (normal mode q:)
if &bt == "nofile" && expand("%") == (v:version < 702 ? 'command-line' : '[Command Line]')
echoerr "***error*** ZoomWin#ZoomWin doesn't work with the ".expand("%")." window"
" call Dret("ZoomWin#ZoomWin : ".expand('%')." window error")
return
endif
" call Decho("1: @@<".@@.">")
" disable all events (autocmds)
" call Decho("disable events")
let ei_keep= &ei
set ei=all
" call Decho("2: @@<".@@.">")
" save window positioning commands
" call Decho("save window positioning commands")
windo let s:savedposn{winnr()}= s:SavePosn(1)
call s:GotoWinNum(s:winkeep)
" set up name of session file
" call Decho("3: @@<".@@.">")
let s:sessionfile= tempname()
" call Decho("4: @@<".@@.">")
" save session
" call Decho("save session")
let ssop_keep = &ssop
let &ssop = 'blank,help,winsize,folds,globals,localoptions,options'
" call Decho("5: @@<".@@.">")
exe 'mksession! '.fnameescape(s:sessionfile)
" call Decho("6: @@<".@@.">")
let keepyy= @@
let keepy0= @0
let keepy1= @1
let keepy2= @2
let keepy3= @3
let keepy4= @4
let keepy5= @5
let keepy6= @6
let keepy7= @7
let keepy8= @8
let keepy9= @9
set lz ei=all bh=
if v:version >= 700
try
exe "keepalt keepmarks new! ".fnameescape(s:sessionfile)
catch /^Vim\%((\a\+)\)\=:E/
echoerr "Too many windows"
silent! call delete(s:sessionfile)
unlet s:sessionfile
" call Dret("ZoomWin#ZoomWin : too many windows")
return
endtry
silent! keepjumps keepmarks v/wincmd\|split\|resize/d
keepalt w!
keepalt bw!
else
exe "new! ".fnameescape(s:sessionfile)
v/wincmd\|split\|resize/d
w!
bw!
endif
let @@= keepyy
let @0= keepy0
let @1= keepy1
let @2= keepy2
let @3= keepy3
let @4= keepy4
let @5= keepy5
let @6= keepy6
let @7= keepy7
let @8= keepy8
let @9= keepy9
call histdel('search', -1)
let @/ = histget('search', -1)
" call Decho("7: @@<".@@.">")
" restore user's session options and restore event handling
" call Decho("restore user session options and event handling")
set nolz
let &ssop = ssop_keep
silent! only!
" call Decho("8: @@<".@@.">")
let &ei = ei_keep
echomsg expand("%")
" call Decho("9: @@<".@@.">")
endif
" restore user option settings {{{3
" call Decho("restore user option settings")
let &hidden= keep_hidden
let &write = keep_write
if v:version < 603
if exists("keep_wmw")
let &wmh= keep_wmh
let &wmw= keep_wmw
endif
endif
" Re-open certain windows {{{3
call s:ZoomWinPreserve(1)
" call Dret("ZoomWin#ZoomWin")
endfun
" ---------------------------------------------------------------------
" SavePosn: this function sets up a savedposn variable that {{{2
" has the commands necessary to restore the view
" of the current window.
fun! s:SavePosn(savewinhoriz)
" call Dfunc("SavePosn(savewinhoriz=".a:savewinhoriz.") file<".expand("%").">")
let swline = line(".")
if swline == 1 && getline(1) == ""
" empty buffer
let savedposn= "silent b ".winbufnr(0)
" call Dret("SavePosn savedposn<".savedposn.">")
return savedposn
endif
let swcol = col(".")
let swwline = winline()-1
let swwcol = virtcol(".") - wincol()
let savedposn = "silent b ".winbufnr(0)."|".swline."|silent norm! z\<cr>"
if swwline > 0
let savedposn= savedposn.":silent norm! ".swwline."\<c-y>\<cr>:silent norm! zs\<cr>"
endif
let savedposn= savedposn.":silent call cursor(".swline.",".swcol.")\<cr>"
if a:savewinhoriz
if swwcol > 0
let savedposn= savedposn.":silent norm! ".swwcol."zl\<cr>"
endif
" handle certain special settings for the multi-window savedposn call
" bufhidden buftype buflisted
let settings= ""
if &bh != ""
let settings="bh=".&bh
setlocal bh=hide
endif
if !&bl
let settings= settings." nobl"
setlocal bl
endif
if &bt != ""
let settings= settings." bt=".&bt
setlocal bt=
endif
if settings != ""
let savedposn= savedposn.":setlocal ".settings."\<cr>"
endif
endif
" call Dret("SavePosn savedposn<".savedposn.">")
return savedposn
endfun
" ---------------------------------------------------------------------
" s:RestorePosn: this function restores noname and scratch windows {{{2
fun! s:RestorePosn(savedposn)
" call Dfunc("RestorePosn(savedposn<".a:savedposn.">) file<".expand("%").">")
if &scb
setlocal noscb
exe a:savedposn
setlocal scb
else
exe a:savedposn
endif
" call Dret("RestorePosn")
endfun
" ---------------------------------------------------------------------
" CleanupSessionFile: if you exit Vim before cleaning up the {{{2
" supposed-to-be temporary session file
fun! ZoomWin#CleanupSessionFile()
" call Dfunc("ZoomWin#CleanupSessionFile()")
if exists("s:sessionfile") && filereadable(s:sessionfile)
" call Decho("sessionfile exists and is readable; deleting it")
silent! call delete(s:sessionfile)
unlet s:sessionfile
endif
" call Dret("ZoomWin#CleanupSessionFile")
endfun
" ---------------------------------------------------------------------
" GotoWinNum: this function puts cursor into specified window {{{2
fun! s:GotoWinNum(winnum)
" call Dfunc("GotoWinNum(winnum=".a:winnum.") winnr=".winnr())
if a:winnum != winnr()
exe a:winnum."wincmd w"
endif
" call Dret("GotoWinNum")
endfun
" ---------------------------------------------------------------------
" ZoomWinPreserve: This function, largely written by David Fishburn, {{{2
" allows ZoomWin to "preserve" certain windows:
"
" TagList, by Yegappan Lakshmanan
" http://vim.sourceforge.net/scripts/script.php?script_id=273
"
" WinManager, by Srinath Avadhanula
" http://vim.sourceforge.net/scripts/script.php?script_id=95
"
" It does so by closing the associated window upon entry to ZoomWin
" and re-opening it upon exit by using commands provided by the
" utilities themselves.
fun! s:ZoomWinPreserve(open)
" call Dfunc("ZoomWinPreserve(open=".a:open.")")
if a:open == 0
" Close Taglist
if exists('g:zoomwin_preserve_taglist') && exists('g:loaded_taglist')
" If taglist window is open then close it.
let s:taglist_winnum = bufwinnr(g:TagList_title)
if s:taglist_winnum != -1
" Close the window
exec "silent! Tlist"
endif
endif
" Close Winmanager
if exists('g:zoomwin_preserve_winmanager') && exists('g:loaded_winmanager')
" If the winmanager window is open then close it.
let s:is_winmgr_vis = IsWinManagerVisible()
if s:is_winmgr_vis == 1
exec "WMClose"
endif
endif
else
" Re-open Taglist
if exists('g:zoomwin_preserve_taglist') && exists('g:loaded_taglist')
" If taglist window was open, open it again
if s:taglist_winnum != -1
exec "silent! Tlist"
endif
endif
" Re-Open Winmanager
if exists('g:zoomwin_preserve_winmanager') && exists('g:loaded_winmanager')
" If the winmanager window is open then close it.
if s:is_winmgr_vis == 1
exec "WManager"
endif
endif
endif
" call Dret("ZoomWinPreserve")
endfun
" =====================================================================
" Restore: {{{1
let &cpo= s:keepcpo
unlet s:keepcpo
" ---------------------------------------------------------------------
" Modelines: {{{1
" vim: ts=4 fdm=marker