vimamsa 0.1.7 → 0.1.10

Sign up to get free protection for your applications and to get access to all the features.
@@ -50,16 +50,15 @@ class FileSelector
50
50
  # puts "def select_line"
51
51
  fn = fullp(@buf.get_current_line[0..-2])
52
52
  if File.directory?(fn)
53
- puts "CHDIR: #{fn}"
53
+ debug "CHDIR: #{fn}"
54
54
  dir_to_buf(fn)
55
- # elsif vma.can_open_extension?(fn) #TODO: remove this check?
55
+ # elsif vma.can_open_extension?(fn) #TODO: remove this check?
56
56
  # jump_to_file(fn)
57
57
  elsif file_is_text_file(fn)
58
58
  jump_to_file(fn)
59
59
  else
60
60
  open_with_default_program(fn)
61
61
  end
62
- # puts l.inspect
63
62
  end
64
63
  end
65
64
 
@@ -71,10 +70,10 @@ end
71
70
 
72
71
  def grep_cur_buffer(search_str, b = nil)
73
72
  debug "grep_cur_buffer(search_str)"
74
- lines = $buffer.split("\n")
73
+ lines = vma.buf.split("\n")
75
74
  r = Regexp.new(Regexp.escape(search_str), Regexp::IGNORECASE)
76
75
  fpath = ""
77
- fpath = $buffer.pathname.expand_path.to_s + ":" if $buffer.pathname
76
+ fpath = vma.buf.pathname.expand_path.to_s + ":" if vma.buf.pathname
78
77
  res_str = ""
79
78
 
80
79
  $grep_matches = []
@@ -85,16 +84,16 @@ def grep_cur_buffer(search_str, b = nil)
85
84
  $grep_matches << i + 1 # Lines start from index 1
86
85
  end
87
86
  }
88
- $grep_bufid = $buffers.current_buf
87
+ $grep_bufid = vma.buffers.current_buf
89
88
  b = create_new_file(nil, res_str)
90
89
  # set_current_buffer(buffer_i, update_history = true)
91
90
  # @current_buf = buffer_i
92
91
 
93
92
  b.line_action_handler = proc { |lineno|
94
- puts "GREP HANDLER:#{lineno}"
93
+ debug "GREP HANDLER:#{lineno}"
95
94
  jumpto = $grep_matches[lineno]
96
95
  if jumpto.class == Integer
97
- $buffers.set_current_buffer($grep_bufid, update_history = true)
96
+ vma.buffers.set_current_buffer($grep_bufid, update_history = true)
98
97
  buf.jump_to_line(jumpto)
99
98
  end
100
99
  }
@@ -104,8 +103,8 @@ def invoke_grep_search()
104
103
  start_minibuffer_cmd("", "", :grep_cur_buffer)
105
104
  end
106
105
 
107
- def gui_one_input_action(title, field_label, button_title, callback)
108
- a = OneInputAction.new(nil, title, field_label, button_title, callback)
106
+ def gui_one_input_action(title, field_label, button_title, callback,opt={})
107
+ a = OneInputAction.new(nil, title, field_label, button_title, callback,opt)
109
108
  a.run
110
109
  return
111
110
  end
@@ -114,7 +113,7 @@ end
114
113
  def gui_replace_callback(vals)
115
114
  search_str = vals["search"]
116
115
  replace_str = vals["replace"]
117
- puts "gui_replace_callback: #{search_str} => #{replace_str}"
116
+ debug "gui_replace_callback: #{search_str} => #{replace_str}"
118
117
  gui_select_window_close(0)
119
118
  buf_replace(search_str, replace_str)
120
119
  end
@@ -137,21 +136,21 @@ def invoke_replace()
137
136
  end
138
137
 
139
138
  def buf_replace(search_str, replace_str)
140
- if $buffer.visual_mode?
141
- r = $buffer.get_visual_mode_range
142
- txt = $buffer[r]
139
+ if vma.buf.visual_mode?
140
+ r = vma.buf.get_visual_mode_range
141
+ txt = vma.buf[r]
143
142
  txt.gsub!(search_str, replace_str)
144
- $buffer.replace_range(r, txt)
145
- $buffer.end_visual_mode
143
+ vma.buf.replace_range(r, txt)
144
+ vma.buf.end_visual_mode
146
145
  else
