arcadia 0.7.0 → 0.8.0

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.
Files changed (168) hide show
  1. data/README +39 -38
  2. data/bin/arc +3 -0
  3. data/bin/arcadia +0 -1
  4. data/conf/arcadia.conf +54 -35
  5. data/conf/arcadia.init.rb +26 -3
  6. data/conf/arcadia.res.rb +56 -4
  7. data/ext/ae-breakpoints/ae-breakpoints.rb +1 -1
  8. data/ext/ae-dir-projects/ae-dir-projects.rb +113 -45
  9. data/ext/ae-editor/ae-editor.conf +6 -2
  10. data/ext/ae-editor/ae-editor.rb +1009 -616
  11. data/ext/ae-editor/langs/coderay.tokens +40 -0
  12. data/ext/ae-editor/langs/conf.lang +12 -10
  13. data/ext/ae-editor/langs/erb.lang.bind +1 -0
  14. data/ext/ae-editor/langs/java.lang +4 -0
  15. data/ext/ae-editor/langs/rb.lang +25 -55
  16. data/ext/ae-editor/langs/rhtml.lang +4 -0
  17. data/ext/ae-editor/langs/tokens.lang.bind +1 -0
  18. data/ext/ae-editor/langs/xml.lang +4 -0
  19. data/ext/ae-file-history/ae-file-history.rb +140 -32
  20. data/ext/ae-output/ae-output.rb +267 -262
  21. data/ext/ae-rad/ae-rad-inspector.rb +1 -1
  22. data/ext/ae-rad/ae-rad-libs.rb +15 -7
  23. data/ext/ae-rad/ae-rad.conf +4 -4
  24. data/ext/ae-rad/lib/tk/al-tk.rb +4 -3
  25. data/ext/ae-ruby-debug/ae-ruby-debug.conf +4 -2
  26. data/ext/ae-ruby-debug/ae-ruby-debug.rb +40 -15
  27. data/ext/ae-search-in-files/ae-search-in-files.rb +70 -14
  28. data/ext/ae-search-in-files/ext/ack-in-files/ack-in-files.conf +15 -0
  29. data/ext/ae-search-in-files/ext/ack-in-files/ack-in-files.rb +80 -0
  30. data/ext/ae-shell/ae-shell.conf +4 -1
  31. data/ext/ae-shell/ae-shell.rb +78 -43
  32. data/ext/test-shutdown-after-startup/test-shutdown-after-startup.conf +4 -0
  33. data/ext/test-shutdown-after-startup/test-shutdown-after-startup.rb +20 -0
  34. data/lib/a-commons.rb +118 -22
  35. data/lib/a-contracts.rb +46 -2
  36. data/lib/a-core.rb +970 -284
  37. data/lib/a-tkcommons.rb +16 -8
  38. data/tcl/{BWidget-1.8.0 → BWidget-1.9.0}/BWman/ArrowButton.html +0 -0
  39. data/tcl/{BWidget-1.8.0 → BWidget-1.9.0}/BWman/BWidget.html +0 -0
  40. data/tcl/{BWidget-1.8.0 → BWidget-1.9.0}/BWman/Button.html +0 -0
  41. data/tcl/{BWidget-1.8.0 → BWidget-1.9.0}/BWman/ButtonBox.html +0 -0
  42. data/tcl/{BWidget-1.8.0 → BWidget-1.9.0}/BWman/ComboBox.html +0 -0
  43. data/tcl/{BWidget-1.8.0 → BWidget-1.9.0}/BWman/Dialog.html +20 -0
  44. data/tcl/{BWidget-1.8.0 → BWidget-1.9.0}/BWman/DragSite.html +6 -4
  45. data/tcl/{BWidget-1.8.0 → BWidget-1.9.0}/BWman/DropSite.html +15 -3
  46. data/tcl/{BWidget-1.8.0 → BWidget-1.9.0}/BWman/DynamicHelp.html +8 -5
  47. data/tcl/{BWidget-1.8.0 → BWidget-1.9.0}/BWman/Entry.html +0 -0
  48. data/tcl/{BWidget-1.8.0 → BWidget-1.9.0}/BWman/Label.html +0 -0
  49. data/tcl/{BWidget-1.8.0 → BWidget-1.9.0}/BWman/LabelEntry.html +0 -0
  50. data/tcl/{BWidget-1.8.0 → BWidget-1.9.0}/BWman/LabelFrame.html +0 -0
  51. data/tcl/{BWidget-1.8.0 → BWidget-1.9.0}/BWman/ListBox.html +1 -1
  52. data/tcl/{BWidget-1.8.0 → BWidget-1.9.0}/BWman/MainFrame.html +8 -0
  53. data/tcl/{BWidget-1.8.0 → BWidget-1.9.0}/BWman/MessageDlg.html +0 -0
  54. data/tcl/{BWidget-1.8.0 → BWidget-1.9.0}/BWman/NoteBook.html +0 -0
  55. data/tcl/{BWidget-1.8.0 → BWidget-1.9.0}/BWman/PagesManager.html +0 -0
  56. data/tcl/{BWidget-1.8.0 → BWidget-1.9.0}/BWman/PanedWindow.html +21 -5
  57. data/tcl/{BWidget-1.8.0 → BWidget-1.9.0}/BWman/PanelFrame.html +0 -0
  58. data/tcl/{BWidget-1.8.0 → BWidget-1.9.0}/BWman/PasswdDlg.html +0 -0
  59. data/tcl/{BWidget-1.8.0 → BWidget-1.9.0}/BWman/ProgressBar.html +0 -0
  60. data/tcl/{BWidget-1.8.0 → BWidget-1.9.0}/BWman/ProgressDlg.html +0 -0
  61. data/tcl/{BWidget-1.8.0 → BWidget-1.9.0}/BWman/ScrollView.html +0 -0
  62. data/tcl/{BWidget-1.8.0 → BWidget-1.9.0}/BWman/ScrollableFrame.html +5 -2
  63. data/tcl/{BWidget-1.8.0 → BWidget-1.9.0}/BWman/ScrolledWindow.html +36 -4
  64. data/tcl/{BWidget-1.8.0 → BWidget-1.9.0}/BWman/SelectColor.html +0 -0
  65. data/tcl/{BWidget-1.8.0 → BWidget-1.9.0}/BWman/SelectFont.html +0 -0
  66. data/tcl/{BWidget-1.8.0 → BWidget-1.9.0}/BWman/Separator.html +0 -0
  67. data/tcl/{BWidget-1.8.0 → BWidget-1.9.0}/BWman/SpinBox.html +0 -0
  68. data/tcl/{BWidget-1.8.0 → BWidget-1.9.0}/BWman/StatusBar.html +0 -0
  69. data/tcl/{BWidget-1.8.0 → BWidget-1.9.0}/BWman/TitleFrame.html +0 -0
  70. data/tcl/{BWidget-1.8.0 → BWidget-1.9.0}/BWman/Tree.html +21 -31
  71. data/tcl/{BWidget-1.8.0 → BWidget-1.9.0}/BWman/Widget.html +0 -0
  72. data/tcl/{BWidget-1.8.0 → BWidget-1.9.0}/BWman/contents.html +0 -0
  73. data/tcl/{BWidget-1.8.0 → BWidget-1.9.0}/BWman/index.html +0 -0
  74. data/tcl/{BWidget-1.8.0 → BWidget-1.9.0}/BWman/navtree.html +0 -0
  75. data/tcl/{BWidget-1.8.0 → BWidget-1.9.0}/BWman/options.htm +0 -0
  76. data/tcl/{BWidget-1.8.0 → BWidget-1.9.0}/CHANGES.txt +0 -0
  77. data/tcl/{BWidget-1.8.0 → BWidget-1.9.0}/ChangeLog +289 -0
  78. data/tcl/{BWidget-1.8.0 → BWidget-1.9.0}/LICENSE.txt +0 -0
  79. data/tcl/{BWidget-1.8.0 → BWidget-1.9.0}/README.txt +2 -2
  80. data/tcl/{BWidget-1.8.0 → BWidget-1.9.0}/arrow.tcl +1 -1
  81. data/tcl/{BWidget-1.8.0 → BWidget-1.9.0}/bitmap.tcl +0 -0
  82. data/tcl/{BWidget-1.8.0 → BWidget-1.9.0}/button.tcl +0 -0
  83. data/tcl/{BWidget-1.8.0 → BWidget-1.9.0}/buttonbox.tcl +23 -12
  84. data/tcl/{BWidget-1.8.0 → BWidget-1.9.0}/color.tcl +0 -0
  85. data/tcl/{BWidget-1.8.0 → BWidget-1.9.0}/combobox.tcl +101 -25
  86. data/tcl/{BWidget-1.8.0 → BWidget-1.9.0}/demo/basic.tcl +0 -0
  87. data/tcl/{BWidget-1.8.0 → BWidget-1.9.0}/demo/bwidget.xbm +0 -0
  88. data/tcl/{BWidget-1.8.0 → BWidget-1.9.0}/demo/demo.tcl +1 -1
  89. data/tcl/{BWidget-1.8.0 → BWidget-1.9.0}/demo/dnd.tcl +0 -0
  90. data/tcl/{BWidget-1.8.0 → BWidget-1.9.0}/demo/manager.tcl +0 -0
  91. data/tcl/{BWidget-1.8.0 → BWidget-1.9.0}/demo/select.tcl +0 -0
  92. data/tcl/{BWidget-1.8.0 → BWidget-1.9.0}/demo/tmpldlg.tcl +0 -0
  93. data/tcl/{BWidget-1.8.0 → BWidget-1.9.0}/demo/tree.tcl +0 -0
  94. data/tcl/{BWidget-1.8.0 → BWidget-1.9.0}/demo/x1.xbm +0 -0
  95. data/tcl/{BWidget-1.8.0 → BWidget-1.9.0}/dialog.tcl +0 -0
  96. data/tcl/{BWidget-1.8.0 → BWidget-1.9.0}/dragsite.tcl +0 -0
  97. data/tcl/{BWidget-1.8.0 → BWidget-1.9.0}/dropsite.tcl +2 -1
  98. data/tcl/{BWidget-1.8.0 → BWidget-1.9.0}/dynhelp.tcl +194 -33
  99. data/tcl/{BWidget-1.8.0 → BWidget-1.9.0}/entry.tcl +8 -5
  100. data/tcl/{BWidget-1.8.0 → BWidget-1.9.0}/font.tcl +0 -0
  101. data/tcl/{BWidget-1.8.0 → BWidget-1.9.0}/images/bold.gif +0 -0
  102. data/tcl/{BWidget-1.8.0 → BWidget-1.9.0}/images/copy.gif +0 -0
  103. data/tcl/{BWidget-1.8.0 → BWidget-1.9.0}/images/cut.gif +0 -0
  104. data/tcl/{BWidget-1.8.0 → BWidget-1.9.0}/images/dragfile.gif +0 -0
  105. data/tcl/{BWidget-1.8.0 → BWidget-1.9.0}/images/dragicon.gif +0 -0
  106. data/tcl/{BWidget-1.8.0 → BWidget-1.9.0}/images/error.gif +0 -0
  107. data/tcl/{BWidget-1.8.0 → BWidget-1.9.0}/images/file.gif +0 -0
  108. data/tcl/{BWidget-1.8.0 → BWidget-1.9.0}/images/folder.gif +0 -0
  109. data/tcl/{BWidget-1.8.0 → BWidget-1.9.0}/images/hourglass.gif +0 -0
  110. data/tcl/{BWidget-1.8.0 → BWidget-1.9.0}/images/info.gif +0 -0
  111. data/tcl/{BWidget-1.8.0 → BWidget-1.9.0}/images/italic.gif +0 -0
  112. data/tcl/{BWidget-1.8.0 → BWidget-1.9.0}/images/minus.xbm +0 -0
  113. data/tcl/{BWidget-1.8.0 → BWidget-1.9.0}/images/new.gif +0 -0
  114. data/tcl/{BWidget-1.8.0 → BWidget-1.9.0}/images/opcopy.xbm +0 -0
  115. data/tcl/{BWidget-1.8.0 → BWidget-1.9.0}/images/open.gif +0 -0
  116. data/tcl/{BWidget-1.8.0 → BWidget-1.9.0}/images/openfold.gif +0 -0
  117. data/tcl/{BWidget-1.8.0 → BWidget-1.9.0}/images/oplink.xbm +0 -0
  118. data/tcl/{BWidget-1.8.0 → BWidget-1.9.0}/images/opmove.xbm +0 -0
  119. data/tcl/{BWidget-1.8.0 → BWidget-1.9.0}/images/overstrike.gif +0 -0
  120. data/tcl/{BWidget-1.8.0 → BWidget-1.9.0}/images/palette.gif +0 -0
  121. data/tcl/{BWidget-1.8.0 → BWidget-1.9.0}/images/passwd.gif +0 -0
  122. data/tcl/{BWidget-1.8.0 → BWidget-1.9.0}/images/paste.gif +0 -0
  123. data/tcl/{BWidget-1.8.0 → BWidget-1.9.0}/images/plus.xbm +0 -0
  124. data/tcl/{BWidget-1.8.0 → BWidget-1.9.0}/images/print.gif +0 -0
  125. data/tcl/{BWidget-1.8.0 → BWidget-1.9.0}/images/question.gif +0 -0
  126. data/tcl/{BWidget-1.8.0 → BWidget-1.9.0}/images/redo.gif +0 -0
  127. data/tcl/{BWidget-1.8.0 → BWidget-1.9.0}/images/save.gif +0 -0
  128. data/tcl/{BWidget-1.8.0 → BWidget-1.9.0}/images/target.xbm +0 -0
  129. data/tcl/{BWidget-1.8.0 → BWidget-1.9.0}/images/underline.gif +0 -0
  130. data/tcl/{BWidget-1.8.0 → BWidget-1.9.0}/images/undo.gif +0 -0
  131. data/tcl/{BWidget-1.8.0 → BWidget-1.9.0}/images/warning.gif +0 -0
  132. data/tcl/{BWidget-1.8.0 → BWidget-1.9.0}/init.tcl +0 -0
  133. data/tcl/{BWidget-1.8.0 → BWidget-1.9.0}/label.tcl +0 -0
  134. data/tcl/{BWidget-1.8.0 → BWidget-1.9.0}/labelentry.tcl +0 -0
  135. data/tcl/{BWidget-1.8.0 → BWidget-1.9.0}/labelframe.tcl +0 -0
  136. data/tcl/{BWidget-1.8.0 → BWidget-1.9.0}/lang/da.rc +0 -0
  137. data/tcl/{BWidget-1.8.0 → BWidget-1.9.0}/lang/de.rc +0 -0
  138. data/tcl/{BWidget-1.8.0 → BWidget-1.9.0}/lang/en.rc +0 -0
  139. data/tcl/{BWidget-1.8.0 → BWidget-1.9.0}/lang/es.rc +0 -0
  140. data/tcl/{BWidget-1.8.0 → BWidget-1.9.0}/lang/fr.rc +0 -0
  141. data/tcl/BWidget-1.9.0/lang/hu.rc +52 -0
  142. data/tcl/BWidget-1.9.0/lang/nl.rc +52 -0
  143. data/tcl/BWidget-1.9.0/lang/no.rc +52 -0
  144. data/tcl/{BWidget-1.8.0 → BWidget-1.9.0}/listbox.tcl +89 -34
  145. data/tcl/{BWidget-1.8.0 → BWidget-1.9.0}/mainframe.tcl +14 -13
  146. data/tcl/{BWidget-1.8.0 → BWidget-1.9.0}/messagedlg.tcl +0 -0
  147. data/tcl/{BWidget-1.8.0 → BWidget-1.9.0}/notebook.tcl +3 -1
  148. data/tcl/{BWidget-1.8.0 → BWidget-1.9.0}/pagesmgr.tcl +0 -0
  149. data/tcl/{BWidget-1.8.0 → BWidget-1.9.0}/panedw.tcl +22 -18
  150. data/tcl/{BWidget-1.8.0 → BWidget-1.9.0}/panelframe.tcl +0 -0
  151. data/tcl/{BWidget-1.8.0 → BWidget-1.9.0}/passwddlg.tcl +7 -3
  152. data/tcl/{BWidget-1.8.0 → BWidget-1.9.0}/pkgIndex.tcl +2 -2
  153. data/tcl/{BWidget-1.8.0 → BWidget-1.9.0}/progressbar.tcl +0 -0
  154. data/tcl/{BWidget-1.8.0 → BWidget-1.9.0}/progressdlg.tcl +0 -0
  155. data/tcl/{BWidget-1.8.0 → BWidget-1.9.0}/scrollframe.tcl +60 -24
  156. data/tcl/{BWidget-1.8.0 → BWidget-1.9.0}/scrollview.tcl +0 -0
  157. data/tcl/{BWidget-1.8.0 → BWidget-1.9.0}/scrollw.tcl +13 -11
  158. data/tcl/{BWidget-1.8.0 → BWidget-1.9.0}/separator.tcl +0 -0
  159. data/tcl/{BWidget-1.8.0 → BWidget-1.9.0}/spinbox.tcl +0 -0
  160. data/tcl/{BWidget-1.8.0 → BWidget-1.9.0}/statusbar.tcl +0 -0
  161. data/tcl/{BWidget-1.8.0 → BWidget-1.9.0}/tests/entry.test +0 -0
  162. data/tcl/{BWidget-1.8.0 → BWidget-1.9.0}/titleframe.tcl +0 -0
  163. data/tcl/{BWidget-1.8.0 → BWidget-1.9.0}/tree.tcl +51 -41
  164. data/tcl/{BWidget-1.8.0 → BWidget-1.9.0}/utils.tcl +26 -11
  165. data/tcl/{BWidget-1.8.0 → BWidget-1.9.0}/widget.tcl +53 -19
  166. data/tcl/{BWidget-1.8.0 → BWidget-1.9.0}/wizard.tcl +0 -0
  167. data/tcl/{BWidget-1.8.0 → BWidget-1.9.0}/xpm2image.tcl +0 -0
  168. metadata +170 -145
