forked from preservim/vimux
/
vimux.vim
209 lines (174 loc) · 5.09 KB
/
vimux.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
if exists("g:loaded_vimux") || &cp
finish
endif
let g:loaded_vimux = 1
if !has("ruby")
finish
end
command RunLastVimTmuxCommand :call RunLastVimTmuxCommand()
command CloseVimTmuxPanes :call CloseVimTmuxPanes()
command CloseVimTmuxWindows :call CloseVimTmuxWindows()
command InspectVimTmuxRunner :call InspectVimTmuxRunner()
command InterruptVimTmuxRunner :call InterruptVimTmuxRunner()
command PromptVimTmuxCommand :call PromptVimTmuxCommand()
function RunVimTmuxCommand(command)
let g:_VimTmuxCmd = a:command
ruby CurrentTmuxSession.new.run_shell_command(Vim.evaluate("g:_VimTmuxCmd"))
endfunction
function RunLastVimTmuxCommand()
if exists("g:_VimTmuxCmd")
ruby CurrentTmuxSession.new.run_shell_command(Vim.evaluate("g:_VimTmuxCmd"))
else
echo "No last command"
endif
endfunction
function ClearVimTmuxWindow()
if exists("g:_VimTmuxRunnerPane")
unlet g:_VimTmuxRunnerPane
end
endfunction
function CloseVimTmuxWindows()
ruby CurrentTmuxSession.new.close_other_panes
call ClearVimTmuxWindow()
echoerr "CloseVimTmuxWindows is deprecated, use CloseVimTmuxPanes"
endfunction
function CloseVimTmuxPanes()
ruby CurrentTmuxSession.new.close_other_panes
call ClearVimTmuxWindow()
endfunction
function InterruptVimTmuxRunner()
ruby CurrentTmuxSession.new.interrupt_runner
endfunction
function InspectVimTmuxRunner()
ruby CurrentTmuxSession.new.inspect_runner
endfunction
function PromptVimTmuxCommand()
let l:command = input("Command? ")
call RunVimTmuxCommand(l:command)
endfunction
ruby << EOF
class TmuxSession
def initialize(session, window, pane)
@session = session
@window = window
@pane = pane
@runner_pane = vim_cached_runner_pane
end
def vim_cached_runner_pane
if Vim.evaluate('exists("g:_VimTmuxRunnerPane")') != 0
Vim.evaluate('g:_VimTmuxRunnerPane')
else
nil
end
end
def vim_cached_runner_pane=(runner_pane)
Vim.command("let g:_VimTmuxRunnerPane = '#{runner_pane}'")
end
def clear_vim_cached_runner_pane
Vim.command("unlet g:_VimTmuxRunnerPane")
end
def height
if Vim.evaluate('exists("g:VimuxHeight")') != 0
Vim.evaluate('g:VimuxHeight')
else
20
end
end
def orientation
if Vim.evaluate('exists("g:VimuxOrientation")') != 0 && ["h", "v"].include?(Vim.evaluate('g:VimuxOrientation'))
"-#{Vim.evaluate('g:VimuxOrientation')}"
else
"-v"
end
end
def inspect_runner
_run("select-pane -t #{target(:pane => runner_pane)}")
_run("copy-mode")
Vim.command("let g:_VimTmuxInspecting = 1")
end
def stop_inspecting_runner
if Vim.evaluate('exists("g:_VimTmuxInspecting")') != 0
_run("send-keys -t #{target(:pane => runner_pane)} q")
Vim.command("unlet g:_VimTmuxInspecting")
end
end
def current_panes
_run('list-panes').split("\n").map do |line|
line.split(':').first
end
end
def active_pane_id
_run('list-panes').split("\n").map do |line|
return line.split[-2] if line =~ /\(active\)/
end
end
def target(args={})
"#{args.fetch(:session, @session)}:#{args.fetch(:window, @window)}.#{args.fetch(:pane, @pane)}"
end
def runner_pane
if @runner_pane.nil?
type = Vim.evaluate('exists("g:_VimTmuxInspecting")') != 0
use_nearest_pane = Vim.evaluate('exists("g:VimuxUseNearestPane")') != 0
if use_nearest_pane && nearest_inactive_pane_id
_run("select-pane -t #{target(:pane => nearest_inactive_pane_id)}")
else
_run("split-window -p #{height} #{orientation}")
end
@runner_pane = active_pane_id
Vim.command("let g:_VimTmuxRunnerPane = '#{@runner_pane}'")
end
_run('list-panes').split("\n").map do |line|
return line.split(':').first if line =~ /#{@runner_pane}/
end
@runner_pane = nil
clear_vim_cached_runner_pane
runner_pane
end
def interrupt_runner
stop_inspecting_runner
_run("send-keys -t #{target(:pane => runner_pane)} ^c")
end
def run_shell_command(command)
stop_inspecting_runner
_send_command(command, target(:pane => runner_pane))
_move_up_pane
end
def close_other_panes
stop_inspecting_runner
if _run("list-panes").split("\n").length > 1
_run("kill-pane -a")
end
end
def nearest_inactive_pane_id
panes = _run("list-pane").split("\n")
pane = panes.find { |p| p !~ /active/ }
pane ? pane.split(':').first : nil
end
def _move_up_pane
_run("select-pane -t #{target}")
end
def _send_command(command, target)
_run("send-keys -t #{target} '#{command.gsub("'", "\'")}'")
_run("send-keys -t #{target} Enter")
end
def _run(command)
`tmux #{command}`
end
end
class CurrentTmuxSession < TmuxSession
def initialize
session = self.get_session
window = self.get_property(:active, :window)
pane = self.get_property(:active, :pane)
super(session, window, pane)
end
def get_property(match, type)
_run("list-#{type.to_s}").split("\n").each do |line|
return line.split(':').first if line =~ /\(#{match.to_s}\)/
end
end
def get_session
_run("list-panes -F '\#\{session_name\}'").split("\n").first.strip
end
end
EOF