147
- repbuf = $buffer.to_s.clone
146
+ repbuf = vma.buf.to_s.clone
148
147
  repbuf.gsub!(search_str, replace_str)
149
- tmppos = $buffer.pos
150
- if repbuf == $buffer.to_s.clone
148
+ tmppos = vma.buf.pos
149
+ if repbuf == vma.buf.to_s.clone
151
150
  message("NO CHANGE. Replacing #{search_str} with #{replace_str}.")
152
151
  else
153
- $buffer.set_content(repbuf)
154
- $buffer.set_pos(tmppos)
152
+ vma.buf.set_content(repbuf)
153
+ vma.buf.set_pos(tmppos)
155
154
  message("Replacing #{search_str} with #{replace_str}.")
156
155
  end
157
156
  end
@@ -263,7 +262,7 @@ class PopupFormGenerator
263
262
  end
264
263
 
265
264
  class OneInputAction
266
- def initialize(main_window, title, field_label, button_title, callback)
265
+ def initialize(main_window, title, field_label, button_title, callback, opt = {})
267
266
  @window = Gtk::Window.new(:toplevel)
268
267
  # @window.screen = main_window.screen
269
268
  # @window.title = title
@@ -292,6 +291,10 @@ class OneInputAction
292
291
 
293
292
  @entry1 = Gtk::Entry.new
294
293
 
294
+ if opt[:hide]
295
+ @entry1.visibility = false
296
+ end
297
+
295
298
  button.signal_connect "clicked" do
296
299
  callback.call(@entry1.text)
297
300
  @window.destroy
@@ -3,7 +3,7 @@ class Converter
3
3
  @obj = obj
4
4
  @type = type
5
5
  if id != nil
6
- $vma.reg_conv(self, id)
6
+ vma.reg_conv(self, id)
7
7
  end
8
8
  end
9
9
 
@@ -30,3 +30,5 @@ Converter.new(lambda { |x|
30
30
  x + "\n" + nums.join("+") + "=#{sum}"
31
31
  }, :lambda, :sum_of_numbers)
32
32
 
33
+ c = Converter.new(lambda { |x| x.scan(/[\w\.]+@[\w\.]+/).join("\n") }, :lambda, :get_emails)
34
+
data/lib/vimamsa/util.rb CHANGED
@@ -3,6 +3,40 @@
3
3
  # Cross-platform way of finding an executable in the $PATH.
4
4
  #
5
5
  # which('ruby') #=> /usr/bin/ruby
6
+
7
+
8
+ # Execute proc after wait_time seconds after last .run call.
9
+ # Used for image scaling after window resize
10
+ class DelayExecutioner
11
+ def initialize(wait_time, _proc)
12
+ @wait_time = wait_time
13
+ @proc = _proc
14
+ @lastt = Time.now
15
+ @thread_running = false
16
+ end
17
+
18
+ def start_thread
19
+ Thread.new {
20
+ while true
21
+ sleep 0.1
22
+ if Time.now - @lastt > @wait_time
23
+ @proc.call
24
+ @thread_running = false
25
+ break
26
+ end
27
+ end
28
+ }
29
+ end
30
+
31
+ def run()
32
+ @lastt = Time.now
33
+ if @thread_running == false
34
+ @thread_running = true
35
+ start_thread
36
+ end
37
+ end
38
+ end
39
+
6
40
  def which(cmd)
7
41
  exts = ENV["PATHEXT"] ? ENV["PATHEXT"].split(";") : [""]
8
42
  ENV["PATH"].split(File::PATH_SEPARATOR).each do |path|
@@ -1,3 +1,3 @@
1
1
  module Vimamsa
2
- VERSION = "0.1.7"
2
+ VERSION = "0.1.10"
3
3
  end
data/lib/vimamsa.rb CHANGED
@@ -1,4 +1,9 @@
1
1
  require "vimamsa/version"
2
+
3
+ require "gtk3"
4
+ require "gtksourceview4"
5
+ test1 = Gtk::TextView.new
6
+
2
7
  require "vmaext"
3
8
 
4
9
  require "vimamsa/rbvma"
data/sheep.jpg ADDED
Binary file
data/styles/dark.xml CHANGED
@@ -136,6 +136,7 @@
136
136
  <style name="def:heading5" scale="1.1" bold="true" foreground="heading" />