@@ -365,4 +365,4 @@ class Breakpoints < ArcadiaExt
365
365
  end
366
366
 
367
367
 
368
- end
368
+ end
@@ -2,11 +2,11 @@
2
2
  # ae-dir-projects.rb - Arcadia Ruby ide
3
3
  # by Antonio Galeone <antonio-galeone@rubyforge.org>
4
4
  #
5
- # §require_dir_ref=../..
6
- # §require_omissis=conf/arcadia.init
7
- # §require_omissis=lib/a-commons
8
- # §require_omissis=lib/a-tkcommons
9
- # §require_omissis=lib/a-core
5
+ # &require_dir_ref=../..
6
+ # &require_omissis=conf/arcadia.init
7
+ # &require_omissis=lib/a-commons
8
+ # &require_omissis=lib/a-tkcommons
9
+ # &require_omissis=lib/a-core
10
10
 
11
11
 
12
12
 
@@ -102,14 +102,14 @@ class DirProjects < ArcadiaExt
102
102
  _sync_val = @sync
103
103
  @sync = false
104
104
  begin
105
- Arcadia.process_event(OpenBufferTransientEvent.new(self,'file'=>node2file(_selected)))
106
- ensure
105
+ Arcadia.process_event(OpenBufferTransientEvent.new(self,'file'=>node2file(_selected)))
106
+ ensure
107
107
  @sync = _sync_val
108
- end
109
- elsif !_selected.nil? && @htree.open?(_selected)
110
- @htree.close_tree(_selected)
111
- elsif !_selected.nil?
112
- @htree.open_tree(_selected,false)
108
+ end
109
+ # elsif !_selected.nil? && @htree.open?(node2file(_selected))
110
+ # @htree.close_tree(node2file(_selected))
111
+ # elsif !_selected.nil?
112
+ # @htree.open_tree(node2file(_selected),false)
113
113
  end
114
114
  else
115
115
  shure_delete_node(_selected)
@@ -170,16 +170,29 @@ class DirProjects < ArcadiaExt
170
170
  _wrapper.show_v_scroll
171
171
  _wrapper.show_h_scroll
172
172
  self.pop_up_menu_tree
173
- @image_kdir = TkPhotoImage.new('dat' => BOOK_GIF)
173
+ @image_kdir = TkPhotoImage.new('dat' => ICON_FOLDER_OPEN_GIF)
174
174
  @image_kdir_closed = TkPhotoImage.new('dat' => FOLDER_GIF)
175
- @image_kfile_rb = TkPhotoImage.new('dat' => RUBY_DOCUMENT_GIF)
176
- @image_kfile = TkPhotoImage.new('dat' => DOCUMENT_GIF)
177
175
  self.load_projects
178
- @htree.areabind_append('KeyPress'){|e| key_press(e[1])}
176
+ @htree.areabind_append('KeyPress',proc{|k|
177
+ key_press(k)
178
+ },"%K")
179
+
180
+ do_double_click = proc{
181
+ _selected = @htree.selection_get[0]
182
+ if File.ftype(node2file(_selected)) == 'directory'
183
+ if !_selected.nil? && @htree.open?(node2file(_selected))
184
+ @htree.close_tree(node2file(_selected))
185
+ elsif !_selected.nil?
186
+ @htree.open_tree(node2file(_selected),false)
187
+ end
188
+ end
189
+ }
190
+
191
+ @htree.textbind_append('Double-1',do_double_click)
179
192
  end
180
193
 
181
- def key_press(_e)
182
- case _e.keysym
194
+ def key_press(_keysym)
195
+ case _keysym
183
196
  when 'F5'
184
197
  _selected = self.selected
185
198
  do_refresh(_selected)
@@ -199,7 +212,7 @@ class DirProjects < ArcadiaExt
199
212
  end
200
213
 
201
214
  def file2node(_file)
202
- if _file.include?("\s")
215
+ if _file.include?("\s") && _file[0..0]!='{'
203
216
  return "{#{_file}}"
204
217
  else
205
218
  return _file
@@ -297,7 +310,6 @@ class DirProjects < ArcadiaExt
297
310
  :hidemargin => false,
298
311
  :command=> proc{
299
312
  _selected = self.selected
300
- p _selected
301
313
  if _selected
302
314
  do_new_folder(_selected)
303
315
  end
@@ -362,6 +374,47 @@ class DirProjects < ArcadiaExt
362
374
  )
363
375
 
364
376
 
377
+ #-----------------
378
+ #----- search submenu
379
+ sub_ref_search = TkMenu.new(
380
+ :parent=>@pop_up,
381
+ :tearoff=>0,
382
+ :title => 'Ref'
383
+ )
384
+ sub_ref_search.configure(Arcadia.style('menu'))
385
+ sub_ref_search.insert('end',
386
+ :command,
387
+ :label=>'Find in files...',
388
+ :hidemargin => false,
389
+ :command=> proc{
390
+ _target = self.selected
391
+ if _target
392
+ _target = File.dirname(_target) if File.ftype(_target) == 'file'
393
+ Arcadia.process_event(SearchInFilesEvent.new(self,'dir'=>_target))
394
+ end
395
+ }
396
+ )
397
+
398
+ sub_ref_search.insert('end',
399
+ :command,
400
+ :label=>'Act in files...',
401
+ :hidemargin => false,
402
+ :command=> proc{
403
+ _target = self.selected
404
+ if _target
405
+ _target = File.dirname(_target) if File.ftype(_target) == 'file'
406
+ Arcadia.process_event(AckInFilesEvent.new(self,'dir'=>_target))
407
+ end
408
+ }
409
+ )
410
+ @pop_up_tree.insert('end',
411
+ :cascade,
412
+ :label=>'Search from here',
413
+ :menu=>sub_ref_search,
414
+ :hidemargin => false
415
+ )
416
+
417
+
365
418
  #-----------------
366
419
 
367
420
  @pop_up_tree.insert('end',
@@ -412,21 +465,28 @@ class DirProjects < ArcadiaExt
412
465
  end
413
466
 
414
467
  def selected
415
- if @htree.selection_get[0].length >0
416
- _selected = ""
417
- @htree.selection_get[0].each{|_block|
418
- _selected = _selected + _block.to_s + "\s"
419
- }
420
- _selected = _selected.strip
421
- else
422
- _selected = @htree.selection_get[0]
468
+ if @htree.selection_get[0]
469
+ if @htree.selection_get[0].length >0
470
+ _selected = ""
471
+ if String.method_defined?(:lines)
472
+ selection_lines = @htree.selection_get[0].lines
473
+ else
474
+ selection_lines = @htree.selection_get[0].split("\n")
475
+ end
476
+ selection_lines.each{|_block|
477
+ _selected = _selected + _block.to_s + "\s"
478
+ }
479
+ _selected = _selected.strip
480
+ else
481
+ _selected = @htree.selection_get[0]
482
+ end
423
483
  end
424
484
  return _selected
425
485
  end
426
486
 
427
487
  def do_new_project(_parent_folder_node=nil)
428
488
  if _parent_folder_node.nil?
429
- _parent_folder_node=Tk.chooseDirectory
489
+ _parent_folder_node=Tk.chooseDirectory 'initialdir' => MonitorLastUsedDir.get_last_dir
430
490
  end
431
491
  if _parent_folder_node && File.exists?(node2file(_parent_folder_node)) && File.ftype(node2file(_parent_folder_node)) == 'directory'
432
492
  tmp_node_name = "#{node2file(_parent_folder_node)}#{File::SEPARATOR}_new_project_"
@@ -444,7 +504,7 @@ class DirProjects < ArcadiaExt
444
504
  ensure
445
505
  @htree.delete(file2node(tmp_node_name))
446
506
  end
447
- return _ret
507
+ _ret
448
508
  }
449
509
  # @htree.textbind('KeyPress', proc{|e|
450
510
  # p 'pippo'})
@@ -455,13 +515,13 @@ class DirProjects < ArcadiaExt
455
515
 
456
516
  def do_open_project(_proj_name=nil)
457
517
  if _proj_name.nil?
458
- _proj_name=Tk.chooseDirectory
518
+ _proj_name=Tk.chooseDirectory 'initialdir' => MonitorLastUsedDir.get_last_dir
459
519
  add_project(_proj_name) if _proj_name && File.exists?(_proj_name)
460
520
  end
461
521
  end
462
522
 
463
523
  def do_close_project(_proj_name)
464
- if _proj_name
524
+ if _proj_name && is_project?(_proj_name)
465
525
  del_project(_proj_name)
466
526
  end
467
527
  end
@@ -484,7 +544,7 @@ class DirProjects < ArcadiaExt
484
544
  @htree.delete(file2node(tmp_node_name))
485
545
  shure_select_node(new_dir_name)
486
546
  end
487
- return _ret
547
+ _ret
488
548
  }
489
549
  @htree.edit(tmp_node_name, tmp_node_name.split(File::SEPARATOR)[-1], _verify_cmd, 1)
490
550
  end
@@ -508,7 +568,7 @@ class DirProjects < ArcadiaExt
508
568
  ensure
509
569
  @htree.delete(file2node(tmp_node_name))
510
570
  end
511
- return _ret
571
+ _ret
512
572
  }
513
573
  @htree.edit(tmp_node_name, tmp_node_name.split(File::SEPARATOR)[-1], _verify_cmd, 1)
514
574
  end
@@ -604,12 +664,16 @@ class DirProjects < ArcadiaExt
604
664
  shure_delete_node(_source)
605
665
  do_refresh(source_dir)
606
666
  end
607
- return _ret
667
+ _ret
608
668
  }
609
669
  @htree.edit(_source, _source.split(File::SEPARATOR)[-1], _verify_cmd, 1)
610
670
  end
611
671
  end
612
672
 
673
+ def is_project?(_node)
674
+ @htree.exist?(_node) && @htree.parent(_node)=='root'
675
+ end
676
+
613
677
  def do_delete(_node, _interactive = true)
614
678
  if File.exists?(node2file(_node))
615
679
  type = File.ftype(node2file(_node))
@@ -624,7 +688,7 @@ class DirProjects < ArcadiaExt
624
688
  entries = Dir.entries(node2file(_node))
625
689
  entries.delete('.')
626
690
  entries.delete('..')
627
- is_project = @htree.exist?(_node) && @htree.parent(_node)=='root'
691
+ #is_project = @htree.exist?(_node) && @htree.parent(_node)=='root'
628
692
  if entries.length > 0
629
693
  _msg2 = "#{_node} isn't empty. Shure to delete all sub entries ?"
