vimamsa 0.1.0 → 0.1.5

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -0,0 +1,207 @@
1
+
2
+ def save_buffer_list()
3
+ message("Save buffer list")
4
+ buffn = get_dot_path("buffers.txt")
5
+ f = File.open(buffn, "w")
6
+ bufstr = $buffers.collect { |buf| buf.fname }.inspect
7
+ f.write(bufstr)
8
+ f.close()
9
+ end
10
+
11
+ def load_buffer_list()
12
+ message("Load buffer list")
13
+ buffn = get_dot_path("buffers.txt")
14
+ return if !File.exist?(buffn)
15
+ bufstr = IO.read(buffn)
16
+ bufl = eval(bufstr)
17
+ debug bufl
18
+ for b in bufl
19
+ load_buffer(b) if b != nil and File.file?(b)
20
+ end
21
+ end
22
+
23
+ class BufferList < Array
24
+ attr_reader :current_buf
25
+
26
+ def <<(_buf)
27
+ super
28
+ $buffer = _buf
29
+ @current_buf = self.size - 1
30
+ $buffer_history << @current_buf
31
+ @recent_ind = 0
32
+ $hook.call(:change_buffer, $buffer)
33
+ qt_set_current_buffer($buffer.id)
34
+ qt_set_cursor_pos($buffer.id, $buffer.pos)
35
+ end
36
+
37
+ def switch()
38
+ debug "SWITCH BUF. bufsize:#{self.size}, curbuf: #{@current_buf}"
39
+ @current_buf += 1
40
+ @current_buf = 0 if @current_buf >= self.size
41
+ m = method("switch")
42
+ set_last_command({ method: m, params: [] })
43
+ set_current_buffer(@current_buf)
44
+ end
45
+
46
+ def switch_to_last_buf()
47
+ debug "SWITCH TO LAST BUF:"
48
+ debug $buffer_history
49
+ last_buf = $buffer_history[-2]
50
+ if last_buf
51
+ set_current_buffer(last_buf)
52
+ end
53
+ end
54
+
55
+ def get_buffer_by_filename(fname)
56
+ #TODO: check using stat/inode? http://ruby-doc.org/core-1.9.3/File/Stat.html#method-i-ino
57
+ buf_idx = self.index { |b| b.fname == fname }
58
+ return buf_idx
59
+ end
60
+
61
+ def add_current_buf_to_history()
62
+ @recent_ind = 0
63
+ $buffer_history << @current_buf
64
+ compact_buf_history()
65
+ end
66
+
67
+ def set_current_buffer(buffer_i, update_history = true)
68
+ buffer_i = self.size -1 if buffer_i > self.size
69
+ buffer_i = 0 if buffer_i < 0
70
+ $buffer = self[buffer_i]
71
+ return if !$buffer
72
+ @current_buf = buffer_i
73
+ debug "SWITCH BUF2. bufsize:#{self.size}, curbuf: #{@current_buf}"
74
+ fpath = $buffer.fname
75
+ if fpath and fpath.size > 50
76
+ fpath = fpath[-50..-1]
77
+ end
78
+
79
+ if update_history
80
+ add_current_buf_to_history
81
+ end
82
+
83
+ $hook.call(:change_buffer, $buffer)
84
+ $buffer.set_active
85
+
86
+ qt_set_current_buffer($buffer.id)
87
+ gui_set_window_title($buffer.title,$buffer.subtitle)
88
+
89
+ # hpt_scan_images() if $debug # experimental
90
+ end
91
+
92
+ def get_last_dir
93
+ lastdir = nil
94
+ if $buffer.fname
95
+ lastdir = File.dirname($buffer.fname)
96
+ else
97
+ for bufid in $buffer_history.reverse[1..-1]
98
+ bf = $buffers[bufid]
99
+ debug "FNAME:#{bf.fname}"
100
+ if bf.fname
101
+ lastdir = File.dirname(bf.fname)
102
+ break
103
+ end
104
+ end
105
+ end
106
+ lastdir = File.expand_path(".") if lastdir.nil?
107
+ return lastdir
108
+ end
109
+
110
+ def get_recent_buffers()
111
+ bufs = []; b = {}
112
+ $buffer_history.reverse.each { |x| bufs << x if !b[x] && x < self.size; b[x] = true }
113
+ return bufs
114
+ end
115
+
116
+ def history_switch_backwards()
117
+ recent = get_recent_buffers()
118
+ @recent_ind += 1
119
+ @recent_ind = 0 if @recent_ind >= recent.size
120
+ bufid = recent[@recent_ind]
121
+ debug "IND:#{@recent_ind} RECENT:#{recent.join(" ")}"
122
+ set_current_buffer(bufid, false)
123
+ end
124
+
125
+ def history_switch_forwards()
126
+ recent = get_recent_buffers()
127
+ @recent_ind -= 1
128
+ @recent_ind = self.size - 1 if @recent_ind < 0
129
+ bufid = recent[@recent_ind]
130
+ debug "IND:#{@recent_ind} RECENT:#{recent.join(" ")}"
131
+ set_current_buffer(bufid, false)
132
+ end
133
+
134
+ def compact_buf_history()
135
+ h = {}
136
+ # Keep only first occurence in history
137
+ bh = $buffer_history.reverse.select { |x| r = h[x] == nil; h[x] = true; r }
138
+ $buffer_history = bh.reverse
139
+ end
140
+
141
+ def close_buffer(buffer_i, from_recent = false)
142
+ return if self.size <= buffer_i
143
+
144
+ bufname = self[buffer_i].basename
145
+ message("Closed buffer #{bufname}")
146
+ recent = get_recent_buffers
147
+ jump_to_buf = recent[@recent_ind + 1]
148
+ jump_to_buf = 0 if jump_to_buf == nil
149
+
150
+ self.slice!(buffer_i)
151
+ $buffer_history = $buffer_history.collect { |x| r = x; r = x - 1 if x > buffer_i; r = nil if x == buffer_i; r }.compact
152
+
153
+ if @current_buf == buffer_i
154
+ if from_recent
155
+ @current_buf = jump_to_buf
156
+ else
157
+ @current_buf = $buffer_history.last
158
+ end
159
+ end
160
+ # Ripl.start :binding => binding
161
+ if self.size == 0
162
+ self << Buffer.new("\n")
163
+ @current_buf = 0
164
+ else
165
+ @current_buf = 0 if @current_buf >= self.size
166
+ end
167
+ set_current_buffer(@current_buf, false)
168
+ end
169
+
170
+ def close_all_buffers()
171
+ message("Closing all buffers")
172
+ while true
173
+ if self.size == 1
174
+ close_buffer(0)
175
+ break
176
+ else
177
+ close_buffer(0)
178
+ end
179
+ end
180
+ # self << Buffer.new("\n")
181
+ end
182
+
183
+ def close_scrap_buffers()
184
+ i = 0
185
+ while i < self.size
186
+ if !self[i].pathname
187
+ close_buffer(i)
188
+ else
189
+ i += 1
190
+ end
191
+ end
192
+ end
193
+
194
+ def close_current_buffer(from_recent = false)
195
+ close_buffer(@current_buf, from_recent)
196
+ end
197
+
198
+ def delete_current_buffer(from_recent = false)
199
+ fn = buf.fname
200
+ close_buffer(@current_buf, from_recent)
201
+ #TODO: confirm with user, "Do you want to delete file X"
202
+ if is_existing_file(fn)
203
+ message("Deleting file: #{fn}")
204
+ File.delete(fn)
205
+ end
206
+ end
207
+ end
@@ -0,0 +1,44 @@
1
+
2
+ NEXT_MARK = 1001
3
+ PREVIOUS_MARK = 1002
4
+ BACKWARD = 1003
5
+ FORWARD = 1004
6
+ BEFORE = 1005
7
+ AFTER = 1006
8
+ SELECTION = 1007
9
+
10
+ FORWARD_CHAR = 2001
11
+ BACKWARD_CHAR = 2002
12
+ FORWARD_LINE = 2003
13
+ BACKWARD_LINE = 2004
14
+ CURRENT_CHAR_FORWARD = 2005
15
+ CURRENT_CHAR_BACKWARD = 2006
16
+ START_OF_BUFFER = 2007
17
+ END_OF_BUFFER = 2008
18
+ BACKWARD = 2009
19
+ FORWARD = 2010
20
+ END_OF_LINE = 2011
21
+ BEGINNING_OF_LINE = 2012
22
+ WORD_START = 2013
23
+ WORD_END = 2014
24
+ FIRST_NON_WHITESPACE = 2014
25
+
26
+ INSERT = 2
27
+ DELETE = 3001
28
+ REPLACE = 3002
29
+
30
+ KEY_PRESS = 6
31
+ KEY_RELEASE = 7 # QEvent::KeyRelease
32
+
33
+ # http://qt-project.org/doc/qt-5.0/qtcore/qt.html#KeyboardModifier-enum
34
+ ALTMODIFIER = 0x08000000
35
+ NOMODIFIER = 0x00000000 # No modifier key is pressed.
36
+ SHIFTMODIFIER = 0x02000000 # A Shift key on the keyboard is pressed.
37
+ CONTROLMODIFIER = 0x04000000 # A Ctrl key on the keyboard is pressed.
38
+ ALTMODIFIER = 0x08000000 # An Alt key on the keyboard is pressed.
39
+ METAMODIFIER = 0x10000000 # A Meta key on the keyboard is pressed.
40
+ KEYPADMODIFIER = 0x20000000 # A keypad button is pressed.
41
+
42
+
43
+
44
+
@@ -0,0 +1,142 @@
1
+ require "fileutils"
2
+
3
+ def debug(message)
4
+ if $debug
5
+ puts "[#{DateTime.now().strftime("%H:%M:%S")}] #{message}"
6
+ $stdout.flush
7
+ end
8
+ end
9
+
10
+ def debug_print_buffer(c)
11
+ puts buf.inspect
12
+ puts buf
13
+ end
14
+
15
+ def debug_dump_clipboard()
16
+ puts $clipboard.inspect
17
+ end
18
+
19
+ def debug_dump_deltas()
20
+ puts buf.edit_history.inspect
21
+ end
22
+
23
+ $log_messages = []
24
+ def log_message(message)
25
+ puts message
26
+ $log_messages << message
27
+ end
28
+
29
+ def log_error(message)
30
+ puts "====== ERROR ====="
31
+ puts caller[0]
32
+ puts message
33
+ puts "=================="
34
+ $errors << [message, caller]
35
+ #TODO
36
+ end
37
+
38
+ def crash(message, e = nil)
39
+ puts "FATAL ERROR:#{message}"
40
+ puts caller().join("\n")
41
+ # savedebug(message, e)
42
+ _quit()
43
+ end
44
+
45
+ def savedebug(message, e)
46
+ FileUtils.mkdir_p("debug")
47
+ puts "savedebug()"
48
+ dbginfo = {}
49
+ dbginfo["message"] = message
50
+ dbginfo["debuginfo"] = $debuginfo
51
+ dbginfo["trace"] = caller()
52
+ dbginfo["trace"] = e.backtrace() if e
53
+ dbginfo["trace_str"] = dbginfo["trace"].join("\n")
54
+ dbginfo["edit_history"] = buf.edit_history
55
+ dbginfo["cnf"] = $cnf
56
+ dbginfo["register"] = $register
57
+ dbginfo["clipboard"] = $clipboard
58
+ # dbginfo["last_event"] = $last_event
59
+ dbginfo["buffer"] = {}
60
+ dbginfo["buffer"]["str"] = buf.to_s
61
+ dbginfo["buffer"]["lpos"] = buf.lpos
62
+ dbginfo["buffer"]["cpos"] = buf.cpos
63
+ dbginfo["buffer"]["pos"] = buf.pos
64
+
65
+ pfxs = DateTime.now().strftime("%d%m%Y_%H%M%S")
66
+ save_fn_dump = sprintf("debug/crash_%s.marshal", pfxs)
67
+ save_fn_json = sprintf("debug/crash_%s.json", pfxs)
68
+ mdump = Marshal.dump(dbginfo)
69
+ IO.binwrite(save_fn_dump, mdump)
70
+ IO.write(save_fn_json, dbginfo.to_json)
71
+ puts "SAVED CRASH INFO TO:"
72
+ puts save_fn_dump
73
+ puts save_fn_json
74
+ end
75
+
76
+ def run_tests()
77
+ run_test("01")
78
+ run_test("02")
79
+ end
80
+
81
+ def run_test(test_id)
82
+ target_results = read_file("", "tests/test_#{test_id}_output.txt")
83
+ old_buffer = $buffer
84
+ $buffer = Buffer.new("", "")
85
+ load "tests/test_#{test_id}.rb"
86
+ test_ok = $buffer.to_s.strip == target_results.strip
87
+ puts "##################"
88
+ puts target_results
89
+ puts "##################"
90
+ puts $buffer.to_s
91
+ puts "##################"
92
+ puts "TEST OK" if test_ok
93
+ puts "TEST FAILED" if !test_ok
94
+ puts "##################"
95
+ $buffer = old_buffer
96
+ end
97
+
98
+ def qt_sleep(t2)
99
+ t1 = Time.now()
100
+ while Time.now < t1 + t2
101
+ qt_process_events
102
+ sleep(0.02)
103
+ end
104
+ end
105
+
106
+ def run_random_jump_test__tmpl(test_time = 60 * 60 * 10)
107
+ open_new_file("TODO"); qt_sleep(0.1)
108
+
109
+ ttstart = Time.now
110
+ Kernel.srand(1231)
111
+ step = 0
112
+ while Time.now < ttstart + test_time
113
+ debug "step=#{step}"
114
+ buf.jump_to_random_pos
115
+ buf.insert_txt("Z") if rand() > 0.25
116
+ buf.reset_highlight() if rand() > 0.1
117
+ qt_trigger_event
118
+
119
+ # puts "========line:========="
120
+ # puts buf.current_line()
121
+ # puts "======================"
122
+
123
+ render_buffer($buffer)
124
+
125
+ qt_sleep(rand() / 2)
126
+ if rand() < (1 / 40.0)
127
+ buf.revert
128
+ end
129
+
130
+ qt_trigger_event
131
+ buf.insert_txt("X") if rand() > 0.25
132
+ render_buffer($buffer)
133
+
134
+ $buffers.set_current_buffer(rand($buffers.size)) if rand > 0.25
135
+ step += 1
136
+ end
137
+ end
138
+
139
+
140
+ def start_ripl
141
+ Ripl.start :binding => binding
142
+ end
@@ -0,0 +1,448 @@
1
+
2
+ def e_move_forward_char
3
+ buf.move(FORWARD_CHAR)
4
+ end
5
+
6
+ def e_move_backward_char
7
+ buf.move(BACKWARD_CHAR)
8
+ end
9
+
10
+ def history_switch_backwards
11
+ bufs.history_switch_backwards
12
+ end
13
+
14
+ def history_switch_forwards
15
+ bufs.history_switch_forwards
16
+ end
17
+
18
+ def jump_to_next_edit
19
+ buf.jump_to_next_edit
20
+ end
21
+
22
+ def is_command_mode()
23
+ return true if $kbd.mode_root_state.to_s() == "C"
24
+ return false
25
+ end
26
+
27
+ def is_visual_mode()
28
+ return 1 if $kbd.mode_root_state.to_s() == "V"
29
+ return 0
30
+ end
31
+
32
+ reg_act(:easy_jump, proc { easy_jump(:visible_area) }, "Easy jump")
33
+ bindkey "VC s", :easy_jump
34
+
35
+ reg_act(:savedebug, "savedebug", "Save debug info")
36
+
37
+ # reg_act(:file_finder, "gui_file_finder", "Fuzzy file finder")
38
+
39
+ reg_act(:open_file_dialog, "open_file_dialog", "Open file")
40
+ reg_act(:create_new_file, "create_new_file", "Create new file")
41
+ reg_act(:backup_all_buffers, "backup_all_buffers", "Backup all buffers")
42
+ reg_act(:invoke_ack_search, "invoke_ack_search", "Invoke ack search")
43
+ reg_act(:e_move_forward_char, "e_move_forward_char", "")
44
+ reg_act(:e_move_backward_char, "e_move_backward_char", "")
45
+ reg_act(:history_switch_backwards, "history_switch_backwards", "")
46
+ reg_act(:history_switch_forwards, "history_switch_forwards", "")
47
+
48
+ reg_act(:center_on_current_line, "center_on_current_line", "")
49
+
50
+ # a = Action.new(:transform_upcase, "Transform selection upcase", proc{ buf.transform_selection(:upcase) } , [:selection])
51
+
52
+ reg_act(:run_last_macro, proc { $macro.run_last_macro }, "Run last recorded or executed macro")
53
+ bindkey ["VCB M","B m"], :run_last_macro
54
+
55
+ bindkey "VC , m f", [:find_macro_gui, proc{$macro.find_macro_gui}, "Find named macro"]
56
+ bindkey "C , m n", [:gui_name_macro, proc{$macro.gui_name_macro}, "Name last macro"]
57
+
58
+
59
+ reg_act(:jump_to_next_edit, "jump_to_next_edit", "")
60
+ reg_act(:jump_to_last_edit, proc { buf.jump_to_last_edit }, "")
61
+
62
+
63
+ reg_act(:jump_to_random, proc { buf.jump_to_random_pos }, "")
64
+ bindkey "C , j r", :jump_to_random
65
+
66
+ reg_act(:insert_new_line, proc { buf.insert_new_line()}, "")
67
+ bindkey "I enter", :insert_new_line
68
+
69
+ reg_act(:show_key_bindings, proc { show_key_bindings }, "Show key bindings")
70
+ bindkey "C , ; s k", :show_key_bindings #TODO: better binding
71
+
72
+ reg_act(:put_file_path_to_clipboard, proc { buf.put_file_path_to_clipboard }, "Put file path of current file to clipboard")
73
+ bindkey "C , , c b", :put_file_path_to_clipboard #TODO: better binding or remove?
74
+
75
+ # reg_act(:encrypt_file, proc{buf.set_encrypted},"Set current file to encrypt on save")
76
+ reg_act(:encrypt_file, proc { encrypt_cur_buffer }, "Set current file to encrypt on save")
77
+ bindkey "C , , e", :encrypt_file #TODO: better binding
78
+
79
+ reg_act(:set_unencrypted, proc { buf.set_unencrypted }, "Set current file to save unencrypted")
80
+ bindkey "C , ; u", :set_unencrypted #TODO: better binding
81
+
82
+ reg_act(:close_all_buffers, proc { bufs.close_all_buffers() }, "Close all buffers")
83
+
84
+ reg_act(:close_current_buffer, proc { bufs.close_current_buffer(true) }, "Close current buffer")
85
+ bindkey "C , c b", :close_current_buffer
86
+
87
+ reg_act(:comment_selection, proc { buf.comment_selection }, "")
88
+ bindkey "V ctrl-c", :comment_selection
89
+
90
+ reg_act(:delete_char_forward, proc { buf.delete(CURRENT_CHAR_FORWARD) }, "Delete char forward")
91
+ bindkey "C x", :delete_char_forward
92
+
93
+ reg_act(:load_theme, proc { load_theme }, "Load theme")
94
+ bindkey "C , , l t", :load_theme
95
+
96
+ reg_act(:gui_file_finder, proc { vma.FileFinder.start_gui }, "Fuzzy file finder")
97
+ bindkey "C , f", :gui_file_finder
98
+
99
+
100
+ reg_act(:gui_file_history_finder, proc { vma.FileHistory.start_gui }, "Fuzzy file history finder")
101
+ bindkey "C , h", :gui_file_history_finder
102
+
103
+
104
+ reg_act(:gui_search_replace, proc { gui_search_replace }, "Search and replace")
105
+ bindkey "C , r r", :gui_search_replace
106
+ bindkey "V , r r", :gui_search_replace
107
+
108
+ reg_act(:set_style_bold, proc { buf.style_transform(:bold) }, "Set text weight to bold")
109
+ bindkey "V , t b", :set_style_bold
110
+
111
+ reg_act(:set_style_link, proc { buf.style_transform(:link) }, "Set text as link")
112
+ bindkey "V , t l", :set_style_link
113
+
114
+ reg_act(:V_join_lines, proc { vma.buf.convert_selected_text(:joinlines) }, "Join lines")
115
+ bindkey "V J", :V_join_lines
116
+
117
+
118
+ reg_act(:clear_formats, proc { buf.style_transform(:clear) }, "Clear style formats")
119
+ bindkey "V , t c", :clear_formats
120
+
121
+ reg_act(:set_line_style_heading, proc { buf.set_line_style(:heading) }, "Set style of current line as heading")
122
+ bindkey "C , t h", :set_line_style_heading
123
+
124
+ reg_act(:set_line_style_h1, proc { buf.set_line_style(:h1) }, "Set cur line as Heading 1")
125
+ bindkey "C , t 1", :set_line_style_h1
126
+ reg_act(:set_line_style_h2, proc { buf.set_line_style(:h2) }, "Set cur line as Heading 1")
127
+ bindkey "C , t 2", :set_line_style_h2
128
+ reg_act(:set_line_style_h3, proc { buf.set_line_style(:h3) }, "Set cur line as Heading 1")
129
+ bindkey "C , t 3", :set_line_style_h3
130
+ reg_act(:set_line_style_h4, proc { buf.set_line_style(:h4) }, "Set cur line as Heading 1")
131
+ bindkey "C , t 4", :set_line_style_h4
132
+
133
+
134
+ reg_act(:set_line_style_bold, proc { buf.set_line_style(:bold) }, "Set style of current line as bold")
135
+ bindkey "C , t b", :set_line_style_bold
136
+
137
+ reg_act(:set_line_style_title, proc { buf.set_line_style(:title) }, "Set style of current line as title")
138
+ bindkey "C , t t", :set_line_style_title
139
+
140
+ reg_act(:clear_line_styles, proc { buf.set_line_style(:clear) }, "Clear styles of current line")
141
+ bindkey "C , t c", :clear_line_styles
142
+
143
+ reg_act(:gui_select_buffer, proc { $kbd.set_mode("S"); gui_select_buffer }, "Select buffer")
144
+ bindkey "C , b", :gui_select_buffer
145
+
146
+ reg_act :open_file_dialog, "open_file_dialog", "Open file"
147
+ # bindkey "C , f o", :open_file_dialog
148
+ bindkey "CI ctrl-o", :open_file_dialog
149
+
150
+ reg_act :minibuffer_end, proc { minibuffer_end }
151
+ bindkey "M enter", :minibuffer_end
152
+
153
+ reg_act(:invoke_replace, "invoke_replace", "")
154
+ reg_act(:diff_buffer, "diff_buffer", "")
155
+
156
+ # reg_act(:invoke_grep_search, proc{invoke_grep_search}, "")
157
+ reg_act(:invoke_grep_search, proc { gui_grep }, "Grep current buffer")
158
+
159
+
160
+ reg_act(:ack_search, proc { gui_ack }, "") #invoke_ack_search
161
+ bindkey "C , a", :ack_search
162
+
163
+ reg_act :update_file_index, proc { update_file_index }, "Update file index"
164
+
165
+
166
+ reg_act :delete_to_word_end, proc { buf.delete2(:to_word_end) }, "Delete to file end"
167
+ bindkey "C d w", :delete_to_word_end
168
+
169
+ reg_act :delete_to_line_start, proc { buf.delete2(:to_line_start) }, "Delete to line start"
170
+ bindkey "C d 0", :delete_to_line_start
171
+
172
+
173
+ bindkey "C , , f", :file_finder
174
+ bindkey "VC h", :e_move_backward_char
175
+
176
+ bindkey "C , , .", :backup_all_buffers
177
+
178
+
179
+ bindkey "C z ", :start_browse_mode
180
+ bindkey "B h", :history_switch_backwards
181
+ bindkey "B l", :history_switch_forwards
182
+ #bindkey 'B z', :center_on_current_line
183
+ bindkey "B z", "center_on_current_line();call(:exit_browse_mode)"
184
+
185
+ reg_act :start_browse_mode, proc { $kbd.set_mode(:browse); $kbd.set_default_mode(:browse) }, "Start browse mode"
186
+
187
+ reg_act :exit_browse_mode, proc { bufs.add_current_buf_to_history();$kbd.set_mode(:command); $kbd.set_default_mode(:command)
188
+ }, "Exit browse mode"
189
+ #TODO: Need to deside which of these is best:
190
+ bindkey "B enter || B return || B esc || B j || B ctrl!", :exit_browse_mode
191
+
192
+ reg_act :page_down, proc {page_down}
193
+ reg_act :page_up, proc {page_up}
194
+ bindkey "B s", :page_up
195
+ bindkey "B d", :page_down
196
+ bindkey "B s", :page_up
197
+ bindkey "B d", :page_down
198
+
199
+ reg_act :jump_to_start_of_buffer, proc{buf.jump(START_OF_BUFFER)}, "Jump to start of buffer"
200
+ reg_act :jump_to_end_of_buffer, proc{buf.jump(END_OF_BUFFER)}, "Jump to end of buffer"
201
+
202
+ bindkey "B i", :jump_to_start_of_buffer
203
+ bindkey "B o", :jump_to_end_of_buffer
204
+
205
+ bindkey "B c", :close_current_buffer
206
+ bindkey "B ;", "buf.jump_to_last_edit"
207
+ bindkey "B q", :jump_to_last_edit
208
+ bindkey "B w", :jump_to_next_edit
209
+
210
+ bindkey "C , d", :diff_buffer
211
+ bindkey "C , g", :invoke_grep_search
212
+ #bindkey 'C , g', proc{invoke_grep_search}
213
+
214
+ reg_act(:auto_indent_buffer, proc { buf.indent }, "Auto format buffer")
215
+ bindkey "C , v", :auto_indent_buffer
216
+ bindkey "C , , d", :savedebug
217
+ bindkey "C , , u", :update_file_index
218
+
219
+ bindkey "C , s a", "buf.save_as()"
220
+
221
+
222
+
223
+ reg_act(:execute_current_line_in_terminal, proc { buf.execute_current_line_in_terminal }, "Execute current line in terminal")
224
+
225
+ reg_act(:show_images, proc { hpt_scan_images() }, "Show images inserted with ⟦img:file.png⟧ syntax")
226
+
227
+ reg_act(:delete_current_file, proc { bufs.delete_current_buffer() }, "Delete current file")
228
+
229
+
230
+ bindkey "C d d", [:delete_line, proc{buf.delete_line}, "Delete current line"]
231
+ bindkey "C enter || C return", [:line_action,proc{buf.handle_line_action()}, "Line action"]
232
+ bindkey "C p" , [:paste_after,proc{buf.paste(AFTER)},""] # TODO: implement as replace for visual mode
233
+ bindkey "V d" , [:delete_selection,proc{buf.delete(SELECTION)},""]
234
+
235
+
236
+ # reg_act(:start_file_selector, proc { FileSelector.new.run; $kbd.set_mode(:file_exp) }, "File selector")
237
+ # bindkey "C , j f", :start_file_selector
238
+ # bindkey "C , f", :start_file_selector
239
+
240
+ # $kbd.add_minor_mode('fexp', :file_exp, :command)
241
+
242
+ # bindkey "fexp l" , [:fexp_right,proc{puts "==fexp_right=="},""]
243
+ # bindkey "fexp esc" , [:fexp_quit,proc{$kbd.set_mode(:command)},""]
244
+ # bindkey "fexp enter" , [:fexp_select,proc{buf.module.select_line},""]
245
+
246
+ # bindkey "C , j j", [:mode_file_exp, proc{$kbd.set_mode(:file_exp)}, "fexp"]
247
+
248
+ #bindkey 'C z h', :history_switch_backwards
249
+ #bindkey 'C z l', :history_switch_forwards
250
+
251
+
252
+ #TODO: Change these evals into proc{}'s
253
+ default_keys = {
254
+
255
+ # File handling
256
+ "C ctrl-s" => "buf.save",
257
+ "C W" => "buf.save",
258
+
259
+ # Buffer handling
260
+ "C B" => "bufs.switch",
261
+ "C tab" => "bufs.switch_to_last_buf",
262
+ # 'C , s'=> 'gui_select_buffer',
263
+ "C , r v b" => "buf.revert",
264
+ "C , c b" => "bufs.close_current_buffer",
265
+ #"C , b" => '$kbd.set_mode("S");gui_select_buffer',
266
+ "C , n b" => "create_new_file()",
267
+ "C , ." => "buf.backup()",
268
+ # "C , , ." => "backup_all_buffers()",
269
+ "VC , , s" => "search_actions()",
270
+
271
+
272
+ # MOVING
273
+ # 'VC h' => 'buf.move(BACKWARD_CHAR)',
274
+ "VC l" => "buf.move(FORWARD_CHAR)",
275
+ "VC j" => "buf.move(FORWARD_LINE)",
276
+ "VC k" => "buf.move(BACKWARD_LINE)",
277
+
278
+ "VC pagedown" => "page_down",
279
+ "VC pageup" => "page_up",
280
+
281
+ "VCI left" => "buf.move(BACKWARD_CHAR)",
282
+ "VCI right" => "buf.move(FORWARD_CHAR)",
283
+ "VCI down" => "buf.move(FORWARD_LINE)",
284
+ "VCI up" => "buf.move(BACKWARD_LINE)",
285
+
286
+ "VC w" => "buf.jump_word(FORWARD,WORD_START)",
287
+ "VC b" => "buf.jump_word(BACKWARD,WORD_START)",
288
+ "VC e" => "buf.jump_word(FORWARD,WORD_END)",
289
+ # 'C '=> 'buf.jump_word(BACKWARD,END)',#TODO
290
+ "VC f <char>" => "buf.jump_to_next_instance_of_char(<char>)",
291
+ "VC F <char>" => "buf.jump_to_next_instance_of_char(<char>,BACKWARD)",
292
+ "VC f space" => "buf.jump_to_next_instance_of_char(' ')",
293
+ "VC F space" => "buf.jump_to_next_instance_of_char(' ',BACKWARD)",
294
+
295
+ "VC /[1-9]/" => "set_next_command_count(<char>)",
296
+ # 'VC number=/[0-9]/+ g'=> 'jump_to_line(<number>)',
297
+ # 'VC X=/[0-9]/+ * Y=/[0-9]/+ '=> 'x_times_y(<X>,<Y>)',
298
+ "VC ^" => "buf.jump(BEGINNING_OF_LINE)",
299
+ "VC G($next_command_count!=nil)" => "buf.jump_to_line()",
300
+ "VC 0($next_command_count!=nil)" => "set_next_command_count(<char>)",
301
+ "VC 0($next_command_count==nil)" => "buf.jump(BEGINNING_OF_LINE)",
302
+ # 'C 0'=> 'buf.jump(BEGINNING_OF_LINE)',
303
+ "VC g g" => "buf.jump(START_OF_BUFFER)",
304
+ "VC g ;" => "buf.jump_to_last_edit",
305
+ "VC G" => "buf.jump(END_OF_BUFFER)",
306
+ # 'VC z z' => 'center_on_current_line',
307
+ "VC *" => "buf.jump_to_next_instance_of_word",
308
+
309
+ # MINIBUFFER bindings
310
+ "VC /" => "invoke_search",
311
+ # 'VC :' => 'invoke_command', #TODO
312
+ "C , e" => "invoke_command", # Currently eval
313
+ "M enter" => "minibuffer_end()",
314
+ # "M return" => "minibuffer_end()",
315
+ "M esc" => "minibuffer_cancel()",
316
+ "M backspace" => "minibuffer_delete()",
317
+ "M <char>" => "minibuffer_new_char(<char>)",
318
+ "M ctrl-v" => "$minibuffer.paste(BEFORE)",
319
+
320
+ # READCHAR bindings
321
+
322
+ "R <char>" => "readchar_new_char(<char>)",
323
+
324
+ "C n" => "$search.jump_to_next()",
325
+ "C N" => "$search.jump_to_previous()",
326
+
327
+ # Debug
328
+ "C , d r p" => "start_ripl",
329
+ "C , D" => "debug_print_buffer",
330
+ "C , c s" => "bufs.close_scrap_buffers",
331
+ "C , d b" => "debug_print_buffer",
332
+ "C , d c" => "debug_dump_clipboard",
333
+ "C , d d" => "debug_dump_deltas",
334
+ "VC O" => "buf.jump(END_OF_LINE)",
335
+ "VC $" => "buf.jump(END_OF_LINE)",
336
+
337
+ "C o" => 'buf.jump(END_OF_LINE);buf.insert_txt("\n");$kbd.set_mode(:insert)',
338
+ "C X" => 'buf.jump(END_OF_LINE);buf.insert_txt("\n");',
339
+ "C A" => "buf.jump(END_OF_LINE);$kbd.set_mode(:insert)",
340
+ "C I" => "buf.jump(FIRST_NON_WHITESPACE);$kbd.set_mode(:insert)",
341
+ "C a" => "buf.move(FORWARD_CHAR);$kbd.set_mode(:insert)",
342
+ "C J" => "buf.join_lines()",
343
+ "C u" => "buf.undo()",
344
+
345
+ "C ^" => "buf.jump(BEGINNING_OF_LINE)",
346
+ "C /[1-9]/" => "set_next_command_count(<char>)",
347
+
348
+ # Command mode only:
349
+ "C ctrl-r" => "buf.redo()", # TODO:???
350
+ "C R" => "buf.redo()",
351
+ "C v" => "buf.start_visual_mode",
352
+ "C P" => "buf.paste(BEFORE)", # TODO: implement as replace for visual mode
353
+ "C space <char>" => "buf.insert_txt(<char>)",
354
+ "C space space" => "buf.insert_txt(' ')",
355
+ "C y y" => "buf.copy_line",
356
+ "C y O" => "buf.copy(:to_line_end)",
357
+ "C y 0" => "buf.copy(:to_line_start)",
358
+ "C y e" => "buf.copy(:to_word_end)", # TODO
359
+ #### Deleting
360
+ "C x" => "buf.delete(CURRENT_CHAR_FORWARD)",
361
+ # 'C d k'=> 'delete_line(BACKWARD)', #TODO
362
+ # 'C d j'=> 'delete_line(FORWARD)', #TODO
363
+ # 'C d d'=> 'buf.delete_cur_line',
364
+ "C d e" => "buf.delete2(:to_word_end)",
365
+ "C d O" => "buf.delete2(:to_line_end)",
366
+ "C d $" => "buf.delete2(:to_line_end)",
367
+ # 'C d e'=> 'buf.delete_to_next_word_end',
368
+ "C d <num> e" => "delete_next_word",
369
+ "C r <char>" => "buf.replace_with_char(<char>)", # TODO
370
+ "C , l b" => "load_buffer_list",
371
+ "C , l l" => "save_buffer_list",
372
+ "C , r <char>" => "set_register(<char>)", # TODO
373
+ "C , p <char>" => "buf.paste(BEFORE,<char>)", # TODO
374
+
375
+ "C ctrl-c" => "buf.comment_line()",
376
+ "C ctrl-x" => "buf.comment_line(:uncomment)",
377
+
378
+ # 'C 0($next_command_count==nil)'=> 'jump_to_beginning_of_line',
379
+
380
+ # Visual mode only:
381
+ "V esc" => "buf.end_visual_mode",
382
+ "V ctrl!" => "buf.end_visual_mode",
383
+ "V y" => "buf.copy_active_selection",
384
+ "V g U" => "buf.transform_selection(:upcase)",
385
+ "V g u" => "buf.transform_selection(:downcase)",
386
+ "V g c" => "buf.transform_selection(:capitalize)",
387
+ "V g s" => "buf.transform_selection(:swapcase)",
388
+ "V g r" => "buf.transform_selection(:reverse)",
389
+
390
+ "V x" => "buf.delete(SELECTION)",
391
+ # "V ctrl-c" => "buf.comment_selection",
392
+ "V ctrl-x" => "buf.comment_selection(:uncomment)",
393
+
394
+ "CI ctrl-v" => "buf.paste(BEFORE)",
395
+ "CI backspace" => "buf.delete(BACKWARD_CHAR)",
396
+
397
+ # Marks
398
+ "CV m <char>" => "buf.mark_current_position(<char>)",
399
+ 'CV \' <char>' => "buf.jump_to_mark(<char>)",
400
+ # "CV ''" =>'jump_to_mark(NEXT_MARK)', #TODO
401
+
402
+ "C i" => "$kbd.set_mode(:insert)",
403
+ "C ctrl!" => "$kbd.set_mode(:insert)",
404
+
405
+ # Macros
406
+ # (experimental, may not work correctly)
407
+ # "C q a" => '$macro.start_recording("a")',
408
+ "VC q <char>" => '$macro.start_recording(<char>)',
409
+ "VC q($macro.is_recording==true) " => "$macro.end_recording", # TODO
410
+ # 'C q'=> '$macro.end_recording', #TODO
411
+ "C q v" => "$macro.end_recording",
412
+ # 'C v'=> '$macro.end_recording',
413
+ # "C M" => '$macro.run_last_macro',
414
+ "C @ <char>" => '$macro.run_macro(<char>)',
415
+ "C , m S" => '$macro.save_macro("a")',
416
+ "C , m s" => '$macro.save',
417
+ "C , t r" => "run_tests()",
418
+
419
+ "C ." => "repeat_last_action", # TODO
420
+ "VC ;" => "repeat_last_find",
421
+ "CV Q" => "_quit",
422
+ "CV ctrl-q" => "_quit",
423
+ "CV , R" => "restart_application",
424
+ "I ctrl!" => "$kbd.set_mode(:command)",
425
+ "C shift!" => "buf.save",
426
+ "I <char>" => "buf.insert_txt(<char>)",
427
+ "I esc" => "$kbd.set_mode(:command)",
428
+
429
+ "I ctrl-d" => "buf.delete2(:to_word_end)",
430
+
431
+ # INSERT MODE: Moving
432
+ "I ctrl-a" => "buf.jump(BEGINNING_OF_LINE)",
433
+ "I ctrl-b" => "buf.move(BACKWARD_CHAR)",
434
+ "I ctrl-f" => "buf.move(FORWARD_CHAR)",
435
+ "I ctrl-n" => "buf.move(FORWARD_LINE)",
436
+ "I ctrl-p" => "buf.move(BACKWARD_LINE)",
437
+ "I ctrl-e" => "buf.jump(END_OF_LINE)", # context: mode:I, buttons down: {C}
438
+ "I alt-f" => "buf.jump_word(FORWARD,WORD_START)",
439
+ "I alt-b" => "buf.jump_word(BACKWARD,WORD_START)",
440
+
441
+ "I tab" => 'buf.insert_txt(" ")',
442
+ "I space" => 'buf.insert_txt(" ")',
443
+ # "I return" => 'buf.insert_new_line()',
444
+ }
445
+
446
+ default_keys.each { |key, value|
447
+ bindkey(key, value)
448
+ }