137
137
  <style name="def:heading6" scale="1.0" bold="true" foreground="heading" />
138
138
 
139
+ <style name="def:bold" scale="1.5" bold="true" foreground="heading" />
139
140
 
140
141
  <!-- Language specific -->
141
142
  <style name="diff:added-line" foreground="butter2"/>
@@ -44,6 +44,6 @@
44
44
  <style name="def:heading4" scale="1.175" bold="true" foreground="heading" />
45
45
  <style name="def:heading5" scale="1.1" bold="true" foreground="heading" />
46
46
  <style name="def:heading6" scale="1.0" bold="true" foreground="heading" />
47
-
47
+ <style name="def:bold" bold="true" />
48
48
  </style-scheme>
49
49
 
data/vimamsa.gemspec CHANGED
@@ -30,8 +30,8 @@ Gem::Specification.new do |spec|
30
30
  spec.add_runtime_dependency 'gdk3', '~> 3.4'
31
31
  spec.add_runtime_dependency 'gtk3', '~> 3.4'
32
32
  spec.add_runtime_dependency 'differ', '~> 0.1'
33
- spec.add_runtime_dependency 'gtksourceview3', '~> 3.4'
34
- # spec.add_runtime_dependency 'gtksourceview4'
33
+ # spec.add_runtime_dependency 'gtksourceview3', '~> 3.4'
34
+ spec.add_runtime_dependency 'gtksourceview4'
35
35
  spec.add_runtime_dependency 'parallel', '~> 1.14'
36
36
  spec.add_runtime_dependency 'listen', '~> 3.4'
37
37
 
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: vimamsa
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.1.7
4
+ version: 0.1.10
5
5
  platform: ruby
6
6
  authors:
7
7
  - Sami Sieranoja
8
- autorequire:
8
+ autorequire:
9
9
  bindir: exe
10
10
  cert_chain: []
11
- date: 2022-04-25 00:00:00.000000000 Z
11
+ date: 2022-05-27 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: bundler
@@ -123,19 +123,19 @@ dependencies:
123
123
  - !ruby/object:Gem::Version
124
124
  version: '0.1'
125
125
  - !ruby/object:Gem::Dependency
126
- name: gtksourceview3
126
+ name: gtksourceview4
127
127
  requirement: !ruby/object:Gem::Requirement
128
128
  requirements:
129
- - - "~>"
129
+ - - ">="
130
130
  - !ruby/object:Gem::Version
131
- version: '3.4'
131
+ version: '0'
132
132
  type: :runtime
133
133
  prerelease: false
134
134
  version_requirements: !ruby/object:Gem::Requirement
135
135
  requirements:
136
- - - "~>"
136
+ - - ">="
137
137
  - !ruby/object:Gem::Version
138
- version: '3.4'
138
+ version: '0'
139
139
  - !ruby/object:Gem::Dependency
140
140
  name: parallel
141
141
  requirement: !ruby/object:Gem::Requirement
@@ -181,6 +181,8 @@ files:
181
181
  - Rakefile
182
182
  - bin/console
183
183
  - bin/setup
184
+ - custom_example.rb
185
+ - demo.txt
184
186
  - exe/vimamsa
185
187
  - ext/vmaext/extconf.rb
186
188
  - ext/vmaext/vmaext.c
@@ -190,6 +192,8 @@ files:
190
192
  - lib/vimamsa/actions.rb
191
193
  - lib/vimamsa/buffer.rb
192
194
  - lib/vimamsa/buffer_list.rb
195
+ - lib/vimamsa/buffer_manager.rb
196
+ - lib/vimamsa/conf.rb
193
197
  - lib/vimamsa/constants.rb
194
198
  - lib/vimamsa/debug.rb
195
199
  - lib/vimamsa/easy_jump.rb
@@ -199,7 +203,7 @@ files:
199
203
  - lib/vimamsa/file_history.rb
200
204
  - lib/vimamsa/file_manager.rb
201
205
  - lib/vimamsa/gui.rb
202
- - lib/vimamsa/gui_gtk_sourceview.rb
206
+ - lib/vimamsa/gui_image.rb
203
207
  - lib/vimamsa/gui_menu.rb