630
694
  entries.each{|en|
@@ -641,7 +705,7 @@ class DirProjects < ArcadiaExt
641
705
  else
642
706
  Dir.delete(node2file(_node))
643
707
  end
644
- if is_project && delete_node
708
+ if is_project?(_node) && delete_node
645
709
  delete_node = false
646
710
  del_project(_node)
647
711
  end
@@ -703,8 +767,8 @@ class DirProjects < ArcadiaExt
703
767
  end
704
768
 
705
769
  def add_project(_dir)
706
- add_node('root', _dir, "project")
707
770
  @projects[_dir] = Project.new(_dir)
771
+ add_node('root', _dir, "project")
708
772
  add_project_to_file(_dir)
709
773
  end
710
774
 
@@ -713,7 +777,7 @@ class DirProjects < ArcadiaExt
713
777
  _sc = @htree.cget('selectcommand')
714
778
  begin
715
779
  @htree.configure('selectcommand'=>nil)
716
- @htree.delete(_node)
780
+ @htree.delete(file2node(_node))
717
781
  ensure
718
782
  @htree.configure('selectcommand'=>_sc)
719
783
  end
@@ -834,7 +898,7 @@ class DirProjects < ArcadiaExt
834
898
  path = File::SEPARATOR
835
899
  end
836
900
  path = path + steps[j]
837
- if @htree.exist?(path)
901
+ if @htree.exist?(path)
838
902
  @htree.open_tree(path, false)
839
903
  end
840
904
  j=j+1
@@ -869,12 +933,16 @@ class DirProjects < ArcadiaExt
869
933
  return @image_kdir
870
934
  elsif _kind == 'project'
871
935
  return @image_kdir_closed
872
- elsif _kind == 'file' && _label.include?('.rb')
873
- return @image_kfile_rb
874
- else
875
- return @image_kfile
936
+ elsif _kind == 'file'
937
+ return Arcadia.file_icon(_label)
876
938
  end
939
+
940
+ # elsif _kind == 'file' && _label.include?('.rb')
941
+ # return @image_kfile_rb
942
+ # else
943
+ # return @image_kfile
944
+ # end
877
945
  end
878
946
 
879
947
 
880
- end
948
+ end
@@ -2,10 +2,14 @@ name=editor
2
2
  frames=0.1,0.2
3
3
  frames.labels=Editor,Outline
4
4
  frames.names=editor,editor_outline
5
+ # attention : editor_outline name is used in code. Do no change it
5
6
  active=yes
6
7
  require=ext/ae-editor/ae-editor
7
8
  class=AgMultiEditor
8
-
9
+ #gems=coderay
10
+ gems=coderay,rdp-rbeautify
11
+ gems.rdp-rbeautify.repository=http://gems.github.com
12
+ gems.rdp-rbeautify.events=PrettifyTextEvent
9
13
  tabs=0.5c left
10
14
  # to use tab key set tab-replace-width-space=0
11
15
  tab-replace-width-space=2
@@ -131,4 +135,4 @@ explorer_panel.tabs.side=top
131
135
 
132
136
  #:::::::::::::::: Editor group ::::::::::::::::::::::<end>
133
137
  popup.bind.shortcut=Button-3
134
- arm::popup.bind.shortcut=F4
138
+ arm::popup.bind.shortcut=F4
@@ -2,13 +2,13 @@
2
2
  # ae-editor.rb - Arcadia Ruby ide
3
3
  # by Antonio Galeone <antonio-galeone@rubyforge.org>
4
4
  #
5
- # §require_dir_ref=../..
6
- # §require_omissis=conf/arcadia.init
5
+ # &require_dir_ref=../..
6
+ # &require_omissis=conf/arcadia.init
7
7
 
8
8
  require 'tk'
9
9
  require 'tktext'
10
10
  require 'lib/a-tkcommons'
11
- #require 'lib/a-commons'
11
+ #require 'lib/a-commons'
12
12
  require 'lib/a-core'
13
13
 
14
14
  class TreeNode
@@ -183,6 +183,19 @@ class SourceStructure
183
183
  return _found_node
184
184
  end
185
185
 
186
+ def deep_node_by_line(_from_node, _line, _found_node=nil)
187
+ _begin = _from_node.rif.to_i
188
+ _end = _from_node.rif_end.to_i
189
+ if _line.to_i <= _end && _line.to_i >= _begin
190
+ _found_node = _from_node
191
+ end
192
+ _sons = _from_node.sons
193
+ for inode in 0.._sons.length - 1
194
+ _son = _sons[inode]
195
+ _found_node = deep_node_by_line(_son, _line, _found_node)
196
+ end
197
+ return _found_node
198
+ end
186
199
 
187
200
  def class_node_by_line(_line)
188
201
  line_node = node_by_line(@root, _line)
@@ -254,7 +267,7 @@ class SafeCompleteCode
254
267
  if _dec_line.include?('.new')
255
268
  pre, post = _dec_line.split('.new')
256
269
  dec_line_processed = "#{pre}.new"
257
- post.strip!
270
+ post.strip! if post
258
271
  if post && post[0..0]=='('
259
272
  k=0
260
273
  ch = '('
@@ -290,10 +303,13 @@ class SafeCompleteCode
290
303
 
291
304
  def refresh_words
292
305
  @words.clear
293
- _re = /[\s\t\n]#{@filter}[a-zA-Z0-9\-_]*/
306
+ _re = /[\s\t\n"'(\[\{=><]#{@filter}[a-zA-Z0-9\-_]*/
294
307
  m = _re.match(@source)
295
308
  while m && (_txt=m.post_match)
296
309
  can = m[0].strip
310
+ if ['"','(','[','{',"'",'=','>','<'].include?(can[0..0])
311
+ can = can[1..-1]
312
+ end
297
313
  @words << can if can != @filter
298
314
  m = _re.match(_txt)
299
315
  end
@@ -334,18 +350,18 @@ class SafeCompleteCode
334
350
  @modified_source = "#{@modified_source}Dir.chdir('#{File.dirname(@file)}')\n" if @file
335
351
  @modified_row = @modified_row+1
336
352
  source_array.each_with_index{|line,j|
337
- # 0) se è un commento non lo prendo in considerazione
353
+ # 0) if a comment I do not consider it
338
354
  if line.strip.length > 0 && line.strip[0..0]=='#'
339
355
  @modified_row = @modified_row-1
340
- m = require_dir_ref=[\s]*(.)*/.match(line)
356
+ m = /&require_dir_ref=[\s]*(.)*/.match(line)
341
357
  if m
342
- require_dir_ref=line.split('§require_dir_ref=')[1].strip
358
+ require_dir_ref=line.split('&require_dir_ref=')[1].strip
343
359
  @modified_source = "#{@modified_source}Dir.chdir('#{require_dir_ref}')\n"
344
360
  @modified_row = @modified_row+1
345
361
  end
346
- m = require_omissis=[\s]*(.)*/.match(line)
362
+ m = /&require_omissis=[\s]*(.)*/.match(line)
347
363
  if m
348
- require_omissis=line.split('§require_omissis=')[1].strip
364
+ require_omissis=line.split('&require_omissis=')[1].strip
349
365
  @modified_source = "#{@modified_source}require '#{require_omissis}'\n"
350
366
  @modified_row = @modified_row+1
351
367
  end
@@ -439,7 +455,7 @@ class SafeCompleteCode
439
455
  @modified_row = @modified_row+1+ss_len
440
456
  end
441
457
  end
442
- if @filter.strip.length > 0
458
+ if @filter.strip.length > 0 && !is_dot?
443
459
  # refresh_words(source_array)
444
460
  refresh_words
445
461
  end
@@ -472,18 +488,19 @@ class SafeCompleteCode
472
488
  def candidates(_show_error = false)
473
489
  temp_file = create_modified_temp_file(@file)
474
490
  begin
475
- _cmp_s = "|ruby '#{temp_file}'"
491
+ Arcadia.is_windows??ruby='rubyw':ruby='ruby'
492
+ _cmp_s = "|#{ruby} '#{temp_file}'"
476
493
  _ret = nil
477
494
  open(_cmp_s,"r") do
478
495
  |f|
479
496
  _ret = f.readlines.collect!{| line |
480
497
  #line.chomp
481
- line
498
+ line.strip
482
499
  }
483
500
  end
484
- if @filter.strip.length > 0
501
+ if @filter.strip.length > 0 && !is_dot?
485
502
  @words.each{|w|
486
- if !_ret.include?(w) # && w[0..@filter.length-1] == @filter
503
+ if !(_ret.include?(w) || _ret.include?("##{w}"))
487
504
  _ret << w
488
505
  end
489
506
  }
@@ -608,80 +625,133 @@ class TkTextListBox < TkScrollText
608
625
 
609
626
  end
610
627
 
611
-
612
- class AgEditor
613
- include Configurable
614
- attr_accessor :file
615
- attr_reader :read_only
616
- attr_reader :page_frame
617
- attr_reader :text, :root
618
- def initialize(_controller, _page_frame)
628
+ class AgEditorOutlineToolbar
629
+ attr_accessor :sync
630
+ def initialize(_frame, _controller)
619
631
  @controller = _controller
620
- @page_frame = _page_frame
621
- @set_mod = false
622
- @modified_from_opening=false
623
- # @font = @controller.conf('font')
624
- # @font_bold = @controller.conf('font.bold')
625
- @font = Arcadia.conf('edit.font')
626
- @font_bold = "#{Arcadia.conf('edit.font')} bold"
627
- @font_metrics = TkFont.new(@font).metrics
628
- @font_metrics_bold = TkFont.new(@font_bold).metrics
629
- @highlighting = false
630
- @classbrowsing = false
631
- @find = @controller.get_find
632
- @read_only=false
633
- @loading=false
632
+ @cb_sync = TkCheckButton.new(_frame, Arcadia.style('checkbox')){
633
+ text 'Sync'
634
+ justify 'left'
635
+ indicatoron 0
636
+ offrelief 'raised'
637
+ image TkPhotoImage.new('dat' => SYNCICON20_GIF)
638
+ place('x' => 0,'y' => 0,'height' => 26)
639
+ }
640
+ Tk::BWidget::DynamicHelp::add(@cb_sync,
641
+ 'text'=>'Link open editors with content in the Navigator')
642
+
643
+ do_check = proc {
644
+ if @cb_sync.cget('onvalue')==@cb_sync.cget('variable').value.to_i
645
+ sync_on
646
+ else
647
+ sync_off
648
+ end
649
+ }
650
+ @sync = false
651
+ @cb_sync.command(do_check)
634
652
  end
635
-
636
- # def hide_exp
637
- # @fm.hide_left if @fm
638
- # end
639
-
640
- # def is_exp_hide?
641
- # if @fm.nil?
642
- # return true
643
- # else
644
- # @fm.is_left_hide?
645
- # end
646
- # end
647
653
 
648
- def modified_from_opening?
649
- @modified_from_opening
654
+ def sync_on
655
+ @sync = true
656
+ e = @controller.raised
657
+ if e
658
+ e.outline.select_without_event(e.outline.last_row) if e.outline.last_row
659
+ end
650
660
  end
651
-
652
- def xy_insert
653
- _index_now = @text.index('insert')
654
- _rx, _ry, _widht, _heigth = @text.bbox(_index_now);
655
- _x = _rx + TkWinfo.rootx(@text)
656
- _y = _ry + TkWinfo.rooty(@text) + @font_metrics[2][1]
657
- _xroot = _x - TkWinfo.rootx(Arcadia.instance.layout.root)
658
- _yroot = _y - TkWinfo.rooty(Arcadia.instance.layout.root)
659
- return _xroot, _yroot
661
+
662
+ def sync_off
663
+ @sync = false
664
+ end
665
+
666
+ def is_sync_on?
667
+ @sync
668
+ end
669
+
670
+ end
671
+
672
+ class AgEditorOutline
673
+ attr_reader :last_row
674
+ attr_reader :tree_exp
675
+ def initialize(_editor, _frame, _bar)
676
+ @editor = _editor
677
+ @frame = _frame
678
+ @bar = _bar
679
+ initialize_tree(_frame)
680
+ end
681
+
682
+ def update_row(_row=0)
683
+ @last_row=_row
684
+ if @bar.is_sync_on?
685
+ select_without_event(_row)
686
+ end
660
687
  end
661
688
 
662
-
689
+ # I think this is "if synced expand out the outline for the current selection"
690
+ def shure_select_node(_node)
691
+ return if @selecting_node
692
+ #return if @tree_exp.exist?(_node.rif)
693
+ @selecting_node = true
694
+ _proc = @tree_exp.selectcommand
695
+ @tree_exp.selectcommand(nil)
696
+ begin
697
+ @tree_exp.selection_clear
698
+ @tree_exp.selection_add(_node.rif)
699
+ @opened = false
700
+ to_open = @last_open_node
701
+ parent = _node.parent
702
+ while !parent.nil? && parent.rif != 'root'
703
+ @tree_exp.open_tree(parent.rif, false)
704
+ @opened = to_open==parent.rif || @opened
705
+ @last_open_node=parent.rif
706
+ parent = parent.parent
707
+ end
708
+
709
+ @tree_exp.close_tree(to_open) if to_open && !@opened
710
+
711
+ @tree_exp.see(_node.rif)
712
+ ensure
713
+ @tree_exp.selectcommand(_proc)
714
+ @selecting_node = false
715
+ end
716
+ end
717
+
718
+ def select_without_event(_line)
719
+ if @ss
720
+ _node=@ss.deep_node_by_line(@ss.root, _line)
721
+ if _node && @tree_exp.exist?(_node.rif) && _node.rif!='root'
722
+ shure_select_node(_node)
723
+ end
724
+ end
725
+ end
726
+
663
727
  def initialize_tree(_frame)
664
- @classbrowsing = @is_ruby
665
728
  _tree_goto = proc{|_self|
666
- _line = _self.selection_get[0]
667
- _index =_line.to_s+'.0'
668
- _hinner_text = @tree_exp.itemcget(_line,'text').strip
669
- _editor_line = @text.get(_index, _index+ ' lineend')
670
- if !_editor_line.include?(_hinner_text)
671
- Arcadia.console(self, 'msg'=>"... rebuild tree \n")
672
- if @tree_thread && @tree_thread.alive?
673
- @tree_thread.exit
674
- end
675
- @tree_thread = Thread.new{
676
- build_tree(_line)
677
- Tk.update
678
- }
729
+ sync_val = @bar.sync
730
+ @bar.sync=false
731
+ begin
679
732
  _line = _self.selection_get[0]
680
733
  _index =_line.to_s+'.0'
734
+ _hinner_text = @tree_exp.itemcget(_line,'text').strip
735
+ _editor_line = @editor.text.get(_index, _index+ ' lineend')
736
+ if !_editor_line.include?(_hinner_text)
737
+ Arcadia.console(self, 'msg'=>"... rebuild tree \n")
738
+ if @tree_thread && @tree_thread.alive?
739
+ @tree_thread.exit # kill the old tree
740
+ end
741
+ @tree_thread = Thread.new{
742
+ build_tree(_line)
743
+ Tk.update
744
+ }
745
+ _line = _self.selection_get[0]
746
+ _index =_line.to_s+'.0'
747
+ end
748
+ @editor.text.set_focus
749
+ @editor.text.see(_index)
750
+ @editor.text.tag_remove('selected','1.0','end')
751
+ @editor.text.tag_add('selected',_line.to_s+'.0',(_line+1).to_s+'.0')
752
+ ensure
753
+ @bar.sync = sync_val
681
754
  end
682
- @text.see(_index)
683
- @text.tag_remove('selected','1.0','end')
684
- @text.tag_add('selected',_line.to_s+'.0',(_line+1).to_s+'.0')
685
755
  }
686
756
  @tree_exp = Tk::BWidget::Tree.new(_frame, Arcadia.style('treepanel')){
687
757
  showlines false
@@ -690,12 +760,87 @@ class AgEditor
690
760
  selectcommand proc{ _tree_goto.call(self) }
691
761
  }
692
762
  @tree_scroll_wrapper = TkScrollWidget.new(@tree_exp)
693
- @tree_scroll_wrapper.show
763
+ self.show
694
764
  @tree_scroll_wrapper.show_v_scroll
695
765
  @tree_scroll_wrapper.show_h_scroll
696
766
  pop_up_menu_tree
697
767
  end
698
768
 
769
+ def destroy
770
+ @tree_scroll_wrapper.destroy
771
+ @tree_exp.destroy
772
+ end
773
+
774
+ def show
775
+ @tree_scroll_wrapper.show(0,26)
776
+ Tk.update
777
+ end
778
+
779
+ def hide
780
+ @tree_scroll_wrapper.hide
781
+ end
782
+
783
+ def build_tree_from_node(_node, _label_match=nil)
784
+ @image_kclass = TkPhotoImage.new('dat' => TREE_NODE_CLASS_GIF)
785
+ @image_kmodule = TkPhotoImage.new('dat' => TREE_NODE_MODULE_GIF)
786
+ @image_kdef = TkPhotoImage.new('dat' => TREE_NODE_DEF_GIF)
787
+ @image_kdefclass = TkPhotoImage.new('dat' => TREE_NODE_DEFCLASS_GIF)
788
+
789
+ _sorted_sons = _node.sons.sort
790
+ for inode in 0.._sorted_sons.length - 1
791
+ _son = _sorted_sons[inode]
792
+ if _son.kind == 'KClass'
793
+ _image = @image_kclass
794
+ elsif _son.kind == 'KModule'
795
+ _image = @image_kmodule
796
+ elsif _son.kind == 'KDef'
797
+ _image = @image_kdef
798
+ elsif _son.kind == 'KDefClass'
799
+ _image = @image_kdefclass
800
+ end
801
+ @tree_exp.insert('end', _son.parent.rif ,_son.rif, {
802
+ 'text' => _son.label ,
803
+ 'helptext' => _son.helptext,
804
+ #'font'=>$arcadia['conf']['editor.explorer_panel.tree.font'],
805
+ 'image'=> _image
806
+ }.update(Arcadia.style('treeitem'))
807
+ )
808
+ if (_label_match) && (_label_match.strip == _son.label.strip)
809
+ @selected = _son
810
+ end
811
+ build_tree_from_node(_son, _label_match) # recursion -- if there are no sons it will do nothing
812
+ end
813
+ end
814
+
815
+ def build_tree(_sel=nil)
816
+ #Arcadia.console(self,"msg"=>"build for #{@file}")
817
+ if _sel
818
+ _label_sel = @tree_exp.itemcget(_sel,'text')
819
+ end
820
+
821
+ #clear tree
822
+ begin
823
+ @tree_exp.delete(@tree_exp.nodes('root'))
824
+ rescue Exception
825
+ # workaround on windows
826
+ @tree_exp.delete(@tree_exp.nodes('root'))
827
+ end
828
+
829
+
830
+ #(re)build tree
831
+ _txt = @editor.text.get('1.0','end')
832
+ #@root = build_tree_from_source(_txt)
833
+ @ss = SourceStructure.new(_txt)
834
+ #@root = @ss.root
835
+ @selected = nil
836
+ build_tree_from_node(@ss.root, _label_sel)
837
+ if @selected
838
+ @tree_exp.selection_add(@selected.rif)
839
+ @tree_exp.open_tree(@selected.parent.rif)
840
+ @tree_exp.see(@selected.rif)
841
+ end
842
+ end
843
+
699
844
  def pop_up_menu_tree
700
845
  @pop_up_tree = TkMenu.new(
701
846
  :parent=>@tree_exp,
@@ -717,7 +862,48 @@ class AgEditor
717
862
  },
718
863
  "%x %y")
719
864
  end
865
+
866
+ end
720
867
 
868
+ class AgEditor
869
+ attr_accessor :file
870
+ attr_reader :read_only
871
+ attr_reader :page_frame
872
+ attr_reader :text, :root
873
+ attr_reader :outline
874
+ attr_reader :highlighting
875
+ def initialize(_controller, _page_frame)
876
+ @controller = _controller
877
+ @page_frame = _page_frame
878
+ @set_mod = false
879
+ @modified_from_opening=false
880
+ @font = Arcadia.conf('edit.font')
881
+ @font_bold = "#{Arcadia.conf('edit.font')} bold"
882
+ @font_metrics = TkFont.new(@font).metrics
883
+ @font_metrics_bold = TkFont.new(@font_bold).metrics
884
+ @highlighting = false
885
+ @classbrowsing = false
886
+ @find = @controller.get_find
887
+ @read_only=false
888
+ @loading=false
889
+ @tabs_show = false
890
+ @spaces_show = false
891
+ end
892
+
893
+ def modified_from_opening?
894
+ @modified_from_opening
895
+ end
896
+
897
+ def xy_insert
898
+ _index_now = @text.index('insert')
899
+ _rx, _ry, _widht, _heigth = @text.bbox(_index_now);
900
+ _x = _rx + TkWinfo.rootx(@text)
901
+ _y = _ry + TkWinfo.rooty(@text) + @font_metrics[2][1]
902
+ _xroot = _x - TkWinfo.rootx(Arcadia.instance.layout.root)
903
+ _yroot = _y - TkWinfo.rooty(Arcadia.instance.layout.root)
904
+ return _xroot, _yroot
905
+ end
906
+
721
907
 
722
908
  def initialize_text(_frame)
723
909
  @text = TkScrollText.new(_frame, Arcadia.style('text')){|j|
@@ -733,6 +919,14 @@ class AgEditor
733
919
  tabs $arcadia['conf']['editor.tabs']
734
920
  }
735
921
 
922
+ class << @text
923
+ def tag_adds(tag, *args)
924
+ tk_send_without_enc('tag', 'add', _get_eval_enc_str(tag),
925
+ *args.flatten)
926
+ self
927
+ end
928
+ end
929
+
736
930
  #do_tag_configure_global('debug')
737
931
  @text.tag_configure('eval','foreground' => 'yellow', 'background' =>'red','borderwidth'=>1, 'relief'=>'raised')
738
932
  @text.tag_configure('errline','borderwidth'=>1, 'relief'=>'groove')
@@ -749,7 +943,11 @@ class AgEditor
749
943
  if @file
750
944
  _file = @file+'~~'
751
945
  else
752
- _file = File.join(Arcadia.instance.local_dir,'buffer~~')
946
+ n=0
947
+ while File.exist?(File.join(Arcadia.instance.local_dir,"buffer#{n}~~"))
948
+ n+=1
949
+ end
950
+ _file = File.join(Arcadia.instance.local_dir,"buffer#{n}~~")
753
951
  end
754
952
  f = File.new(_file, "w")
755
953
  begin
@@ -1125,6 +1323,9 @@ class AgEditor
1125
1323
 
1126
1324
  end
1127
1325
 
1326
+ #
1327
+ # setup all key bindings (normal, +control, etc)
1328
+ #
1128
1329
  def activate_key_binding
1129
1330
  activate_complete_code_key_binding if @is_ruby
1130
1331
  @text.bind_append("Control-KeyPress"){|e|
@@ -1133,20 +1334,25 @@ class AgEditor
1133
1334
  # @do_complete = true
1134
1335
  # complete_code.call
1135
1336
  when 'z'
1136
- _b = @text.index('insert').split('.')[0].to_i
1137
- @text.edit_undo
1138
- _e = @text.index('insert').split('.')[0].to_i
1337
+ #_b = @text.index('insert').split('.')[0].to_i
1338
+ begin
1339
+ @text.edit_undo
1340
+ rescue RuntimeError => e
1341
+ throw e unless e.to_s.include? "nothing to undo" # this is ok--we've done undo back to the beginning
1342
+ break
1343
+ end
1344
+ #_e = @text.index('insert').split('.')[0].to_i
1139
1345
  if @highlighting
1140
- for j in _b..._e
1141
- rehighlightline(j)
1142
- end
1346
+ _b = @text.index('@0,0').split('.')[0].to_i
1347
+ _e = @text.index('@0,'+TkWinfo.height(@text).to_s).split('.')[0].to_i + 1
1348
+ rehighlightlines(_b,_e)
1143
1349
  end
1144
1350
  break
1145
1351
  when 'o'
1146
1352
  if @file
1147
1353
  _dir = File.dirname(@file)
1148
1354
  else
1149
- _dir = Dir.pwd
1355
+ _dir = MonitorLastUsedDir.get_last_dir
1150
1356
  end
1151
1357
  Arcadia.process_event(OpenBufferEvent.new(self,'file'=>Tk.getOpenFile('initialdir'=>_dir)))
1152
1358
  break
@@ -1161,9 +1367,10 @@ class AgEditor
1161
1367
  @text.text_paste
1162
1368
  _e = @text.index('insert').split('.')[0].to_i
1163
1369
  if @highlighting
1164
- for j in _b..._e
1165
- rehighlightline(j)
1166
- end
1370
+ rehighlightlines(_b,_e)
1371
+ # for j in _b..._e
1372
+ # rehighlightline(j)
1373
+ # end
1167
1374
  end
1168
1375
  break
1169
1376
  end
@@ -1176,6 +1383,12 @@ class AgEditor
1176
1383
  @text.insert('insert',"{")
1177
1384
  when 'plus'
1178
1385
  @text.insert('insert',"}")
1386
+ when 'g'
1387
+ Arcadia.process_event(GoToLineBufferEvent.new(self))
1388
+ when 'n'
1389
+ $arcadia['main.action.new_file'] # necessary? Is there an event for this?
1390
+ when 'w'
1391
+ Arcadia.process_event(CloseCurrentTabEvent.new(self))
1179
1392
  end
1180
1393
  }
1181
1394
 
@@ -1222,9 +1435,11 @@ class AgEditor
1222
1435
  else
1223
1436
  @text.insert(_row.to_s+'.0',"#")
1224
1437
  end
1225
- rehighlightline(_row) if @highlighting
1438
+ #rehighlightline(_row) if @highlighting
1226
1439
  end
1227
-
1440
+ rehighlightlines(_row_begin, _row_end) if @highlighting
1441
+ when 'F'
1442
+ Arcadia.process_event(AckInFilesEvent.new(self))
1228
1443
  end
1229
1444
  }
1230
1445
 
@@ -1235,11 +1450,13 @@ class AgEditor
1235
1450
  when 'BackSpace'
1236
1451
  _index = @text.index('insert')
1237
1452
  _row, _col = _index.split('.')
1238
- rehighlightline(_row.to_i) if @highlighting
1453
+ rehighlightlines(_row.to_i,_row.to_i) if @highlighting
1454
+ # rehighlightline(_row.to_i) if @highlighting
1239
1455
  when 'Delete'
1240
1456
  _index = @text.index('insert')
1241
1457
  _row, _col = _index.split('.')
1242
- rehighlightline(_row.to_i) if @highlighting
1458
+ rehighlightlines(_row.to_i, _row.to_i) if @highlighting
1459
+ # rehighlightline(_row.to_i) if @highlighting
1243
1460
  when 'F5'
1244
1461
  run_buffer
1245
1462
  when 'F3'
@@ -1278,16 +1495,11 @@ class AgEditor
1278
1495
 
1279
1496
  @text.bind_append("KeyRelease"){|e|
1280
1497
  case e.keysym
1281
- # when 'period'
1282
- # @do_complete = true
1283
- # #Thread.new do
1284
- # complete_code.call
1285
- # #end
1286
- when 'Control_L','Return', 'Control_V', 'BackSpace', 'Delete'
1287
- do_line_update
1288
- end
1289
- case e.keysym
1290
- when 'Return'
1498
+ when 'Up','Down'
1499
+ refresh_outline
1500
+ when 'Left', 'Right'
1501
+
1502
+ when 'Return' #,'Control_L', 'Control_V', 'BackSpace', 'Delete'
1291
1503
  _index = @text.index('insert')
1292
1504
  _row, _col = _index.split('.')
1293
1505
  _txt = @text.get((_row.to_i-1).to_s+'.0',_index)
@@ -1305,8 +1517,13 @@ class AgEditor
1305
1517
  do_line_update
1306
1518
  end
1307
1519
  else
1520
+ if ['Control_L', 'Control_V', 'BackSpace', 'Delete'].include?(e.keysym)
1521
+ do_line_update
1522
+ end
1308
1523
  if @highlighting && /\w/.match(e.keysym)
1309
- rehighlightline(@text.index('insert').split('.')[0].to_i)
1524
+ # rehighlightline(@text.index('insert').split('.')[0].to_i)
1525
+ row = @text.index('insert').split('.')[0].to_i
1526
+ rehighlightlines(row, row)
1310
1527
  end
1311
1528
  end
1312
1529
  check_modify
@@ -1339,6 +1556,7 @@ class AgEditor
1339
1556
  }
1340
1557
  end
1341
1558
 
1559
+ # show the "find in file" dialog
1342
1560
  def find
1343
1561
  _r = @text.tag_ranges('sel')
1344
1562
  if _r.length>0
@@ -1362,27 +1580,41 @@ class AgEditor
1362
1580
 
1363
1581
  end
1364
1582
 
1583
+ def do_enter
1584
+ check_file_last_access_time
1585
+ end
1586
+
1365
1587
  def initialize_text_binding
1366
1588
  @text.add_yscrollcommand(proc{|first,last| self.do_line_update()})
1367
1589
 
1368
1590
  @text.tag_bind('selected', 'Enter', proc{@text.tag_remove('selected','1.0','end')})
1369
1591
 
1370
- @text.bind("Enter", proc{check_file_last_access_time})
1592
+ @text.bind("Enter", proc{do_enter})
1371
1593
 
1372
1594
  @text.bind("<Modified>"){|e|
1373
1595
  check_modify
1374
1596
  }
1375
1597
  activate_key_binding
1376
- @text.bind_append("1",proc{Arcadia.process_event(InputEnterEvent.new(self,'receiver'=>@text))})
1598
+ @text.bind_append("1"){
1599
+ Arcadia.process_event(InputEnterEvent.new(self,'receiver'=>@text))
1600
+ refresh_outline
1601
+ }
1602
+ end
1603
+
1604
+ def refresh_outline
1605
+ if @outline
1606
+ Tk.after(1,proc{ @outline.update_row(self.row)})
1607
+ end
1377
1608
  end
1378
1609
 
1379
1610
  def run_buffer
1380
1611
  if !@file
1381
1612
  _file = create_temp_file
1382
1613
  begin
1383
- Arcadia.process_event(RunRubyFileEvent.new(self, 'file'=>_file, 'persistent'=>false))
1614
+ _event = Arcadia.process_event(RunRubyFileEvent.new(self, 'file'=>_file, 'persistent'=>false))
1384
1615
  ensure
1385
- File.delete(_file) if File.exist?(_file)
1616
+ _event.add_finalize_callback(proc{File.delete(_file) if File.exist?(_file)})
1617
+ # File.delete(_file) if File.exist?(_file)
1386
1618
  end
1387
1619
  else
1388
1620
  save if !@read_only
@@ -1546,19 +1778,40 @@ class AgEditor
1546
1778
 
1547
1779
  def reset_highlight
1548
1780
  @is_line_bold.clear
1549
- @is_tag_bold.clear
1550
- @highlight_zone.clear
1781
+ @highlight_zone.clear if @highlighting
1551
1782
  @last_line_begin=0
1552
1783
  @last_line_end=0
1553
1784
  @last_zone_begin=0
1554
1785
  @last_zone_end=0
1555
1786
  end
1787
+
1788
+ def change_highlight(_ext)
1789
+ new_highlight_scanner = @controller.highlight_scanner(_ext)
1790
+ if new_highlight_scanner != @highlight_scanner
1791
+ @highlight_scanner.classes.each{|c|
1792
+ @text.tag_remove(c,'1.0', 'end')
1793
+ @text.tag_delete(c)
1794
+ @is_tag_bold.delete(c)
1795
+ }
1796
+ @highlight_scanner = new_highlight_scanner
1797
+ reset_highlight
1798
+ if @highlight_scanner
1799
+ @highlight_scanner.classes.each{|c|
1800
+ do_tag_configure(c)
1801
+ }
1802
+ @highlighting = true
1803
+ else
1804
+ @highlighting = false
1805
+ end
1806
+ end
1807
+ end
1556
1808
 
1557
- def initialize_highlight
1809
+ def initialize_highlight(_ext)
1810
+ @highlight_scanner = @controller.highlight_scanner(_ext)
1558
1811
  @is_line_bold = Hash.new
1559
1812
  @is_tag_bold = Hash.new
1560
1813
  do_tag_configure_global('debug')
1561
- if @lang_hash.nil?
1814
+ if @lang_hash.nil? || @highlight_scanner.nil?
1562
1815
  @highlighting = false
1563
1816
  return
1564
1817
  end
@@ -1570,19 +1823,8 @@ class AgEditor
1570
1823
  @last_line_end = 0
1571
1824
  @last_zone_begin=0;
1572
1825
  @last_zone_end=0;
1573
- #@is_line_bold = Hash.new
1574
- #@is_tag_bold = Hash.new
1575
- @h_classes = @lang_hash['classes'].split(',')
1576
- @h_re = Hash.new
1577
- @op_to_end_line = Array.new
1578
- @op_to_end_line.concat(@lang_hash['re_op.to_line_end'].split(',')) if @lang_hash['re_op.to_line_end']
1579
-
1580
- @op_only_first = Array.new
1581
- @op_only_first.concat(@lang_hash['re_op.only_first'].split(',')) if @lang_hash['re_op.only_first']
1582
-
1583
- @h_classes.each{|c|
1826
+ @highlight_scanner.classes.each{|c|
1584
1827
  do_tag_configure(c)
1585
- @h_re[c]=Regexp::new(@lang_hash["re.#{c}"].strip) if @lang_hash["re.#{c}"]
1586
1828
  }
1587
1829
 
1588
1830
  ['sel','selected','tabs','spaces'].each{|_name|
@@ -1596,23 +1838,23 @@ class AgEditor
1596
1838
 
1597
1839
  def do_tag_configure(_name)
1598
1840
  h = Hash.new
1599
- if @lang_hash['hightlight.'+_name+'.foreground']
1600
- h['foreground']=@lang_hash['hightlight.'+_name+'.foreground']
1841
+ if @lang_hash["#{@lang_hash['scanner']}.hightlight."+_name+'.foreground']
1842
+ h['foreground']=@lang_hash["#{@lang_hash['scanner']}.hightlight."+_name+'.foreground']
1601
1843
  end
1602
- if @lang_hash['hightlight.'+_name+'.background']
1603
- h['background']=@lang_hash['hightlight.'+_name+'.background']
1844
+ if @lang_hash["#{@lang_hash['scanner']}.hightlight."+_name+'.background']
1845
+ h['background']=@lang_hash["#{@lang_hash['scanner']}.hightlight."+_name+'.background']
1604
1846
  end
1605
- if @lang_hash['hightlight.'+_name+'.style']== 'bold'
1847
+ if @lang_hash["#{@lang_hash['scanner']}.hightlight."+_name+'.style']== 'bold'
1606
1848
  h['font']=@font_bold
1607
1849
  @is_tag_bold[_name]= true
1608
1850
  else
1609
1851
  @is_tag_bold[_name]= false
1610
1852
  end
1611
- if @lang_hash['hightlight.'+_name+'.relief']
1612
- h['relief']=@lang_hash['hightlight.'+_name+'.relief']
1853
+ if @lang_hash["#{@lang_hash['scanner']}.hightlight."+_name+'.relief']
1854
+ h['relief']=@lang_hash["#{@lang_hash['scanner']}.hightlight."+_name+'.relief']
1613
1855
  end
1614
- if @lang_hash['hightlight.'+_name+'.borderwidth']
1615
- h['borderwidth']=@lang_hash['hightlight.'+_name+'.borderwidth']
1856
+ if @lang_hash["#{@lang_hash['scanner']}.hightlight."+_name+'.borderwidth']
1857
+ h['borderwidth']=@lang_hash["#{@lang_hash['scanner']}.hightlight."+_name+'.borderwidth']
1616
1858
  end
1617
1859
  @text.tag_configure(_name, h)
1618
1860
  end
@@ -1763,8 +2005,8 @@ class AgEditor
1763
2005
  :command,
1764
2006
  :label=>'Data image from file',
1765
2007
  :hidemargin => false,
1766
- :command=> proc{
1767
- file = Tk.getOpenFile
2008
+ :command=> proc{
2009
+ file = Arcadia.open_file_dialog
1768
2010
  if file
1769
2011
  require 'base64'
1770
2012
  f = File.open(file,"rb")
@@ -1990,154 +2232,9 @@ class AgEditor
1990
2232
  @text.tag_add('selected',_index +' linestart', _index +' +1 lines linestart')
1991
2233
  end
1992
2234
 
1993
-
1994
- # def build_tree_from_source(_source)
1995
- # _row = 1
1996
- # _liv = 0
1997
- # _livs = Array.new
1998
- # root = TreeNode.new(nil, 'KRoot'){|_node|
1999
- # _node.rif= 'root'
2000
- # _node.label=''
2001
- # }
2002
- # _livs[_liv]=root
2003
- # _source.each_line{|line|
2004
- # line = "\s"+line.split("#")[0]+"\s"
2005
- # m = /[\s\n\t\;]+(module|class|def|if|unless|begin|case|for|while|do)[\s\n\t\;]+/.match(line)
2006
- # if m
2007
- # index = m.post_match.strip.length - 1
2008
- # if m.post_match.strip[index,index]=='{'
2009
- # _row = _row +1
2010
- # next
2011
- # end
2012
- # _liv>=0? _liv = _liv + 1:_liv=1
2013
- # _pliv = _liv
2014
- # _parent = nil
2015
- # while (_parent == nil && _pliv>=0)
2016
- # _pliv = _pliv -1
2017
- # _parent = _livs[_pliv]
2018
- # end
2019
- # if _parent
2020
- # _helptext = m.post_match.strip
2021
- # _label = _helptext.split('<')[0]
2022
- # if _label == nil || _label.strip.length==0
2023
- # _label = _helptext
2024
- # end
2025
- # if (m[0].strip[0..4] == "class" && m.pre_match.strip.length==0)
2026
- # _kind = 'KClass'
2027
- # elsif (m[0].strip[0..4] == "class" && m.pre_match.strip.length>0)
2028
- # _row = _row +1
2029
- # _liv = _liv - 1
2030
- # next
2031
- # elsif (m[0].strip[0..5] == "module" && m.pre_match.strip.length==0)
2032
- # _kind = 'KModule'
2033
- # elsif (m[0].strip[0..5] == "module" && m.pre_match.strip.length>0)
2034
- # _row = _row +1
2035
- # _liv = _liv - 1
2036
- # next
2037
- # elsif ((m[0].strip[0..4] == "begin")||(m[0].strip[0..3] == "case") ||(m[0].strip[0..4] == "while") || (m[0].strip[0..2] == "for") || (m[0].strip[0..1] == "do") || ((m[0].strip[0..1] == "if" || m[0].strip[0..5] == "unless") && m.pre_match.strip.length==0))
2038
- # _row = _row +1
2039
- # next
2040
- # elsif ((m[0].strip[0..1] == "if" || m[0].strip[0..5] == "unless") && m.pre_match.strip.length>0)
2041
- # _row = _row +1
2042
- # _liv = _liv - 1
2043
- # next
2044
- # elsif (m[0].strip[0..2] == "def" && m.pre_match.strip.length==0)
2045
- # _kind = 'KDef'
2046
- # if _label.include?(_parent.label + '.')
2047
- # _kind = 'KDefClass'
2048
- # end
2049
- # # elsif (m[0].strip[0..10] == "attr_reader" && m.pre_match.strip.length==0)
2050
- # # _kind = 'KAttr_reader'
2051
- # # _liv = _liv - 1
2052
- # # _row = _row +1
2053
- # end
2054
- #
2055
- # TreeNode.new(_parent, _kind){|_node|
2056
- # _node.label = _label
2057
- # _node.helptext = _helptext
2058
- # _node.rif = _row.to_s
2059
- # _livs[_pliv + 1]=_node
2060
- # }
2061
- # else
2062
- # _row = _row +1
2063
- # _liv = _liv - 1
2064
- # next
2065
- # end
2066
- # end
2067
- # m_end = /[\s\n\t\;]+end[\s\n\t\;]+/.match(line)
2068
- # if m_end
2069
- # _liv = _liv - 1
2070
- # end
2071
- # _row = _row +1
2072
- # }
2073
- # return root
2074
- # end
2075
-
2076
- def build_tree_from_node(_node, _label_match=nil)
2077
-
2078
- @image_kclass = TkPhotoImage.new('dat' => TREE_NODE_CLASS_GIF)
2079
- @image_kmodule = TkPhotoImage.new('dat' => TREE_NODE_MODULE_GIF)
2080
- @image_kdef = TkPhotoImage.new('dat' => TREE_NODE_DEF_GIF)
2081
- @image_kdefclass = TkPhotoImage.new('dat' => TREE_NODE_DEFCLASS_GIF)
2082
-
2083
- _sorted_sons = _node.sons.sort
2084
- for inode in 0.._sorted_sons.length - 1
2085
- _son = _sorted_sons[inode]
2086
- if _son.kind == 'KClass'
2087
- _image = @image_kclass
2088
- elsif _son.kind == 'KModule'
2089
- _image = @image_kmodule
2090
- elsif _son.kind == 'KDef'
2091
- _image = @image_kdef
2092
- elsif _son.kind == 'KDefClass'
2093
- _image = @image_kdefclass
2094
- end
2095
- @tree_exp.insert('end', _son.parent.rif ,_son.rif, {
2096
- 'text' => _son.label ,
2097
- 'helptext' => _son.helptext,
2098
- #'font'=>$arcadia['conf']['editor.explorer_panel.tree.font'],
2099
- 'image'=> _image
2100
- }.update(Arcadia.style('treeitem'))
2101
- )
2102
- if (_label_match) && (_label_match.strip == _son.label.strip)
2103
- @selected = _son
2104
- end
2105
- build_tree_from_node(_son, _label_match)
2106
- end
2107
- end
2108
-
2109
- def build_tree(_sel=nil)
2110
- #Arcadia.console(self,"msg"=>"build for #{@file}")
2111
- if _sel
2112
- _label_sel = @tree_exp.itemcget(_sel,'text')
2113
- end
2114
-
2115
- #clear tree
2116
- begin
2117
- @tree_exp.delete(@tree_exp.nodes('root'))
2118
- rescue Exception
2119
- # workaround on windows
2120
- @tree_exp.delete(@tree_exp.nodes('root'))
2121
- end
2122
-
2123
-
2124
- #(re)build tree
2125
- _txt = @text.get('1.0','end')
2126
- #@root = build_tree_from_source(_txt)
2127
- @root = SourceStructure.new(_txt).root
2128
-
2129
- @selected = nil
2130
- build_tree_from_node(@root, _label_sel)
2131
- if @selected
2132
- @tree_exp.selection_add(@selected.rif)
2133
- @tree_exp.open_tree(@selected.parent.rif)
2134
- @tree_exp.see(@selected.rif)
2135
- end
2136
- end
2137
-
2138
- def insert_popup_menu_item(_where, *args)
2139
- @pop_up.insert(_where,*args)
2140
- end
2235
+ def insert_popup_menu_item(_where, *args)
2236
+ @pop_up.insert(_where,*args)
2237
+ end
2141
2238
 
2142
2239
  def text_value
2143
2240
  return @text.value
@@ -2180,85 +2277,94 @@ class AgEditor
2180
2277
  return (_riga.to_i + _gap_row).to_s + '.'+ (_colonna.to_i + _gap_col).to_s
2181
2278
  end
2182
2279
 
2183
- def find_and_set_tag_ml(_re, _row, _txt, _tag, _tag_rem = nil)
2184
- m = _re.match(_txt)
2185
- _offset = 0
2186
- _s_txt = _txt
2187
- #_old_txt = ''
2188
- while m && (_txt=m.post_match)
2189
- if !defined?(_old_txt) || _txt != _old_txt
2280
+ # def find_and_set_tag_ml(_re, _row, _txt, _tag, _tag_rem = nil)
2281
+ # m = _re.match(_txt)
2282
+ # _offset = 0
2283
+ # _s_txt = _txt
2284
+ # #_old_txt = ''
2285
+ # while m && (_txt=m.post_match)
2286
+ # if !defined?(_old_txt) || _txt != _old_txt
2287
+ #
2288
+ # apos = pos_to_index(_s_txt, _offset+m.begin(0))
2289
+ # _offset = _offset + m.end(0)
2290
+ #
2291
+ #
2292
+ # _old_txt = _txt
2293
+ # _r = _row + apos[0]
2294
+ # _ibegin = _r.to_s+'.'+apos[1].to_s
2295
+ # _iend = _r.to_s+'.'+(apos[1]+m.end(0)-m.begin(0)).to_s
2296
+ # if _tag_rem
2297
+ # _tag_rem.each {|value|
2298
+ # @text.tag_remove(value,_ibegin, _iend)
2299
+ # }
2300
+ # end
2301
+ # @text.tag_add(_tag,_ibegin, _iend)
2302
+ # if @is_tag_bold[_tag]
2303
+ # @is_line_bold[_r]=true
2304
+ # end
2305
+ #
2306
+ # if @op_only_first.include?(_tag) && _txt
2307
+ # #eliminino la prima riga a partire dal risultato
2308
+ # _p = _txt.index("\n")+1
2309
+ # if _p
2310
+ # _txt = _txt[_p..-1]
2311
+ # _offset = _offset + _p
2312
+ # else
2313
+ # m = nil
2314
+ # end
2315
+ # end
2316
+ # m = _re.match(_txt)
2317
+ #
2318
+ # else
2319
+ # m = nil
2320
+ # end
2321
+ # end
2322
+ # end
2190
2323
 
2191
- apos = pos_to_index(_s_txt, _offset+m.begin(0))
2192
- _offset = _offset + m.end(0)
2193
-
2194
-
2195
- _old_txt = _txt
2196
- _r = _row + apos[0]
2197
- _ibegin = _r.to_s+'.'+apos[1].to_s
2198
- _iend = _r.to_s+'.'+(apos[1]+m.end(0)-m.begin(0)).to_s
2199
- if _tag_rem
2200
- _tag_rem.each {|value|
2201
- @text.tag_remove(value,_ibegin, _iend)
2202
- }
2203
- end
2204
- @text.tag_add(_tag,_ibegin, _iend)
2205
- if @is_tag_bold[_tag]
2206
- @is_line_bold[_r]=true
2207
- end
2208
2324
 
2209
- if @op_only_first.include?(_tag) && _txt
2210
- #eliminino la prima riga a partire dal risultato
2211
- _p = _txt.index("\n")+1
2212
- if _p
2213
- _txt = _txt[_p..-1]
2214
- _offset = _offset + _p
2215
- else
2216
- m = nil
2217
- end
2218
- end
2219
- m = _re.match(_txt)
2220
-
2221
- else
2222
- m = nil
2223
- end
2224
- end
2225
- end
2325
+ # def find_and_set_tag(_re, _row, _txt, _tag, _tag_rem = nil)
2326
+ # m = _re.match(_txt)
2327
+ # _end = 0
2328
+ # if m && @is_tag_bold[_tag]
2329
+ # @is_line_bold[_row]=true
2330
+ # end
2331
+ # #_old_txt = ''
2332
+ # while m && (_txt=m.post_match)
2333
+ # if !defined?(_old_txt) || _txt != _old_txt
2334
+ # _old_txt = _txt
2335
+ # _ibegin = _row.to_s+'.'+(m.begin(0)+_end).to_s
2336
+ # _end = m.end(0) + _end
2337
+ # _iend = _row.to_s+'.'+(_end.to_s)
2338
+ # if _tag_rem
2339
+ # _tag_rem.each {|value|
2340
+ # @text.tag_remove(value,_ibegin, _iend)
2341
+ # }
2342
+ # end
2343
+ # @text.tag_add(_tag,_ibegin, _iend)
2344
+ # if @op_only_first.include?(_tag)
2345
+ # m = nil
2346
+ # else
2347
+ # m = _re.match(_txt)
2348
+ # end
2349
+ # else
2350
+ # m = nil
2351
+ # end
2352
+ # end
2353
+ # end
2226
2354
 
2227
2355
 
2228
- def find_and_set_tag(_re, _row, _txt, _tag, _tag_rem = nil)
2229
- m = _re.match(_txt)
2230
- _end = 0
2231
- if m && @is_tag_bold[_tag]
2232
- @is_line_bold[_row]=true
2233
- end
2234
- #_old_txt = ''
2235
- while m && (_txt=m.post_match)
2236
- if !defined?(_old_txt) || _txt != _old_txt
2237
- _old_txt = _txt
2238
- _ibegin = _row.to_s+'.'+(m.begin(0)+_end).to_s
2239
- _end = m.end(0) + _end
2240
- _iend = _row.to_s+'.'+(_end.to_s)
2241
- if _tag_rem
2242
- _tag_rem.each {|value|
2243
- @text.tag_remove(value,_ibegin, _iend)
2244
- }
2245
- end
2246
- @text.tag_add(_tag,_ibegin, _iend)
2247
- if @op_only_first.include?(_tag)
2248
- m = nil
2249
- else
2250
- m = _re.match(_txt)
2251
- end
2252
- else
2253
- m = nil
2254
- end
2356
+ def text_value_lines
2357
+ if String.method_defined?(:lines)
2358
+ return @text.value.lines
2359
+ else
2360
+ return @text.value
2255
2361
  end
2256
2362
  end
2257
2363
 
2258
2364
  def show_spaces
2259
2365
  @spaces_show = true
2260
2366
  _row = 1
2261
- @text.value.each{|_line|
2367
+ text_value_lines.each{|_line|
2262
2368
  show_chars_line(_row, _line, /[ ^\t]\s*/, 'spaces')
2263
2369
  _row = _row+1
2264
2370
  }
@@ -2268,7 +2374,7 @@ class AgEditor
2268
2374
  def show_tabs
2269
2375
  @tabs_show = true
2270
2376
  _row = 1
2271
- @text.value.each{|_line|
2377
+ text_value_lines.each{|_line|
2272
2378
  show_chars_line(_row, _line, /\t/, 'tabs')
2273
2379
  _row = _row+1
2274
2380
  }
@@ -2290,7 +2396,7 @@ class AgEditor
2290
2396
 
2291
2397
  def indentation_space_2_tabs(_n_space=2)
2292
2398
  _row = 1
2293
- @text.value.each{|_line|
2399
+ text_value_lines.each{|_line|
2294
2400
  m = /\s*/.match(_line)
2295
2401
  _end = 0
2296
2402
  if m && m.begin(0)==0
@@ -2310,7 +2416,7 @@ class AgEditor
2310
2416
 
2311
2417
  def indentation_tabs_2_space(_n_space=2)
2312
2418
  _row = 1
2313
- @text.value.each{|_line|
2419
+ text_value_lines.each{|_line|
2314
2420
  m = /\t*/.match(_line)
2315
2421
  _end = 0
2316
2422
  if m && m.begin(0)==0
@@ -2339,6 +2445,7 @@ class AgEditor
2339
2445
  end
2340
2446
 
2341
2447
 
2448
+ # modify in this instance means the (...) in the tab header of each file
2342
2449
  def modified?
2343
2450
  return !(@buffer === text_value)
2344
2451
  end
@@ -2372,98 +2479,16 @@ class AgEditor
2372
2479
  end
2373
2480
  end
2374
2481
 
2375
- def highlightlines(_row, _lines, _check_mod = false)
2376
- if _check_mod
2377
- check_modify
2378
- end
2379
- _txt = _lines
2380
- _end = 0
2381
-
2382
- # @op_to_end_line.each{|c|
2383
- # if @h_re[c]
2384
- # m_c = @h_re[c].match(_txt)
2385
- # if m_c then
2386
- # _ibegin = _row.to_s+'.'+(m_c.begin(0)).to_s
2387
- # _iend = _row.to_s+'.'+(_line.length - 1).to_s
2388
- # @text.tag_add(c,_ibegin, _iend)
2389
- # _txt = m_c.pre_match
2390
- # end
2391
- # end
2392
- # } if @lang_hash['re_op.to_line_end']
2393
-
2394
- arem = Array.new
2395
-
2396
-
2397
- @h_classes.each{|c|
2398
- if !@op_to_end_line.include?(c) && @h_re[c]
2399
- find_and_set_tag_ml(@h_re[c], _row, _txt, c, arem)
2400
- arem << c
2401
- end
2402
- } if _txt.strip.length > 0
2403
2482
 
2404
- find_and_set_tag_ml(/\t/, _row, _txt, 'tabs', arem) if @tabs_show
2405
- find_and_set_tag_ml(/[ ^\t]\s*/, _row, _txt, 'spaces', arem) if @spaces_show
2406
- end
2407
-
2408
-
2409
- def highlightline(_row, _line, _check_mod = false)
2410
- #p "highlightline #{_row} _line=#{_line}"
2411
- if _check_mod
2412
- check_modify
2413
- end
2414
- _txt = _line
2415
- _end = 0
2416
-
2417
- @op_to_end_line.each{|c|
2418
- if @h_re[c]
2419
- m_c = @h_re[c].match(_txt)
2420
- if m_c then
2421
- _ibegin = _row.to_s+'.'+(m_c.begin(0)).to_s
2422
- _iend = _row.to_s+'.'+(_line.length - 1).to_s
2423
- @text.tag_add(c,_ibegin, _iend)
2424
- #p "tag_add found #{c}"
2425
- _txt = m_c.pre_match
2426
- end
2427
- end
2428
- } if @lang_hash['re_op.to_line_end']
2429
-
2430
- arem = Array.new
2431
-
2432
-
2433
- @h_classes.each{|c|
2434
- if !@op_to_end_line.include?(c) && @h_re[c]
2435
- find_and_set_tag(@h_re[c], _row, _txt, c, arem)
2436
- arem << c
2437
- end
2438
- } if _txt.strip.length > 0
2439
-
2440
- find_and_set_tag(/\t/, _row, _txt, 'tabs', arem) if @tabs_show
2441
- find_and_set_tag(/[ ^\t]\s*/, _row, _txt, 'spaces', arem) if @spaces_show
2442
- end
2443
-
2444
- def rehighlightline(_row)
2445
- _ibegin = _row.to_s+'.0'
2446
- _iend = (_row+1).to_s+'.0'
2447
- #p "rehighlightline _ibegin=#{_ibegin}"
2448
- #p "rehighlightline _iend=#{_iend}"
2449
- #p "_line = #{@text.get(_ibegin, _iend)}"
2450
- @h_classes.each{|c| @text.tag_remove(c,_ibegin, _iend)}
2451
- _line = @text.get(_ibegin, _iend)
2452
- highlightline(_row, _line)
2453
- end
2454
-
2455
- def rehighlightlines(_row_begin, _row_end)
2483
+ def rehighlightlines(_row_begin, _row_end, _check_mod=false)
2456
2484
  _ibegin = _row_begin.to_s+'.0'
2457
2485
  _iend = (_row_end+1).to_s+'.0'
2458
- @h_classes.each{|c| @text.tag_remove(c,_ibegin, _iend)}
2459
- _lines = @text.get(_ibegin, _iend)
2460
- highlightlines(_row_begin, _lines)
2486
+ @highlight_scanner.classes.each{|c| @text.tag_remove(c,_ibegin, _iend)}
2487
+ highlightlines(_row_begin, _row_end, _check_mod)
2461
2488
  end
2462
2489
 
2463
-
2464
2490
  def row(_index='insert')
2465
2491
  _row = @text.index(_index).split('.')[0].to_i
2466
- #print "def row(_index='insert')",_row.to_s,"\n"
2467
2492
  return _row
2468
2493
  end
2469
2494
 
@@ -2473,9 +2498,7 @@ class AgEditor
2473
2498
 
2474
2499
  def do_line_update
2475
2500
  #re num in @text_line_num the portion of visibled screen of @text
2476
- #Arcadia.console(self, 'msg'=>"do_line_update loading ..")
2477
2501
  return if @loading
2478
- #Arcadia.console(self, 'msg'=>"do_line_update")
2479
2502
  if @text_line_num
2480
2503
  line_begin_index = @text.index('@0,0')
2481
2504
  line_begin = line_begin_index.split('.')[0].to_i
@@ -2487,7 +2510,7 @@ class AgEditor
2487
2510
  _zone_begin = ((line_begin) / @highlight_zone_length).to_i + 1
2488
2511
  _zone_end = ((line_end) / @highlight_zone_length).to_i + 1
2489
2512
  #Arcadia.new_msg(self, "for lines #{line_begin}..#{line_end} \n
2490
- _zone_begin=#{_zone_begin} ; _zone_end=#{_zone_end}")
2513
+ #_zone_begin=#{_zone_begin} ; _zone_end=#{_zone_end}")
2491
2514
  (_zone_begin >=@last_zone_begin)?_zone_begin.upto(_zone_end+1){|_zone|
2492
2515
  highlight_zone(_zone)
2493
2516
  }:_zone_end.downto(_zone_begin-1){|_zone|
@@ -2498,28 +2521,13 @@ class AgEditor
2498
2521
  @last_zone_begin = _zone_begin
2499
2522
  @last_zone_end = _zone_end
2500
2523
  end
2501
-
2502
2524
  @text_line_num.delete('1.0','end')
2525
+
2503
2526
 
2504
2527
  _rx, _ry, _widht, _heigth = @text.bbox(line_begin_index);
2505
- # _rx2, _ry2, _widht2, _heigth2 = @text.bbox(line_begin_index+" +1 lines");
2506
- # if _rx2
2507
- # _coef = _ry2-_ry-_heigth
2508
- # end
2509
- # if _ry < 0
2510
- # nline = (line_begin + 1).to_s.rjust(line_end.to_s.length+2)
2511
- # @text_line_num.tag_configure('start_case', 'spacing1'=>(_heigth+_ry))
2512
- # @text_line_num.insert('end', "#{nline}\n",'normal_case','start_case')
2513
- # real_line_begin = line_begin + 2
2514
- # else
2515
- # real_line_begin = line_begin
2516
- # end
2517
2528
 
2518
2529
  if _ry && _ry < 0
2519
2530
  real_line_end = line_end + 1
2520
- # x = (_heigth+_ry)/_heigth
2521
- # @text_line_num.yview_scroll(-(_heigth+_ry),"pixels")
2522
-
2523
2531
  else
2524
2532
  real_line_end = line_end
2525
2533
  end
@@ -2549,46 +2557,73 @@ class AgEditor
2549
2557
  end
2550
2558
 
2551
2559
  @text_line_num.insert(_index, "#{nline}\n",_tags)
2552
- # if @highlighting && @is_line_bold[j]
2553
- # @text_line_num.insert('end', "#{nline}\n",'bold_case')
2554
- # else
2555
- # @text_line_num.insert('end', "#{nline}\n",'normal_case')
2556
- # end
2557
2560
  if b.include?(j.to_s)
2558
2561
  add_tag_breakpoint(j)
2559
- #add_tag_breakpoint(_index)
2560
- #p "aggiungo tag break on line #{j} on index ->#{_index}"
2561
- #add_tag_breakpoint(_index+' -1 lines')
2562
2562
  end
2563
2563
  end
2564
2564
  if _ry && _ry < 0
2565
- #Arcadia.console(self, 'msg'=>"scrollo -> #{-(_heigth+_ry)}")
2566
- #Arcadia.console(self, 'msg'=>"_coef -> #{_coef}")
2567
-
2568
- # @text_line_num.yview_scroll((_heigth+_ry),"pixels")
2569
- # @text_line_num.yview_scroll((-_ry+3),"pixels")
2570
- @text_line_num.yview_scroll(_ry.abs+3,"pixels")
2565
+ @text_line_num.yview_scroll(_ry.abs+2,"pixels")
2571
2566
  end
2572
2567
  end
2568
+ refresh_outline if Tk.focus==@text
2569
+ # if TkWinfo.mapped?(@text_line_num)
2570
+ # x,y,w,h = @text.bbox("#{(line_end).to_s}.3");
2571
+ # @fm1.splitter_frame.go(w,0)
2572
+ # @fm1.do_resize
2573
+ # end
2573
2574
  end
2574
2575
 
2575
- def highlight_zone_new(_zone)
2576
- if !@highlight_zone[_zone]
2577
- _b = @highlight_zone_length*(_zone - 1)
2578
- _e = @highlight_zone_length*(_zone) #+ 1
2579
- rehighlightlines(_b,_e)
2580
- @highlight_zone[_zone] = true
2576
+ def highlightlines(_row_begin, _row_end, _check_mod = false)
2577
+ if _check_mod
2578
+ check_modify
2579
+ end
2580
+ #_row_begin = _row_begin+1
2581
+ _ibegin = _row_begin.to_s+'.0'
2582
+ _iend = (_row_end+1).to_s+'.0'
2583
+ @highlight_scanner.classes.each{|c| @text.tag_remove(c,_ibegin, _iend)}
2584
+ _lines = @text.get(_ibegin, _iend)
2585
+ tags_map = @highlight_scanner.highlight_tags(_row_begin,_lines)
2586
+ tags_map.each do |key,value|
2587
+ to_tag = Array.new
2588
+ value.each{|ite|
2589
+ to_tag.concat(ite)
2590
+ if @is_tag_bold[key.to_s]
2591
+ if ite.length==2
2592
+ row_begin = ite[0].split('.')[0].to_i
2593
+ row_end = ite[1].split('.')[0].to_i
2594
+ for row in row_begin..row_end
2595
+ @is_line_bold[row]=true
2596
+ end
2597
+ end
2598
+ # ite.each{|p|
2599
+ # row_begin = p[0].split('.')[0].to_i
2600
+ # row_end = p[1].split('.')[0].to_i
2601
+ # for row in row_begin...row_end
2602
+ # @is_line_bold[row]=true
2603
+ # end
2604
+ # }
2605
+ end
2606
+ }
2607
+ @text.tag_adds(key.to_s,to_tag)
2608
+ end
2609
+ if @tabs_show || @spaces_show
2610
+ if !defined?(@rescanner)
2611
+ if @lang_hash['scanner']!='re'
2612
+ @rescanner = ReHighlightScanner.new(@lang_hash) if !defined?(@rescanner)
2613
+ else
2614
+ @rescanner = @highlight_scanner
2615
+ end
2616
+ end
2617
+ @rescanner.highlight_tags(_row_begin,_lines,['tabs']) if @tabs_show
2618
+ @rescanner.highlight_tags(_row_begin,_lines,['spaces']) if @spaces_show
2581
2619
  end
2582
2620
  end
2583
2621
 
2584
-
2585
2622
  def highlight_zone(_zone, _force_highlight=false)
2586
2623
  if !@highlight_zone[_zone] || _force_highlight
2587
- _b = @highlight_zone_length*(_zone - 1)
2624
+ _b = @highlight_zone_length*(_zone - 1) +1
2588
2625
  _e = @highlight_zone_length*(_zone) #+ 1
2589
- for j in _b..._e
2590
- rehighlightline(j)
2591
- end
2626
+ rehighlightlines(_b,_e)
2592
2627
  @highlight_zone[_zone] = true
2593
2628
  end
2594
2629
  end
@@ -2621,7 +2656,8 @@ class AgEditor
2621
2656
  _iend = _row+'.'+(line.length - 1).to_s
2622
2657
  @text.tag_add('comment',_ibegin, _iend)
2623
2658
  else
2624
- highlightline(_row.to_i, line, false)
2659
+ #highlightline(_row.to_i, line, false)
2660
+ highlightlines(_row.to_i, _row.to_i, false)
2625
2661
  end
2626
2662
  end
2627
2663
  _row = (_row.to_i + 1).to_s
@@ -2634,21 +2670,31 @@ class AgEditor
2634
2670
  @text.edit_reset
2635
2671
  end
2636
2672
  end
2637
-
2638
- def save
2673
+
2674
+
2675
+ def save ignore_read_only = false
2639
2676
  if !@file
2640
2677
  save_as
2641
- elsif @read_only
2642
- Arcadia.dialog(self,
2643
- 'type' => 'ok',
2644
- 'title' =>"#{@file}:read-only",
2645
- 'msg' =>"The file : #{@file} is read-only!",
2646
- 'level' =>'warning')
2678
+ elsif @read_only && !ignore_read_only
2679
+ r=Arcadia.dialog(self,
2680
+ 'type' => 'yes_no_cancel',
2681
+ 'title' =>"#{@file}:read-only",
2682
+ 'msg' =>"The file : #{@file} is read-only! -- save anyway?",
2683
+ 'level' =>'warning')
2684
+ if r=="yes"
2685
+ save true
2686
+ end
2647
2687
  else
2648
- f = File.new(@file, "w")
2688
+ f = File.new(@file, "wb")
2649
2689
  begin
2650
2690
  if f
2651
- f.syswrite(text_value)
2691
+ to_write = text_value
2692
+ if @dos_line_endings
2693
+ # we stripped these out, previously...
2694
+ # for now assume they want them all this way, no mixing and matching...
2695
+ to_write = to_write.gsub("\n", "\r\n")
2696
+ end
2697
+ f.syswrite(to_write)
2652
2698
  @buffer = text_value
2653
2699
  reset_modify
2654
2700
  end
@@ -2660,15 +2706,24 @@ class AgEditor
2660
2706
  end
2661
2707
 
2662
2708
  def save_as
2663
- @file = Tk.getSaveFile("filetypes"=>[["Ruby Files", [".rb", ".rbw"]],["All Files", [".*"]]])
2664
- @file = nil if @file == "" # cancelled
2665
- if @file
2709
+ file = Tk.getSaveFile("filetypes"=>[["Ruby Files", [".rb", ".rbw"]],["All Files", [".*"]]])
2710
+ file = nil if file == "" # cancelled
2711
+ if file
2712
+ new_file_name(file)
2666
2713
  save
2667
- @controller.change_file_name(@page_frame, @file)
2714
+ @controller.change_file_name(@page_frame, file)
2668
2715
  #EditorContract.instance.file_created(self, 'file'=>@file)
2669
2716
  end
2670
2717
  end
2671
2718
 
2719
+ def new_file_name(_new_file)
2720
+ @file =_new_file
2721
+ base_name= File.basename(_new_file)
2722
+ if base_name.include?('.')
2723
+ self.change_highlight(base_name.split('.')[-1])
2724
+ end
2725
+ end
2726
+
2672
2727
  def check_modify
2673
2728
  return if @loading
2674
2729
  if modified?
@@ -2679,54 +2734,50 @@ class AgEditor
2679
2734
  end
2680
2735
 
2681
2736
  def check_file_last_access_time
2682
- if @file && @file_last_access_time
2683
-
2684
- ftime = File.mtime(@file)
2685
- if @file_last_access_time != ftime
2686
- msg = 'File "'+@file+'" is changed! Reload?'
2737
+ if @file
2738
+ file_exist = File.exist?(@file)
2739
+ if @file_last_access_time && file_exist
2740
+ ftime = File.mtime(@file)
2741
+ if @file_last_access_time != ftime
2742
+ msg = 'File "'+@file+'" is changed! Reload?'
2687
2743
  if Tk.messageBox('icon' => 'error', 'type' => 'yesno',
2688
2744
  'title' => '(Arcadia) Libs', 'parent' => @text,
2689
2745
  'message' => msg) == 'yes'
2690
- @text.delete('1.0','end')
2691
- reset_highlight if @highlighting
2692
- load_file(@file)
2746
+ reload
2747
+
2693
2748
  else
2694
2749
  @file_last_access_time = ftime
2695
2750
  end
2751
+ end
2752
+ elsif !file_exist
2753
+ msg = 'Appears that file "'+@file+'" was deleted by other process! Do you want to resave it?'
2754
+ if Tk.messageBox('icon' => 'error', 'type' => 'yesno',
2755
+ 'title' => '(Arcadia) editor', 'parent' => @text,
2756
+ 'message' => msg) == 'yes'
2757
+ save
2758
+ else
2759
+ @file = nil
2760
+ @buffer = ''
2761
+ set_modify
2762
+ end
2696
2763
  end
2697
2764
  end
2698
2765
  end
2699
2766
 
2700
- def languages_hash(_ext=nil)
2701
- @@langs_hash = Hash.new if !defined?(@@langs_hash)
2702
- return nil if _ext.nil?
2703
- if @@langs_hash[_ext].nil?
2704
- #_ext='' if _ext.nil?
2705
- lang_file = File.dirname(__FILE__)+'/langs/'+_ext+'.lang'
2706
- if File.exist?(lang_file)
2707
- @@langs_hash[_ext] = properties_file2hash(lang_file)
2708
- elsif File.exist?(lang_file+'.bind')
2709
- b= properties_file2hash(lang_file+'.bind')
2710
- if b
2711
- if @@langs_hash[b['bind']].nil?
2712
- lang_file_bind = File.dirname(__FILE__)+'/langs/'+b['bind']+".lang"
2713
- if File.exist?(lang_file_bind)
2714
- @@langs_hash[b['bind']]=properties_file2hash(lang_file_bind)
2715
- @@langs_hash[_ext]=@@langs_hash[b['bind']]
2716
- end
2717
- else
2718
- @@langs_hash[_ext]=@@langs_hash[b['bind']]
2719
- end
2720
- end
2721
- end
2722
- self.resolve_properties_link(@@langs_hash[_ext], Arcadia.instance['conf']) if @@langs_hash[_ext]
2723
- end
2724
- @@langs_hash[_ext]
2767
+ def reload
2768
+ pos_index = @text.index('insert')
2769
+ @text.delete('1.0','end')
2770
+ reset_highlight if @highlighting
2771
+ load_file(@file)
2772
+ @text.see(pos_index)
2773
+ @text.set_insert(pos_index)
2725
2774
  end
2726
2775
 
2727
2776
  def init_editing(_ext='rb', _w1=150, _w2=60)
2728
- @is_ruby = _ext=='rb'||_ext=='rbw'
2729
- @lang_hash = languages_hash(_ext)
2777
+ @is_ruby = _ext=='rb'|| _ext=='rbw'
2778
+ @classbrowsing = @is_ruby
2779
+ @lang_hash = @controller.languages_hash(_ext)
2780
+ # @highlight_scanner = @controller.highlight_scanner(_ext)
2730
2781
  # if !_ext.nil? && @is_ruby
2731
2782
  # @fm = AGTkVSplittedFrames.new(@page_frame,_w1)
2732
2783
  # @fm1 = AGTkVSplittedFrames.new(@fm.right_frame,_w2)
@@ -2738,22 +2789,27 @@ class AgEditor
2738
2789
  @fm1 = AGTkVSplittedFrames.new(@page_frame,@page_frame,_w2)
2739
2790
  @fm1.splitter_frame.configure('relief'=>'flat')
2740
2791
  initialize_text(@fm1.right_frame)
2741
- initialize_highlight
2792
+ initialize_highlight(_ext)
2742
2793
  initialize_line_number(@fm1.left_frame)
2743
2794
  initialize_text_binding
2744
2795
  end
2745
2796
 
2746
2797
  def show_outline
2747
- if @tree_scroll_wrapper
2748
- @tree_scroll_wrapper.show
2798
+ if @outline
2799
+ @outline.show
2749
2800
  else
2750
- initialize_tree(@controller.frame(1).hinner_frame)
2751
- build_tree
2801
+ @outline=AgEditorOutline.new(self,@controller.frame(1).hinner_frame,@controller.outline_bar)
2802
+ @outline.build_tree
2752
2803
  end
2753
2804
  end
2754
2805
 
2755
2806
  def hide_outline
2756
- @tree_scroll_wrapper.hide if @tree_scroll_wrapper
2807
+ @outline.hide if @outline
2808
+ end
2809
+
2810
+ def destroy_outline
2811
+ @outline.destroy if @outline
2812
+ @outline = nil
2757
2813
  end
2758
2814
 
2759
2815
  def file_extension(_filename=nil)
@@ -2766,14 +2822,18 @@ class AgEditor
2766
2822
  def load_file(_filename = nil)
2767
2823
  #if filename is nil then open a new tab
2768
2824
  @loading=true
2825
+ @dos_line_endings=false
2769
2826
  begin
2770
2827
  @file = _filename
2771
2828
  if _filename
2772
2829
  #init_editing(file_extension(_filename))
2773
- File::open(_filename,'r'){ |file|
2774
- @text.insert('end',file.readlines.collect!{| line | line.chomp+"\n" }.to_s)
2830
+ File::open(_filename,'rb'){ |file|
2831
+ @text.insert('end',file.readlines.collect!{| line | line.chomp}.join("\n"))
2775
2832
  #@text.insert('end',file.read)
2776
2833
  }
2834
+ File.open(_filename, 'rb') { |file|
2835
+ @dos_line_endings=true if file.read.include?("\r\n") # pesky windows line endings
2836
+ }
2777
2837
  end
2778
2838
  set_read_only(!File.stat(_filename).writable?)
2779
2839
  reset
@@ -2803,7 +2863,7 @@ class AgEditor
2803
2863
  end
2804
2864
 
2805
2865
  def refresh
2806
- build_tree if @classbrowsing #&& !is_exp_hide?
2866
+ @outline.build_tree if @outline && @classbrowsing #&& !is_exp_hide?
2807
2867
  end
2808
2868
  end
2809
2869
 
@@ -2821,15 +2881,179 @@ class AgMultiEditorView
2821
2881
  font Arcadia.conf('editor.tabs.font')
2822
2882
  pack('fill'=>'both', :padx=>0, :pady=>0, :expand => 'yes')
2823
2883
  }
2884
+ refresh_after_map = proc{
2885
+ if !@enb.pages.empty?
2886
+ if @enb.raise.nil? || @enb.raise.strip.length == 0
2887
+ @enb.raise(@enb.pages[0])
2888
+ @enb.see(@enb.pages[0])
2889
+ end
2890
+ end
2891
+ }
2892
+ @enb.bind_append("Map",refresh_after_map)
2893
+
2894
+ end
2895
+
2896
+ end
2897
+
2898
+ class HighlightScanner
2899
+
2900
+ def initialize(_langs_conf)
2901
+ @langs_conf = _langs_conf
2902
+ @lang=@langs_conf['language'].to_sym if @langs_conf['language']
2903
+ end
2904
+
2905
+ def highlight_tags(_row_begin,_code)
2906
+ end
2907
+
2908
+ def classes
2909
+ if !defined?(@h_classes)
2910
+ @h_classes = @langs_conf["#{@langs_conf['scanner']}.classes"].split(',')
2911
+ end
2912
+ @h_classes
2913
+ end
2914
+ end
2915
+
2916
+ class ReHighlightScanner < HighlightScanner
2917
+ def initialize(_langs_conf)
2918
+ super(_langs_conf)
2919
+ @h_re = Hash.new
2920
+ @op_to_end_line = Array.new
2921
+ @op_to_end_line.concat(@langs_conf['re_op.to_line_end'].split(',')) if @langs_conf['re_op.to_line_end']
2922
+
2923
+ @op_only_first = Array.new
2924
+ @op_only_first.concat(@langs_conf['re_op.only_first'].split(',')) if @langs_conf['re_op.only_first']
2925
+
2926
+ self.classes.each{|c|
2927
+ @h_re[c]=Regexp::new(@langs_conf["re.#{c}"].strip) if @langs_conf["re.#{c}"]
2928
+ }
2929
+ end
2930
+
2931
+
2932
+ def find_tag(_tag, _row, _txt)
2933
+ to_ret = []
2934
+ _re = @h_re[_tag]
2935
+ m = _re.match(_txt)
2936
+ _end = 0
2937
+ while m && (_txt=m.post_match)
2938
+ if !defined?(_old_txt) || _txt != _old_txt
2939
+ _old_txt = _txt
2940
+ _ibegin = _row.to_s+'.'+(m.begin(0)+_end).to_s
2941
+ _end = m.end(0) + _end
2942
+ _iend = _row.to_s+'.'+(_end.to_s)
2943
+ to_ret << [_ibegin, _iend]
2944
+ if @op_only_first.include?(_tag)
2945
+ m = nil
2946
+ else
2947
+ m = _re.match(_txt)
2948
+ end
2949
+ else
2950
+ m = nil
2951
+ end
2952
+ end
2953
+ to_ret
2954
+ end
2955
+
2956
+ def highlight_tags(_row_begin,_code,_classes=self.classes)
2957
+ super(_row_begin,_code)
2958
+ tags_map = Hash.new
2959
+ lines = _code.split("\n")
2960
+ lines.each_with_index{|_line,_i|
2961
+ _line+="\n"
2962
+ _row = _row_begin+_i
2963
+ #p "_row=#{_row}-_line=#{_line}"
2964
+ _txt = _line
2965
+ _end = 0
2966
+ @op_to_end_line.each{|c|
2967
+ if _classes.include?(c) && @h_re[c]
2968
+ m_c = @h_re[c].match(_txt)
2969
+ if m_c then
2970
+ _ibegin = _row.to_s+'.'+(m_c.begin(0)).to_s
2971
+ _iend = _row.to_s+'.'+(_line.length - 1).to_s
2972
+ tags_map[c] = [] if tags_map[c].nil?
2973
+ tags_map[c] << [_ibegin, _iend]
2974
+ _txt = m_c.pre_match
2975
+ end
2976
+ end
2977
+ } if @langs_conf['re_op.to_line_end']
2978
+
2979
+ _classes.each{|c|
2980
+ if !@op_to_end_line.include?(c) && @h_re[c]
2981
+ _tags = find_tag(c, _row, _txt)
2982
+ if _tags.length >0
2983
+ tags_map[c] = [] if tags_map[c].nil?
2984
+ tags_map[c].concat(_tags)
2985
+ end
2986
+ end
2987
+ } if _txt.strip.length > 0
2988
+ }
2989
+ tags_map
2824
2990
  end
2991
+ end
2825
2992
 
2993
+ class CoderayHighlightScanner < HighlightScanner
2994
+ def initialize(_langs_conf)
2995
+ super(_langs_conf)
2996
+ require 'coderay'
2997
+ end
2998
+ # def highlight_tags(_row_begin,_code)
2999
+ # super(_row_begin,_code)
3000
+ # case @lang
3001
+ # when :ruby
3002
+ # _highlight_tags_ruby(_row_begin,_code)
3003
+ # end
3004
+ # end
3005
+ def highlight_tags(_row_begin,_code)
3006
+ super(_row_begin,_code)
3007
+ c_scanner = CodeRay::Scanners[@lang].new _code
3008
+ row=_row_begin
3009
+ col=0
3010
+ tags_map = Hash.new
3011
+ c_scanner.tokens.each{|tok|
3012
+ #p tok
3013
+ if tok[1]==:space && tok[0].include?("\n")
3014
+ row+=tok[0].count("\n")
3015
+ begin_gap = tok[0].split("\n")[-1]
3016
+ if begin_gap && tok[0][-1..-1]!="\n"
3017
+ col = begin_gap.length
3018
+ else
3019
+ col = 0
3020
+ end
3021
+ elsif !([:open,:close].include?(tok[0])&& tok[1].class==Symbol)
3022
+ toklength = tok[0].length
3023
+ t_begin="#{row}.#{col}"
3024
+ if tok[0].include?("\n")
3025
+ ar = tok[0].split
3026
+ row+=tok[0].count("\n")
3027
+
3028
+ begin_gap = ar[-1]
3029
+ if begin_gap && tok[0][-1..-1]!="\n"
3030
+ col = begin_gap.length
3031
+ else
3032
+ col = 0
3033
+ end
3034
+ else
3035
+ col+=toklength
3036
+ end
3037
+ t_end="#{row}.#{col}"
3038
+ if tok[1]!=:space
3039
+ tags_map[tok[1]] = [] if tags_map[tok[1]].nil?
3040
+ tags_map[tok[1]] << [t_begin,t_end]
3041
+ #Arcadia.console(self, 'msg'=>"#{tok[1]}=#{[t_begin,t_end]}", 'level'=>'error')
3042
+ #p [t_begin,t_end]
3043
+ end
3044
+ end
3045
+ }
3046
+ tags_map
3047
+ end
2826
3048
  end
2827
3049
 
2828
3050
 
2829
3051
  class AgMultiEditor < ArcadiaExt
2830
3052
  include Autils
3053
+ include Configurable
2831
3054
  attr_reader :breakpoints
2832
3055
  attr_reader :splitted_frame
3056
+ attr_reader :outline_bar
2833
3057
  def on_before_build(_event)
2834
3058
  @breakpoints =Array.new
2835
3059
  @tabs_file =Hash.new
@@ -2837,7 +3061,8 @@ class AgMultiEditor < ArcadiaExt
2837
3061
  Arcadia.attach_listener(self, BufferEvent)
2838
3062
  Arcadia.attach_listener(self, DebugEvent)
2839
3063
  Arcadia.attach_listener(self, RunRubyFileEvent)
2840
- Arcadia.attach_listener(self, StartDebugEvent)
3064
+ # Arcadia.attach_listener(self, StartDebugEvent)
3065
+ Arcadia.attach_listener(self, FocusEvent)
2841
3066
  end
2842
3067
 
2843
3068
 
@@ -2856,18 +3081,20 @@ class AgMultiEditor < ArcadiaExt
2856
3081
  end
2857
3082
  end
2858
3083
 
2859
- def on_before_start_debug(_event)
2860
- _filename = _event.file
2861
- if _filename.nil?
2862
- current_editor = self.raised
2863
- _event.file =current_editor.file if current_editor
2864
- end
2865
- end
3084
+ # def on_before_start_debug(_event)
3085
+ # _filename = _event.file
3086
+ # if _filename.nil?
3087
+ # current_editor = self.raised
3088
+ # _event.file =current_editor.file if current_editor
3089
+ # end
3090
+ # end
2866
3091
 
2867
3092
  def on_build(_event)
2868
3093
  @main_frame = AgMultiEditorView.new(self.frame.hinner_frame)
2869
- create_find
3094
+ @outline_bar = AgEditorOutlineToolbar.new(self.frame(1).hinner_frame, self)
3095
+ create_find # this is the "find within current file" one
2870
3096
  pop_up_menu
3097
+
2871
3098
  #self.open_last_files
2872
3099
  end
2873
3100
 
@@ -2875,6 +3102,86 @@ class AgMultiEditor < ArcadiaExt
2875
3102
  self.open_last_files
2876
3103
  end
2877
3104
 
3105
+ def on_exit_query(_event)
3106
+ _event.can_exit=true
3107
+ @tabs_editor.each_value{|editor|
3108
+ _event.can_exit = can_close_editor?(editor)
3109
+ if !_event.can_exit
3110
+ _event.break
3111
+ break
3112
+ end
3113
+ }
3114
+ end
3115
+
3116
+ def on_after_focus(_event)
3117
+ if raised && _event.focus_widget == raised.text
3118
+ if [CutTextEvent, PasteTextEvent].include?(_event.class)
3119
+ if raised.highlighting
3120
+ line_begin_index = raised.text.index('@0,0')
3121
+ line_begin = line_begin_index.split('.')[0].to_i
3122
+ line_end = raised.text.index('@0,'+TkWinfo.height(raised.text).to_s).split('.')[0].to_i + 1
3123
+ raised.rehighlightlines(line_begin,line_end,true)
3124
+ else
3125
+ raised.check_modify
3126
+ end
3127
+ end
3128
+ end
3129
+ end
3130
+
3131
+ def highlight_scanner(_ext=nil)
3132
+ return nil if _ext.nil?
3133
+ scanner = nil
3134
+ @highlight_scanner_hash = Hash.new if !defined?(@highlight_scanner_hash)
3135
+ lh = languages_hash(_ext)
3136
+ if lh && lh['language'] && lh['scanner']
3137
+ if @highlight_scanner_hash[lh['language']].nil?
3138
+ case lh['scanner']
3139
+ when 'coderay'
3140
+ @highlight_scanner_hash[lh['language']]=CoderayHighlightScanner.new(lh)
3141
+ when 're'
3142
+ @highlight_scanner_hash[lh['language']]=ReHighlightScanner.new(lh)
3143
+ end
3144
+ end
3145
+ scanner = @highlight_scanner_hash[lh['language']]
3146
+ end
3147
+ scanner
3148
+ end
3149
+
3150
+ def languages_hash(_ext=nil)
3151
+ @@langs_hash = Hash.new if !defined?(@@langs_hash)
3152
+ return nil if _ext.nil?
3153
+ if @@langs_hash[_ext].nil?
3154
+ #_ext='' if _ext.nil?
3155
+ lang_file = File.dirname(__FILE__)+'/langs/'+_ext+'.lang'
3156
+ if File.exist?(lang_file)
3157
+ @@langs_hash[_ext] = properties_file2hash(lang_file)
3158
+ elsif File.exist?(lang_file+'.bind')
3159
+ b= properties_file2hash(lang_file+'.bind')
3160
+ if b
3161
+ if @@langs_hash[b['bind']].nil?
3162
+ lang_file_bind = File.dirname(__FILE__)+'/langs/'+b['bind']+".lang"
3163
+ if File.exist?(lang_file_bind)
3164
+ @@langs_hash[b['bind']]=properties_file2hash(lang_file_bind)
3165
+ @@langs_hash[_ext]=@@langs_hash[b['bind']]
3166
+ end
3167
+ else
3168
+ @@langs_hash[_ext]=@@langs_hash[b['bind']]
3169
+ end
3170
+ end
3171
+ end
3172
+ if @@langs_hash[_ext] && @@langs_hash[_ext]['@include'] != nil
3173
+ include_file = "#{File.dirname(__FILE__)}/langs/#{@@langs_hash[_ext]['@include']}"
3174
+ if File.exist?(include_file)
3175
+ include_hash = properties_file2hash(include_file)
3176
+ @@langs_hash[_ext] = include_hash.merge(@@langs_hash[_ext])
3177
+ end
3178
+ end
3179
+ self.resolve_properties_link(@@langs_hash[_ext], Arcadia.instance['conf']) if @@langs_hash[_ext]
3180
+ end
3181
+ @@langs_hash[_ext]
3182
+ end
3183
+
3184
+
2878
3185
  def pop_up_menu
2879
3186
  @pop_up = TkMenu.new(
2880
3187
  :parent=>@main_frame.enb,
@@ -2883,14 +3190,7 @@ class AgMultiEditor < ArcadiaExt
2883
3190
  )
2884
3191
  @pop_up.configure(Arcadia.style('menu'))
2885
3192
  #Arcadia.instance.main_menu.update_style(@pop_up)
2886
- @pop_up.insert('end',
2887
- :command,
2888
- :label=>'...',
2889
- :state=>'disabled',
2890
- :background=>Arcadia.conf('titlelabel.background'),
2891
- :font => "#{Arcadia.conf('menu.font')} bold",
2892
- :hidemargin => true
2893
- )
3193
+
2894
3194
 
2895
3195
  @c = @pop_up.insert('end',
2896
3196
  :command,
@@ -2929,6 +3229,15 @@ class AgMultiEditor < ArcadiaExt
2929
3229
  }
2930
3230
  )
2931
3231
 
3232
+ @pop_up.insert('end',
3233
+ :command,
3234
+ :label=>'...',
3235
+ :state=>'disabled',
3236
+ :background=>Arcadia.conf('titlelabel.background'),
3237
+ :font => "#{Arcadia.conf('menu.font')} bold",
3238
+ :hidemargin => false
3239
+ )
3240
+
2932
3241
  @main_frame.enb.tabbind("Button-3",
2933
3242
  proc{|*x|
2934
3243
  _x = TkWinfo.pointerx(@main_frame.enb)
@@ -2939,10 +3248,11 @@ class AgMultiEditor < ArcadiaExt
2939
3248
  @selected_tab_name_from_popup = 'ff'+@selected_tab_name_from_popup
2940
3249
  _index = @main_frame.enb.index(@selected_tab_name_from_popup)
2941
3250
  end
3251
+
2942
3252
  if _index != -1
2943
- _file = @main_frame.enb.itemcget(@selected_tab_name_from_popup, 'text')
2944
- @pop_up.entryconfigure(0, 'label'=>_file)
2945
- @pop_up.popup(_x,_y)
3253
+ _file = @tabs_file[(@selected_tab_name_from_popup)] # full path of file
3254
+ @pop_up.entryconfigure(3, 'label'=> _file)
3255
+ @pop_up.popup(_x,_y+10)
2946
3256
  end
2947
3257
  })
2948
3258
  end
@@ -2968,7 +3278,15 @@ class AgMultiEditor < ArcadiaExt
2968
3278
  end
2969
3279
 
2970
3280
  def on_before_debug(_event)
3281
+ "on_before_debug #{_event}"
2971
3282
  case _event
3283
+ when StartDebugEvent
3284
+ _filename = _event.file
3285
+ if _filename.nil?
3286
+ current_editor = self.raised
3287
+ _event.file=current_editor.file if current_editor
3288
+ end
3289
+ self.debug_begin
2972
3290
  when SetBreakpointEvent
2973
3291
  if _event.active == 1
2974
3292
  @breakpoints << {:file=>_event.file,:line=>_event.row}
@@ -2988,9 +3306,8 @@ class AgMultiEditor < ArcadiaExt
2988
3306
  end
2989
3307
 
2990
3308
  def on_after_debug(_event)
3309
+ "on_after_debug #{_event}"
2991
3310
  case _event
2992
- when StartDebugEvent
2993
- self.debug_begin
2994
3311
  when StepDebugEvent
2995
3312
  if _event.command == :quit_yes
2996
3313
  self.debug_end
@@ -3031,7 +3348,7 @@ class AgMultiEditor < ArcadiaExt
3031
3348
  when NewBufferEvent
3032
3349
  self.open_buffer
3033
3350
  when OpenBufferEvent
3034
- if _event.file
3351
+ if _event.file
3035
3352
  if _event.row
3036
3353
  _index = _event.row.to_s+'.0'
3037
3354
  end
@@ -3060,7 +3377,7 @@ class AgMultiEditor < ArcadiaExt
3060
3377
  #add_reverse_item(_e)
3061
3378
  end
3062
3379
  else
3063
- _event.file = Tk.getOpenFile
3380
+ _event.file = Arcadia.open_file_dialog
3064
3381
  self.open_file(_event.file)
3065
3382
  end
3066
3383
  when CloseBufferEvent
@@ -3071,8 +3388,9 @@ class AgMultiEditor < ArcadiaExt
3071
3388
  if _event.file == nil
3072
3389
  self.raised.save_as
3073
3390
  else
3074
- self.save_as_file(_event.file)
3391
+ self.save_as_file(_event.file)
3075
3392
  end
3393
+ _event.new_file = self.raised.file
3076
3394
  when SaveBufferEvent
3077
3395
  if _event.file == nil && _event.title == nil
3078
3396
  self.raised.save
@@ -3089,6 +3407,14 @@ class AgMultiEditor < ArcadiaExt
3089
3407
  if _event.line == nil
3090
3408
  @find.show_go_to_line_dialog
3091
3409
  end
3410
+ when CloseCurrentTabEvent
3411
+ close_raised
3412
+ when PrettifyTextEvent
3413
+ require 'rbeautify.rb' # gem
3414
+ self.raised.save # so we can beautify it kludgely here...
3415
+ path = raised.file
3416
+ RBeautify.beautify_file(path)
3417
+ self.raised.reload
3092
3418
  when MoveBufferEvent
3093
3419
  if _event.old_file && _event.new_file && editor_exist?(_event.old_file)
3094
3420
  #close_file(_event.old_file)
@@ -3101,9 +3427,8 @@ class AgMultiEditor < ArcadiaExt
3101
3427
  @find
3102
3428
  end
3103
3429
 
3104
-
3105
3430
  def create_find
3106
- @find = Find.new(@arcadia.layout.root, self)
3431
+ @find = Finder.new(@arcadia.layout.root, self)
3107
3432
  @find.on_close=proc{@find.hide}
3108
3433
  @find.hide
3109
3434
  end
@@ -3116,13 +3441,17 @@ class AgMultiEditor < ArcadiaExt
3116
3441
  def on_finalize(_event)
3117
3442
  @batch_files = true
3118
3443
  _files =''
3444
+ _raised = self.raised
3445
+ Arcadia.persistent('editor.files.last', _raised.file) if _raised
3119
3446
  @tabs_editor.each_value{|editor|
3120
3447
  if editor.file != nil
3448
+ #_insert_index = editor.text.index('insert')
3449
+ _insert_index = editor.text.index('@0,0')
3121
3450
  _files=_files+'|' if _files.strip.length > 0
3122
- _files=_files + editor.file
3451
+ _files=_files + "#{editor.file};#{_insert_index}"
3123
3452
  end
3124
3453
  #p editor.text.dump_tag('0.1',editor.text.index('end'))
3125
- close_editor(editor)
3454
+ close_editor(editor,true)
3126
3455
  }
3127
3456
  Arcadia.persistent('editor.files.open', _files)
3128
3457
  # _breakpoints = '';
@@ -3185,20 +3514,27 @@ class AgMultiEditor < ArcadiaExt
3185
3514
 
3186
3515
  def open_last_files
3187
3516
  @batch_files = true
3188
- if $arcadia['pers']['editor.files.open']
3189
- _files_index =$arcadia['pers']['editor.files.open'].split("|")
3517
+ if Arcadia.persistent('editor.files.open')
3518
+ _files_index =Arcadia.persistent('editor.files.open').split("|")
3190
3519
  _files_index.each do |value|
3191
3520
  _file,_index = value.split(';')
3192
- if _file
3193
- open_file(_file,_index)
3521
+ if _file && _index
3522
+ open_file(_file,_index,false)
3523
+ else
3524
+ open_file(_file)
3194
3525
  end
3195
3526
  end
3196
3527
  end
3197
3528
  @batch_files = false
3198
- _first_page = @main_frame.enb.pages(0) if @main_frame.enb.pages.length > 0
3199
- if _first_page
3200
- @main_frame.enb.raise(_first_page)
3201
- @main_frame.enb.see(_first_page)
3529
+ to_raise_file = Arcadia.persistent('editor.files.last')
3530
+ if to_raise_file
3531
+ raise_file(to_raise_file,0)
3532
+ else
3533
+ _first_page = @main_frame.enb.pages(0) if @main_frame.enb.pages.length > 0
3534
+ if _first_page
3535
+ @main_frame.enb.raise(_first_page) if frame_def_visible?
3536
+ @main_frame.enb.see(_first_page)
3537
+ end
3202
3538
  end
3203
3539
  frame(1)
3204
3540
  #@arcadia.layout.add_observer(self)
@@ -3304,17 +3640,22 @@ class AgMultiEditor < ArcadiaExt
3304
3640
  @main_frame.enb.itemconfigure(page_name(_tab), 'text'=> _new_text)
3305
3641
  end
3306
3642
 
3643
+ def change_tab_icon(_tab, _new_text)
3644
+ @main_frame.enb.itemconfigure(page_name(_tab), 'image'=> Arcadia.file_icon(_new_text))
3645
+ end
3646
+
3307
3647
  def change_file(_old_file, _new_file)
3308
3648
  _tab_name=tab_file_name(_old_file)
3309
3649
  _tab = @main_frame.enb.get_frame(_tab_name)
3310
3650
  e = @tabs_editor[_tab_name]
3311
- e.file =_new_file if e
3651
+ e.new_file_name(_new_file) if e
3312
3652
  change_file_name(_tab, _new_file)
3313
3653
  end
3314
3654
 
3315
3655
  def change_file_name(_tab, _new_file)
3316
3656
  _new_label = File.basename(_new_file)
3317
3657
  change_tab_title(_tab, _new_label)
3658
+ change_tab_icon(_tab, _new_label)
3318
3659
  @tabs_file[page_name(_tab)] = _new_file
3319
3660
  end
3320
3661
 
@@ -3415,6 +3756,15 @@ class AgMultiEditor < ArcadiaExt
3415
3756
  tab_name(_fstr)
3416
3757
  end
3417
3758
 
3759
+ def raise_file(_filename=nil, _pos=nil)
3760
+ if _filename && frame_def_visible?
3761
+ tab_name=self.tab_file_name(_filename)
3762
+ @main_frame.enb.move(tab_name,_pos) if _pos
3763
+ @main_frame.enb.raise(tab_name)
3764
+ @main_frame.enb.see(tab_name)
3765
+ end
3766
+ end
3767
+
3418
3768
  def open_file(_filename = nil, _text_index='1.0', _mark_selected=true, _exp=true)
3419
3769
  return if _filename == nil || !File.exist?(_filename) || File.ftype(_filename) != 'file'
3420
3770
  _basefilename = File.basename(_filename)
@@ -3431,7 +3781,7 @@ class AgMultiEditor < ArcadiaExt
3431
3781
  else
3432
3782
  open_buffer(_tab_name, _basefilename,0)
3433
3783
  end
3434
- #@tabs_file[_tab_name]= _filename
3784
+ @tabs_editor[_tab_name].reset_highlight
3435
3785
  @tabs_editor[_tab_name].load_file(_filename)
3436
3786
  end
3437
3787
 
@@ -3453,7 +3803,7 @@ class AgMultiEditor < ArcadiaExt
3453
3803
 
3454
3804
  if _index != -1
3455
3805
  _tab = @main_frame.enb.get_frame(_buffer_name)
3456
- @main_frame.enb.raise(_buffer_name)
3806
+ @main_frame.enb.raise(_buffer_name) if frame_visible?
3457
3807
  else
3458
3808
  _n = 1
3459
3809
  while @main_frame.enb.index(_buffer_name) != -1
@@ -3466,6 +3816,7 @@ class AgMultiEditor < ArcadiaExt
3466
3816
  end
3467
3817
  _tab = @main_frame.enb.insert('end', _buffer_name ,
3468
3818
  'text'=> _title,
3819
+ 'image'=> Arcadia.file_icon(_title),
3469
3820
  'background'=> Arcadia.style("tabpanel.background"),
3470
3821
  'foreground'=> Arcadia.style("tabpanel.foreground"),
3471
3822
  'raisecmd'=>proc{do_buffer_raise(_buffer_name, _title)}
@@ -3479,7 +3830,7 @@ class AgMultiEditor < ArcadiaExt
3479
3830
  @tabs_editor[_buffer_name]=_e
3480
3831
  end
3481
3832
  @main_frame.enb.move(_buffer_name, 1)
3482
- @main_frame.enb.raise(_buffer_name)
3833
+ @main_frame.enb.raise(_buffer_name) if frame_visible?
3483
3834
  @main_frame.enb.see(_buffer_name)
3484
3835
  return _tab
3485
3836
  end
@@ -3499,24 +3850,54 @@ class AgMultiEditor < ArcadiaExt
3499
3850
  end
3500
3851
  @batch_files = false
3501
3852
  end
3502
-
3503
- def close_editor(_editor, _mod=true)
3504
- if ((_mod)&&(_editor.modified?))
3505
- _message = @main_frame.enb.itemcget(page_name(_editor.page_frame), 'text')+"\n modified. Save?"
3506
- _r = TkDialog2.new('message'=>_message, 'buttons'=>['Ok','No','Cancel']).show()
3507
- if _r == 0
3853
+
3854
+ def can_close_editor?(_editor)
3855
+ ret = true
3856
+ if _editor.modified?
3857
+ filename = page_name(_editor.page_frame)
3858
+ message = @main_frame.enb.itemcget(filename, 'text')+"\n modified. Save?"
3859
+ r=Arcadia.dialog(self,
3860
+ 'type'=>'yes_no_cancel',
3861
+ 'level'=>'warning',
3862
+ 'title'=> 'Confirm saving',
3863
+ 'msg'=>message)
3864
+ if r=="yes"
3508
3865
  _editor.save
3509
- elsif _r == 1
3510
- close_tab(_editor.page_frame)
3511
- elsif _r == 2
3512
- return
3866
+ ret = !_editor.modified?
3867
+ elsif r=="cancel"
3868
+ ret = false
3513
3869
  end
3514
- else
3870
+ end
3871
+ ret
3872
+ end
3873
+
3874
+ def close_editor(_editor, _force=false)
3875
+ if _force || can_close_editor?(_editor)
3876
+ _editor.destroy_outline
3515
3877
  close_tab(_editor.page_frame)
3878
+ else
3879
+ return
3516
3880
  end
3517
- #EditorContract.instance.file_closed(self, 'file'=>_editor.file)
3518
3881
  end
3519
3882
 
3883
+
3884
+ # def close_editor(_editor, _mod=true)
3885
+ # if ((_mod)&&(_editor.modified?))
3886
+ # _message = @main_frame.enb.itemcget(page_name(_editor.page_frame), 'text')+"\n modified. Save?"
3887
+ # _r = TkDialog2.new('message'=>_message, 'buttons'=>['Ok','No','Cancel']).show()
3888
+ # if _r == 0
3889
+ # _editor.save
3890
+ # elsif _r == 1
3891
+ # close_tab(_editor.page_frame)
3892
+ # elsif _r == 2
3893
+ # return
3894
+ # end
3895
+ # else
3896
+ # close_tab(_editor.page_frame)
3897
+ # end
3898
+ # #EditorContract.instance.file_closed(self, 'file'=>_editor.file)
3899
+ # end
3900
+
3520
3901
  def close_tab(_page_frame)
3521
3902
  _name = page_name(_page_frame)
3522
3903
  @tabs_editor.delete(_name)
@@ -3626,7 +4007,16 @@ class Findview < TkFloatTitledFrame
3626
4007
  #pack('side'=>'left', 'anchor'=>'e')
3627
4008
  place('x' => 8,'y' => y0,'height' => 22)
3628
4009
  }
4010
+ y0 = y0 + d
4011
+ @cb_ignore_case = TkCheckButton.new(self.frame, Arcadia.style('checkbox')){|_cb_reg|
4012
+ text 'Ignore case'
4013
+ justify 'left'
4014
+ #relief 'flat'
4015
+ #pack('side'=>'left', 'anchor'=>'e')
4016
+ place('x' => 8,'y' => y0,'height' => 22)
4017
+ }
3629
4018
 
4019
+ y0 = y0 + d
3630
4020
  y0 = y0 + d
3631
4021
  y0 = y0 + d
3632
4022
  @buttons_frame = TkFrame.new(self.frame, Arcadia.style('panel')).pack('fill'=>'x', 'side'=>'bottom')
@@ -3669,7 +4059,7 @@ class Findview < TkFloatTitledFrame
3669
4059
  #place('width' => 50,'x' => 0,'y' => y0,'height' => 23,'bordermode' => 'inside')
3670
4060
  }
3671
4061
  #place('x'=>0,'y'=>0,'relheight'=> 1,'relwidth'=> 1)
3672
- place('x'=>100,'y'=>100,'height'=> 220,'width'=> 300)
4062
+ place('x'=>100,'y'=>100,'height'=> 240,'width'=> 300)
3673
4063
 
3674
4064
  end
3675
4065
 
@@ -3683,7 +4073,7 @@ class Findview < TkFloatTitledFrame
3683
4073
 
3684
4074
  end
3685
4075
 
3686
- class Find < Findview
4076
+ class Finder < Findview
3687
4077
  attr_reader :e_what
3688
4078
  def initialize(_frame, _controller)
3689
4079
  super(_frame)
@@ -3774,15 +4164,18 @@ class Find < Findview
3774
4164
  end
3775
4165
 
3776
4166
  def show_go_to_line_dialog
4167
+ use(@controller.raised)
3777
4168
  @goto_line_dialog.show
3778
4169
  end
3779
4170
 
3780
4171
  def go_line
3781
4172
  if @goto_line_dialog.e_line.value.length > 0
3782
4173
  _row = @goto_line_dialog.e_line.value
3783
- _index = _row+'.1'
4174
+ _index = _row.strip+'.1'
3784
4175
  self.editor.text.see(_index)
3785
- self.editor.text.tag_add('sel', _index,_index+' lineend')
4176
+ self.editor.text.tag_remove('selected','1.0','end')
4177
+ self.editor.text.tag_add('selected',_index,_index+' lineend')
4178
+ #self.editor.text.tag_add('sel', _index,_index+' lineend')
3786
4179
  self.editor.text.set_insert(_index)
3787
4180
  @controller.bookmark_add(self.editor.file, _index)
3788
4181
  @goto_line_dialog.hide
@@ -3826,20 +4219,20 @@ class Find < Findview
3826
4219
  else
3827
4220
  _istart = '1.0'
3828
4221
  end
3829
- if @forwards
3830
- if @cb_reg.cget('onvalue')==@cb_reg.cget('variable').value.to_i
3831
- _index = self.editor.text.tksearch(['regexp'],@e_what.text,_istart)
3832
- else
3833
- _index = self.editor.text.search(@e_what.text,_istart)
3834
- end
3835
- else
3836
-
3837
- if @cb_reg.cget('onvalue')==@cb_reg.cget('variable').value.to_i
3838
- _index = self.editor.text.tksearch(['regexp','backwards'],@e_what.text,_istart)
3839
- else
3840
- _index = self.editor.text.tksearch(['backwards'],@e_what.text,_istart)
3841
- end
4222
+
4223
+ # propagate some search options
4224
+ options = []
4225
+ if !@forwards
4226
+ options << 'backwards'
4227
+ end
4228
+ if @cb_reg.cget('onvalue')==@cb_reg.cget('variable').value.to_i
4229
+ options << 'regexp'
3842
4230
  end
4231
+ if @cb_ignore_case.cget('onvalue')==@cb_ignore_case.cget('variable').value.to_i
4232
+ options << 'nocase'
4233
+ end
4234
+ _index = self.editor.text.tksearch(options,@e_what.text,_istart)
4235
+
3843
4236
  if _index && _index.length>0
3844
4237
  self.editor.text.see(_index)
3845
4238
  _row, _col = _index.split('.')
@@ -3852,7 +4245,7 @@ class Find < Findview
3852
4245
  self.editor.text.tag_add('sel', _index,_index_sel_end)
3853
4246
  self.editor.text.set_insert(_index)
3854
4247
  @idx1 =_index
3855
- @idx2 =_index_sel_end
4248
+ @idx2 =_index_sel_end
3856
4249
  _found = true
3857
4250
  @controller.bookmark_add(self.editor.file, _index)
3858
4251
  else
@@ -3922,4 +4315,4 @@ class GoToLine < TkFloatTitledFrame
3922
4315
  @e_line.focus
3923
4316
  @e_line.selection_range(0,'end')
3924
4317
  end
3925
- end
4318
+ end