204
208
  - lib/vimamsa/gui_select_window.rb
205
209
  - lib/vimamsa/gui_sourceview.rb
@@ -216,6 +220,7 @@ files:
216
220
  - lib/vimamsa/text_transforms.rb
217
221
  - lib/vimamsa/util.rb
218
222
  - lib/vimamsa/version.rb
223
+ - sheep.jpg
219
224
  - styles/134272-molokai.xml
220
225
  - styles/dark.xml
221
226
  - styles/molokai_edit.xml
@@ -224,7 +229,7 @@ homepage: https://github.com/SamiSieranoja/vimamsa
224
229
  licenses:
225
230
  - GPL-3.0+
226
231
  metadata: {}
227
- post_install_message:
232
+ post_install_message:
228
233
  rdoc_options: []
229
234
  require_paths:
230
235
  - lib
@@ -241,7 +246,7 @@ required_rubygems_version: !ruby/object:Gem::Requirement
241
246
  version: '0'
242
247
  requirements: []
243
248
  rubygems_version: 3.1.2
244
- signing_key:
249
+ signing_key:
245
250
  specification_version: 4
246
251
  summary: Vimamsa
247
252
  test_files: []
@@ -1,294 +0,0 @@
1
-
2
- class VSourceView < GtkSource::View
3
- def initialize(title = nil)
4
- # super(:toplevel)
5
- super()
6
- puts "vsource init"
7
- @last_keyval = nil
8
- @last_event = [nil, nil]
9
-
10
- signal_connect "button-press-event" do |_widget, event|
11
- if event.button == Gdk::BUTTON_PRIMARY
12
- # puts "Gdk::BUTTON_PRIMARY"
13
- false
14
- elsif event.button == Gdk::BUTTON_SECONDARY
15
- # puts "Gdk::BUTTON_SECONDARY"
16
- true
17
- else
18
- true
19
- end
20
- end
21
-
22
- signal_connect("key_press_event") do |widget, event|
23
- handle_key_event(event, :key_press_event)
24
- true
25
- end
26
-
27
- signal_connect("key_release_event") do |widget, event|
28
- handle_key_event(event, :key_release_event)
29
- true
30
- end
31
-
32
- signal_connect("move-cursor") do |widget, event|
33
- $update_cursor = true
34
- false
35
- end
36
-
37
- signal_connect "button-release-event" do |widget, event|
38
- $buffer.set_pos(buffer.cursor_position)
39
- false
40
- end
41
- @curpos_mark = nil
42
- end
43
-
44
- def handle_key_event(event, sig)
45
- if $update_cursor
46
- curpos = buffer.cursor_position
47
- puts "MOVE CURSOR: #{curpos}"
48
- buf.set_pos(curpos)
49
- $update_cursor = false
50
- end
51
- puts $view.visible_rect.inspect
52
-
53
- puts "key event"
54
- puts event
55
-
56
- key_name = event.string
57
- if event.state.control_mask?
58
- key_name = Gdk::Keyval.to_name(event.keyval)
59
- # Gdk::Keyval.to_name()
60
- end
61
-
62
- keyval_trans = {}
63
- keyval_trans[Gdk::Keyval::KEY_Control_L] = "ctrl"
64
- keyval_trans[Gdk::Keyval::KEY_Control_R] = "ctrl"
65
-
66
- keyval_trans[Gdk::Keyval::KEY_Escape] = "esc"
67
-
68
- keyval_trans[Gdk::Keyval::KEY_Return] = "enter"
69
- keyval_trans[Gdk::Keyval::KEY_ISO_Enter] = "enter"
70
- keyval_trans[Gdk::Keyval::KEY_KP_Enter] = "enter"
71
- keyval_trans[Gdk::Keyval::KEY_Alt_L] = "alt"
72
- keyval_trans[Gdk::Keyval::KEY_Alt_R] = "alt"
73
-
74
- keyval_trans[Gdk::Keyval::KEY_BackSpace] = "backspace"
75
- keyval_trans[Gdk::Keyval::KEY_KP_Page_Down] = "pagedown"
76
- keyval_trans[Gdk::Keyval::KEY_KP_Page_Up] = "pageup"
77
- keyval_trans[Gdk::Keyval::KEY_Page_Down] = "pagedown"
78
- keyval_trans[Gdk::Keyval::KEY_Page_Up] = "pageup"
79
- keyval_trans[Gdk::Keyval::KEY_Left] = "left"
80
- keyval_trans[Gdk::Keyval::KEY_Right] = "right"
81
- keyval_trans[Gdk::Keyval::KEY_Down] = "down"
82
- keyval_trans[Gdk::Keyval::KEY_Up] = "up"
83
- keyval_trans[Gdk::Keyval::KEY_space] = "space"
84
-
85
- keyval_trans[Gdk::Keyval::KEY_Shift_L] = "shift"
86
- keyval_trans[Gdk::Keyval::KEY_Shift_R] = "shift"
87
- keyval_trans[Gdk::Keyval::KEY_Tab] = "tab"
88
-
89
- key_trans = {}
90
- key_trans["\e"] = "esc"
91
- tk = keyval_trans[event.keyval]
92
- key_name = tk if !tk.nil?
93
-
94
- key_str_parts = []
95
- key_str_parts << "ctrl" if event.state.control_mask? and key_name != "ctrl"
96
- key_str_parts << "alt" if event.state.mod1_mask? and key_name != "alt"
97
-
98
- key_str_parts << key_name
99
- key_str = key_str_parts.join("-")
100
- keynfo = { :key_str => key_str, :key_name => key_name, :keyval => event.keyval }
101
- puts keynfo.inspect
102
- # $kbd.match_key_conf(key_str, nil, :key_press)
103
- # puts "key_str=#{key_str} key_"
104
-
105
- if key_str != "" # or prefixed_key_str != ""
106
- if sig == :key_release_event and event.keyval == @last_keyval
107
- $kbd.match_key_conf(key_str + "!", nil, :key_release)
108
- @last_event = [event, :key_release]
109
- elsif sig == :key_press_event
110
- $kbd.match_key_conf(key_str, nil, :key_press)
111
- @last_event = [event, key_str, :key_press]
112
- end
113
- @last_keyval = event.keyval #TODO: outside if?
114
- end
115
-
116
- handle_deltas
117
-
118
- # set_focus(5)
119
- # false
120
-
121
- end
122
-
123
- def pos_to_coord(i)
124
- b = buffer
125
- iter = b.get_iter_at(:offset => i)
126
- iterxy = get_iter_location(iter)
127
- winw = parent_window.width
128
- view_width = visible_rect.width
129
- gutter_width = winw - view_width
130
-
131
- x = iterxy.x + gutter_width
132
- y = iterxy.y
133
-
134
- # buffer_to_window_coords(Gtk::TextWindowType::TEXT, iterxy.x, iterxy.y).inspect
135
- # puts buffer_to_window_coords(Gtk::TextWindowType::TEXT, x, y).inspect
136
- (x, y) = buffer_to_window_coords(Gtk::TextWindowType::TEXT, x, y)
137
- # Ripl.start :binding => binding
138
-
139
- return [x, y]
140
- end
141
-
142
- def handle_deltas()
143
- any_change = false
144
- while d = buf.deltas.shift
145
- any_change = true
146
- pos = d[0]
147
- op = d[1]
148
- num = d[2]
149
- txt = d[3]
150
- if op == DELETE
151
- startiter = buffer.get_iter_at(:offset => pos)
152
- enditer = buffer.get_iter_at(:offset => pos + num)
153
- buffer.delete(startiter, enditer)
154
- elsif op == INSERT
155
- startiter = buffer.get_iter_at(:offset => pos)
156
- buffer.insert(startiter, txt)
157
- end
158
- end
159
- if any_change
160
- gui_set_cursor_pos($buffer.id, $buffer.pos) #TODO: only when necessary
161
- end
162
-
163
- # sanity_check #TODO
164
- end
165
-
166
- def sanity_check()
167
- a = buffer.text
168
- b = buf.to_s
169
- # puts "===================="
170
- # puts a.lines[0..10].join()
171
- # puts "===================="
172
- # puts b.lines[0..10].join()
173
- # puts "===================="
174
- if a == b
175
- puts "Buffers match"
176
- else
177
- puts "ERROR: Buffer's don't match."
178
- end
179
- end
180
-
181
- def set_cursor_pos(pos)
182
- # return
183
- itr = buffer.get_iter_at(:offset => pos)
184
- itr2 = buffer.get_iter_at(:offset => pos + 1)
185
- buffer.place_cursor(itr)
186
-
187
- # $view.signal_emit("extend-selection", Gtk::MovementStep.new(:PAGES), -1, false)
188
-
189
- within_margin = 0.075 #margin as a [0.0,0.5) fraction of screen size
190
- use_align = false
191
- xalign = 0.5 #0.0=top 1.0=bottom, 0.5=center
192
- yalign = 0.5
193
-
194
- if @curpos_mark.nil?
195
- @curpos_mark = buffer.create_mark("cursor", itr, false)
196
- else
197
- buffer.move_mark(@curpos_mark, itr)
198
- end
199
- scroll_to_mark(@curpos_mark, within_margin, use_align, xalign, yalign)
200
- $idle_scroll_to_mark = true
201
- ensure_cursor_visible
202
-
203
- # scroll_to_iter(itr, within_margin, use_align, xalign, yalign)
204
-
205
- # $view.signal_emit("extend-selection", Gtk::TextExtendSelection.new, itr,itr,itr2)
206
- # Ripl.start :binding => binding
207
- draw_cursor
208
-
209
- return true
210
- end
211
-
212
- def cursor_visible_idle_func
213
- puts "cursor_visible_idle_func"
214
- # From https://picheta.me/articles/2013/08/gtk-plus--a-method-to-guarantee-scrolling.html
215
- # vr = visible_rect
216
-
217
- # b = $view.buffer
218
- # iter = buffer.get_iter_at(:offset => buffer.cursor_position)
219
- # iterxy = get_iter_location(iter)
220
-
221
- sleep(0.01)
222
- # intr = iterxy.intersect(vr)
223
- if is_cursor_visible == false
224
- # set_cursor_pos(buffer.cursor_position)
225
-
226
- itr = buffer.get_iter_at(:offset => buffer.cursor_position)
227
-
228
- within_margin = 0.075 #margin as a [0.0,0.5) fraction of screen size
229
- use_align = false
230
- xalign = 0.5 #0.0=top 1.0=bottom, 0.5=center
231
- yalign = 0.5
232
-
233
- scroll_to_iter(itr, within_margin, use_align, xalign, yalign)
234
-
235
- # return true # Call this func again
236
- else
237
- return false # Don't call this idle func again
238
- end
239
- end
240
-
241
- def is_cursor_visible
242
- vr = visible_rect
243
- iter = buffer.get_iter_at(:offset => buffer.cursor_position)
244
- iterxy = get_iter_location(iter)
245
- iterxy.width = 1 if iterxy.width == 0
246
- iterxy.height = 1 if iterxy.height == 0
247
-
248
- intr = iterxy.intersect(vr)
249
- if intr.nil?
250
- puts iterxy.inspect
251
- puts vr.inspect
252
- # Ripl.start :binding => binding
253
-
254
- # exit!
255
- return false
256
- else
257
- return true
258
- end
259
- end
260
-
261
- def ensure_cursor_visible
262
- if is_cursor_visible == false
263
- Thread.new {
264
- sleep 0.01
265
- GLib::Idle.add(proc { cursor_visible_idle_func })
266
- }
267
- end
268
- end
269
-
270
- def draw_cursor
271
- if is_command_mode
272
- itr = buffer.get_iter_at(:offset => buf.pos)
273
- itr2 = buffer.get_iter_at(:offset => buf.pos + 1)
274
- $view.buffer.select_range(itr, itr2)
275
- elsif buf.visual_mode?
276
- puts "VISUAL MODE"
277
- (_start, _end) = buf.get_visual_mode_range2
278
- puts "#{_start}, #{_end}"
279
- itr = buffer.get_iter_at(:offset => _start)
280
- itr2 = buffer.get_iter_at(:offset => _end + 1)
281
- $view.buffer.select_range(itr, itr2)
282
- else # Insert mode
283
- itr = buffer.get_iter_at(:offset => buf.pos)
284
- $view.buffer.select_range(itr, itr)
285
- puts "INSERT MODE"
286
- end
287
- end
288
-
289
- # def quit
290
- # destroy
291
- # true
292
- # end
293
- end
294
-