redcar 0.3.4.3 → 0.3.5
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- data/CHANGES +45 -0
- data/README.md +2 -1
- data/ROADMAP.md +0 -1
- data/Rakefile +10 -4
- data/bin/redcar +2 -2
- data/lib/openssl/build.properties +7 -0
- data/lib/plugin_manager/lib/plugin_manager.rb +10 -0
- data/lib/plugin_manager/lib/plugin_manager/plugin_definition.rb +1 -13
- data/lib/redcar.rb +12 -8
- data/lib/redcar/installer.rb +16 -15
- data/lib/redcar/ruby_extensions.rb +146 -1
- data/lib/redcar/runner.rb +16 -7
- data/lib/redcar/usage.rb +4 -7
- data/lib/redcar_quick_start.rb +5 -5
- data/lib/regex_replace.rb +0 -7
- data/plugins/application/features/step_definitions/command_steps.rb +5 -0
- data/plugins/application/features/step_definitions/dialog_steps.rb +5 -0
- data/plugins/application/features/step_definitions/filter_list_dialog_steps.rb +38 -0
- data/plugins/application/features/step_definitions/window_steps.rb +1 -1
- data/plugins/application/features/support/env.rb +44 -8
- data/plugins/application/lib/application.rb +32 -33
- data/plugins/application/lib/application/command.rb +32 -2
- data/plugins/application/lib/application/command/executor.rb +2 -12
- data/plugins/application/lib/application/dialog.rb +14 -14
- data/plugins/application/lib/application/event_spewer.rb +32 -0
- data/plugins/application/lib/application/menu.rb +5 -5
- data/plugins/application/lib/application/menu/builder.rb +5 -0
- data/plugins/application/lib/application/menu/lazy_menu.rb +24 -0
- data/plugins/application/lib/application/notebook.rb +4 -3
- data/plugins/application/lib/application/tab.rb +6 -2
- data/plugins/application/lib/application/window.rb +8 -4
- data/plugins/application/spec/application/menu/builder_spec.rb +17 -1
- data/plugins/application/spec/application/notebook_spec.rb +1 -1
- data/plugins/application_swt/build.xml +74 -0
- data/plugins/application_swt/lib/application_swt.rb +79 -0
- data/plugins/application_swt/lib/application_swt/cucumber_patches.rb +6 -1
- data/plugins/application_swt/lib/application_swt/dialog_adapter.rb +25 -17
- data/plugins/application_swt/lib/application_swt/dialogs/filter_list_dialog_controller.rb +50 -12
- data/plugins/application_swt/lib/application_swt/html_tab.rb +20 -0
- data/plugins/application_swt/lib/application_swt/menu.rb +26 -2
- data/plugins/application_swt/lib/application_swt/notebook.rb +10 -12
- data/plugins/application_swt/lib/application_swt/window.rb +11 -11
- data/plugins/application_swt/src/com/redcareditor/application_swt/CocoaUIEnhancer.java +313 -0
- data/plugins/auto_completer/lib/auto_completer.rb +74 -67
- data/plugins/auto_completer/lib/auto_completer/current_document_completion_source.rb +19 -0
- data/plugins/auto_completer/lib/auto_completer/document_controller.rb +2 -2
- data/plugins/auto_completer/lib/auto_completer/word_list.rb +8 -1
- data/plugins/auto_indenter/features/ruby_style_indentation.feature +24 -0
- data/plugins/auto_indenter/features/step_definitions/indentation_steps.rb +6 -0
- data/plugins/auto_indenter/features/support/env.rb +2 -0
- data/plugins/auto_indenter/lib/auto_indenter.rb +86 -0
- data/plugins/auto_indenter/lib/auto_indenter/analyzer.rb +91 -0
- data/plugins/auto_indenter/lib/auto_indenter/commands.rb +34 -0
- data/plugins/auto_indenter/lib/auto_indenter/document_controller.rb +67 -12
- data/plugins/auto_indenter/lib/auto_indenter/rules.rb +41 -0
- data/plugins/auto_indenter/spec/auto_indenter/analyzer_spec.rb +151 -0
- data/plugins/auto_indenter/spec/spec_helper.rb +5 -0
- data/plugins/auto_pairer/lib/auto_pairer.rb +1 -0
- data/plugins/auto_pairer/lib/auto_pairer/document_controller.rb +43 -42
- data/plugins/auto_pairer/lib/auto_pairer/pairs_for_scope.rb +1 -5
- data/plugins/core/lib/core.rb +12 -1
- data/plugins/core/lib/core/observable.rb +7 -7
- data/plugins/core/lib/core/persistent_cache.rb +14 -2
- data/plugins/core/lib/core/plugin.rb +7 -0
- data/plugins/core/lib/core/resource.rb +78 -0
- data/plugins/core/lib/core/task.rb +62 -0
- data/plugins/core/lib/core/task_queue.rb +72 -0
- data/plugins/core/spec/core/resource_spec.rb +124 -0
- data/plugins/core/spec/core/task_queue_spec.rb +202 -0
- data/plugins/core/spec/spec_helper.rb +23 -1
- data/plugins/declarations/TODO +3 -0
- data/plugins/declarations/lib/declarations.rb +144 -0
- data/plugins/declarations/lib/declarations/completion_source.rb +22 -0
- data/plugins/declarations/lib/declarations/file.rb +68 -0
- data/plugins/declarations/lib/declarations/parser.rb +94 -0
- data/plugins/declarations/lib/declarations/select_tag_dialog.rb +44 -0
- data/plugins/declarations/plugin.rb +7 -0
- data/plugins/declarations/spec/declarations/file_spec.rb +62 -0
- data/plugins/declarations/spec/fixtures/federalist.rb +15 -0
- data/plugins/declarations/spec/spec_helper.rb +4 -0
- data/plugins/edit_view/features/indentation_commands.feature +40 -0
- data/plugins/edit_view/features/line_delimiter.feature +40 -0
- data/plugins/edit_view/features/step_definitions/editing_steps.rb +16 -4
- data/plugins/edit_view/features/step_definitions/notebook_steps.rb +1 -1
- data/plugins/edit_view/features/step_definitions/tab_steps.rb +1 -1
- data/plugins/edit_view/features/step_definitions/window_steps.rb +5 -1
- data/plugins/edit_view/features/support/env.rb +3 -5
- data/plugins/edit_view/features/undo_and_redo.feature +21 -0
- data/plugins/edit_view/lib/edit_view.rb +57 -4
- data/plugins/edit_view/lib/edit_view/actions/arrow_keys.rb +19 -3
- data/plugins/edit_view/lib/edit_view/document.rb +46 -11
- data/plugins/edit_view/lib/edit_view/document/indentation.rb +35 -0
- data/plugins/edit_view/lib/edit_view/modified_tabs_checker.rb +35 -0
- data/plugins/edit_view/lib/edit_view/tab_settings.rb +13 -3
- data/plugins/edit_view/spec/edit_view/document/indentation_spec.rb +112 -0
- data/plugins/edit_view/spec/edit_view/document_spec.rb +22 -0
- data/plugins/edit_view/spec/spec_helper.rb +1 -0
- data/plugins/edit_view_swt/lib/edit_view_swt.rb +59 -7
- data/plugins/edit_view_swt/lib/edit_view_swt/document.rb +3 -3
- data/plugins/edit_view_swt/lib/edit_view_swt/word_movement.rb +2 -2
- data/plugins/edit_view_swt/vendor/java-mateview.rb +3 -2
- data/plugins/encryption/encryption.rb +13 -6
- data/plugins/execute_current_tab/lib/execute_current_tab.rb +25 -15
- data/plugins/html_view/assets/redcar.css +32 -1
- data/plugins/html_view/lib/html_view.rb +23 -3
- data/plugins/html_view/lib/html_view/html_tab.rb +4 -0
- data/plugins/my_plugin/lib/my_plugin.rb +4 -12
- data/plugins/plugin_manager_ui/lib/plugin_manager_ui.rb +1 -0
- data/plugins/plugin_manager_ui/views/index.html.erb +30 -37
- data/plugins/project/features/find_file.feature +75 -0
- data/plugins/project/features/open_and_save_files.feature +7 -7
- data/plugins/project/features/open_directory_tree.feature +11 -3
- data/plugins/project/features/refresh_directory_tree.feature +7 -1
- data/plugins/project/features/step_definitions/directory_steps.rb +11 -1
- data/plugins/project/features/step_definitions/file_steps.rb +10 -0
- data/plugins/project/features/support/env.rb +6 -1
- data/plugins/project/features/watch_for_modified_files.feature +79 -0
- data/plugins/project/lib/project.rb +72 -306
- data/plugins/project/lib/project/commands.rb +128 -0
- data/plugins/project/lib/project/dir_mirror.rb +5 -1
- data/plugins/project/lib/project/drb_service.rb +21 -31
- data/plugins/project/lib/project/file_list.rb +76 -0
- data/plugins/project/lib/project/file_mirror.rb +13 -1
- data/plugins/project/lib/project/find_file_dialog.rb +22 -52
- data/plugins/project/lib/project/manager.rb +210 -0
- data/plugins/project/lib/project/recent_directories.rb +16 -3
- data/plugins/project/plugin.rb +1 -1
- data/plugins/project/spec/fixtures/myproject/README +2 -0
- data/plugins/project/spec/fixtures/myproject/lib/foo_lib.rb +1 -0
- data/plugins/project/spec/fixtures/myproject/spec/foo_spec.rb +1 -0
- data/plugins/project/{features → spec}/fixtures/winter.txt +0 -0
- data/plugins/project/spec/project/dir_mirror_spec.rb +1 -12
- data/plugins/project/spec/project/file_list_spec.rb +140 -0
- data/plugins/project/spec/spec_helper.rb +20 -0
- data/plugins/redcar/plugin.rb +1 -0
- data/plugins/redcar/redcar.rb +254 -84
- data/plugins/redcar_debug/lib/redcar_debug.rb +58 -11
- data/plugins/redcar_debug/vendor/jruby-prof/README +46 -0
- data/plugins/redcar_debug/vendor/jruby-prof/Rakefile +36 -0
- data/plugins/redcar_debug/vendor/jruby-prof/build.xml +31 -0
- data/plugins/redcar_debug/vendor/jruby-prof/example/call_tree.html +22677 -0
- data/plugins/redcar_debug/vendor/jruby-prof/example/call_tree.txt +589 -0
- data/plugins/redcar_debug/vendor/jruby-prof/example/flat.txt +28 -0
- data/plugins/redcar_debug/vendor/jruby-prof/example/graph.html +1670 -0
- data/plugins/redcar_debug/vendor/jruby-prof/example/graph.txt +125 -0
- data/plugins/redcar_debug/vendor/jruby-prof/example/pidigits.rb +92 -0
- data/plugins/redcar_debug/vendor/jruby-prof/example/test.rb +28 -0
- data/plugins/redcar_debug/vendor/jruby-prof/example/test2.rb +29 -0
- data/plugins/redcar_debug/vendor/jruby-prof/example/test_exception.rb +28 -0
- data/plugins/redcar_debug/vendor/jruby-prof/example/test_overhead.rb +43 -0
- data/plugins/redcar_debug/vendor/jruby-prof/lib/jruby-prof.rb +66 -0
- data/plugins/redcar_debug/vendor/jruby-prof/lib/jruby-prof/abstract_printer.rb +21 -0
- data/plugins/redcar_debug/vendor/jruby-prof/lib/jruby-prof/flat_text_printer.rb +35 -0
- data/plugins/redcar_debug/vendor/jruby-prof/lib/jruby-prof/graph_html_printer.rb +123 -0
- data/plugins/redcar_debug/vendor/jruby-prof/lib/jruby-prof/graph_text_printer.rb +45 -0
- data/plugins/redcar_debug/vendor/jruby-prof/lib/jruby-prof/invocation_set.rb +34 -0
- data/plugins/redcar_debug/vendor/jruby-prof/lib/jruby-prof/method.rb +107 -0
- data/plugins/redcar_debug/vendor/jruby-prof/lib/jruby-prof/profile_invocation.rb +43 -0
- data/plugins/redcar_debug/vendor/jruby-prof/lib/jruby-prof/simple_tree_printer.rb +27 -0
- data/plugins/redcar_debug/vendor/jruby-prof/lib/jruby-prof/tree_html_printer.rb +144 -0
- data/plugins/redcar_debug/vendor/jruby-prof/src/org/jruby/prof/Invocation.java +14 -0
- data/plugins/redcar_debug/vendor/jruby-prof/src/org/jruby/prof/JRubyProf.java +94 -0
- data/plugins/redcar_debug/vendor/jruby-prof/src/org/jruby/prof/ProfEventHook.java +49 -0
- data/plugins/redcar_debug/vendor/jruby-prof/templates/graph_row.html.erb +18 -0
- data/plugins/redcar_debug/vendor/jruby-prof/test/basic_test.rb +291 -0
- data/plugins/redcar_debug/views/history.html.erb +33 -0
- data/plugins/redcar_debug/views/index.html.erb +33 -0
- data/plugins/repl/lib/repl/internal_mirror.rb +3 -15
- data/plugins/repl/spec/repl/internal_mirror_spec.rb +2 -2
- data/plugins/snippets/lib/snippets.rb +0 -1
- data/plugins/snippets/lib/snippets/document_controller.rb +7 -1
- data/plugins/task_manager/lib/task_manager.rb +28 -0
- data/plugins/task_manager/plugin.rb +11 -0
- data/plugins/task_manager/views/index.html.erb +67 -0
- data/plugins/textmate/lib/textmate.rb +17 -21
- data/plugins/textmate/lib/textmate/plist.rb +1 -2
- data/plugins/textmate/lib/textmate/preference.rb +5 -1
- data/plugins/textmate/lib/textmate/snippet.rb +6 -1
- data/plugins/tree_view_swt/lib/tree_view_swt.rb +0 -6
- data/textmate/Bundles/Cucumber.tmbundle/Preferences/Comments.tmPreferences +1 -1
- data/textmate/Bundles/Cucumber.tmbundle/Preferences/next_Cucumber_Plain_Text_Feature_Completions.tmPreferences +30 -0
- data/textmate/Bundles/Cucumber.tmbundle/Preferences/next_Symbol_list___Scenario.tmPreferences +19 -0
- data/textmate/Bundles/Cucumber.tmbundle/Syntaxes/next_Cucumber_Plain_Text_Feature.tmLanguage +221 -0
- data/textmate/Bundles/Cucumber.tmbundle/Syntaxes/next_Cucumber_Steps.tmLanguage +424 -0
- data/textmate/Bundles/Cucumber.tmbundle/Syntaxes/plaintext_template.erb +19 -77
- data/textmate/Bundles/Cucumber.tmbundle/info.plist +1 -20
- data/textmate/Bundles/Perl.tmbundle/Syntaxes/Perl.plist +1 -1
- data/textmate/Themes/Emacs Strict.tmTheme +241 -0
- data/textmate/Themes/IR_White.tmTheme +792 -0
- data/textmate/Themes/Monokai.tmTheme +291 -0
- data/textmate/Themes/WhysPoignant.tmTheme +191 -0
- metadata +92 -7
- data/plugins/application/features/main_window.feature +0 -8
- data/plugins/project/lib/project/project_command.rb +0 -5
- data/textmate/Bundles/Cucumber.tmbundle/Snippets/Scenario.tmSnippet +0 -22
- data/textmate/Bundles/Cucumber.tmbundle/Snippets/Story.tmSnippet +0 -25
|
@@ -2,7 +2,10 @@
|
|
|
2
2
|
module Cucumber
|
|
3
3
|
module Ast
|
|
4
4
|
class StepInvocation #:nodoc:#
|
|
5
|
-
|
|
5
|
+
class << self
|
|
6
|
+
attr_accessor :wait_time
|
|
7
|
+
end
|
|
8
|
+
|
|
6
9
|
def invoke(step_mother, options)
|
|
7
10
|
block = Swt::RRunnable.new do
|
|
8
11
|
find_step_match!(step_mother)
|
|
@@ -28,6 +31,8 @@ module Cucumber
|
|
|
28
31
|
if ENV["SLOW_CUKES"]
|
|
29
32
|
sleep ENV["SLOW_CUKES"].to_f
|
|
30
33
|
end
|
|
34
|
+
sleep(Cucumber::Ast::StepInvocation.wait_time || 0)
|
|
35
|
+
Cucumber::Ast::StepInvocation.wait_time = nil
|
|
31
36
|
end
|
|
32
37
|
end
|
|
33
38
|
end
|
|
@@ -1,16 +1,16 @@
|
|
|
1
1
|
module Redcar
|
|
2
2
|
class ApplicationSWT
|
|
3
3
|
class DialogAdapter
|
|
4
|
-
def open_file(
|
|
5
|
-
file_dialog(
|
|
4
|
+
def open_file(options)
|
|
5
|
+
file_dialog(Swt::SWT::OPEN, options)
|
|
6
6
|
end
|
|
7
7
|
|
|
8
|
-
def open_directory(
|
|
9
|
-
directory_dialog(
|
|
8
|
+
def open_directory(options)
|
|
9
|
+
directory_dialog(options)
|
|
10
10
|
end
|
|
11
11
|
|
|
12
|
-
def save_file(
|
|
13
|
-
file_dialog(
|
|
12
|
+
def save_file(options)
|
|
13
|
+
file_dialog(Swt::SWT::SAVE, options)
|
|
14
14
|
end
|
|
15
15
|
|
|
16
16
|
MESSAGE_BOX_TYPES = {
|
|
@@ -40,14 +40,14 @@ module Redcar
|
|
|
40
40
|
:abort_retry_ignore => [:abort, :retry, :ignore]
|
|
41
41
|
}
|
|
42
42
|
|
|
43
|
-
def message_box(
|
|
43
|
+
def message_box(text, options)
|
|
44
44
|
styles = 0
|
|
45
45
|
styles = styles | MESSAGE_BOX_TYPES[options[:type]] if options[:type]
|
|
46
46
|
if options[:buttons]
|
|
47
47
|
buttons = MESSAGE_BOX_BUTTON_COMBOS[options[:buttons]]
|
|
48
48
|
buttons.each {|b| styles = styles | BUTTONS[b] }
|
|
49
49
|
end
|
|
50
|
-
dialog = Swt::Widgets::MessageBox.new(
|
|
50
|
+
dialog = Swt::Widgets::MessageBox.new(parent_shell, styles)
|
|
51
51
|
dialog.set_message(text)
|
|
52
52
|
result = nil
|
|
53
53
|
Redcar.app.protect_application_focus do
|
|
@@ -75,12 +75,12 @@ module Redcar
|
|
|
75
75
|
|
|
76
76
|
def createShell
|
|
77
77
|
super
|
|
78
|
-
p [:in, get_shell]
|
|
79
78
|
end
|
|
80
79
|
end
|
|
81
80
|
|
|
82
|
-
def input(
|
|
83
|
-
dialog = JFace::Dialogs::InputDialog.new(
|
|
81
|
+
def input(title, message, initial_value, &block)
|
|
82
|
+
dialog = JFace::Dialogs::InputDialog.new(
|
|
83
|
+
parent_shell,
|
|
84
84
|
title, message, initial_value) do |text|
|
|
85
85
|
block ? block[text] : nil
|
|
86
86
|
end
|
|
@@ -89,16 +89,16 @@ module Redcar
|
|
|
89
89
|
{:button => button, :value => dialog.getValue}
|
|
90
90
|
end
|
|
91
91
|
|
|
92
|
-
def tool_tip(
|
|
93
|
-
tool_tip = Swt::Widgets::ToolTip.new(
|
|
92
|
+
def tool_tip(message)
|
|
93
|
+
tool_tip = Swt::Widgets::ToolTip.new(parent_shell, Swt::SWT::ICON_INFORMATION)
|
|
94
94
|
tool_tip.set_message(message)
|
|
95
95
|
tool_tip.set_visible(true)
|
|
96
96
|
end
|
|
97
97
|
|
|
98
98
|
private
|
|
99
99
|
|
|
100
|
-
def file_dialog(
|
|
101
|
-
dialog = Swt::Widgets::FileDialog.new(
|
|
100
|
+
def file_dialog(type, options)
|
|
101
|
+
dialog = Swt::Widgets::FileDialog.new(parent_shell, type)
|
|
102
102
|
if options[:filter_path]
|
|
103
103
|
dialog.set_filter_path(options[:filter_path])
|
|
104
104
|
end
|
|
@@ -107,8 +107,8 @@ module Redcar
|
|
|
107
107
|
end
|
|
108
108
|
end
|
|
109
109
|
|
|
110
|
-
def directory_dialog(
|
|
111
|
-
dialog = Swt::Widgets::DirectoryDialog.new(
|
|
110
|
+
def directory_dialog(options)
|
|
111
|
+
dialog = Swt::Widgets::DirectoryDialog.new(parent_shell)
|
|
112
112
|
if options[:filter_path]
|
|
113
113
|
dialog.set_filter_path(options[:filter_path])
|
|
114
114
|
end
|
|
@@ -116,6 +116,14 @@ module Redcar
|
|
|
116
116
|
dialog.open
|
|
117
117
|
end
|
|
118
118
|
end
|
|
119
|
+
|
|
120
|
+
def parent_shell
|
|
121
|
+
if focussed_window = Redcar.app.focussed_window
|
|
122
|
+
focussed_window.controller.shell
|
|
123
|
+
else
|
|
124
|
+
Redcar.app.controller.fake_shell
|
|
125
|
+
end
|
|
126
|
+
end
|
|
119
127
|
end
|
|
120
128
|
end
|
|
121
129
|
end
|
|
@@ -2,7 +2,13 @@ module Redcar
|
|
|
2
2
|
class ApplicationSWT
|
|
3
3
|
class FilterListDialogController
|
|
4
4
|
include ReentryHelpers
|
|
5
|
-
|
|
5
|
+
|
|
6
|
+
class << self
|
|
7
|
+
# when set, the FilterListDialog is non-modal for testing
|
|
8
|
+
attr_writer :test_mode
|
|
9
|
+
def test_mode?; @test_mode; end
|
|
10
|
+
end
|
|
11
|
+
|
|
6
12
|
class FilterListDialog < Dialogs::NoButtonsDialog
|
|
7
13
|
attr_reader :list, :text
|
|
8
14
|
attr_accessor :controller
|
|
@@ -14,12 +20,13 @@ module Redcar
|
|
|
14
20
|
|
|
15
21
|
@text = Swt::Widgets::Text.new(composite, Swt::SWT::SINGLE | Swt::SWT::LEFT | Swt::SWT::ICON_CANCEL)
|
|
16
22
|
@text.set_layout_data(Swt::Layout::RowData.new(400, 20))
|
|
17
|
-
@list = Swt::Widgets::List.new(composite, Swt::SWT::SINGLE)
|
|
23
|
+
@list = Swt::Widgets::List.new(composite, Swt::SWT::V_SCROLL | Swt::SWT::H_SCROLL | Swt::SWT::SINGLE)
|
|
18
24
|
@list.set_layout_data(Swt::Layout::RowData.new(400, 200))
|
|
19
25
|
controller.attach_listeners
|
|
20
|
-
controller.
|
|
26
|
+
controller.update_list_sync
|
|
21
27
|
get_shell.add_shell_listener(ShellListener.new(controller))
|
|
22
28
|
ApplicationSWT.register_shell(get_shell)
|
|
29
|
+
ApplicationSWT.register_dialog(get_shell, self)
|
|
23
30
|
|
|
24
31
|
@list.set_selection(0)
|
|
25
32
|
end
|
|
@@ -57,6 +64,10 @@ module Redcar
|
|
|
57
64
|
@model = model
|
|
58
65
|
@dialog = FilterListDialog.new(Redcar.app.focussed_window.controller.shell)
|
|
59
66
|
@dialog.controller = self
|
|
67
|
+
if FilterListDialogController.test_mode?
|
|
68
|
+
@dialog.setBlockOnOpen(false)
|
|
69
|
+
@dialog.setShellStyle(Swt::SWT::DIALOG_TRIM)
|
|
70
|
+
end
|
|
60
71
|
attach_model_listeners
|
|
61
72
|
end
|
|
62
73
|
|
|
@@ -81,42 +92,69 @@ module Redcar
|
|
|
81
92
|
end
|
|
82
93
|
|
|
83
94
|
def key_pressed(e)
|
|
84
|
-
|
|
95
|
+
@controller.key_pressed(e)
|
|
85
96
|
end
|
|
86
97
|
|
|
87
98
|
def key_released(e)
|
|
88
99
|
end
|
|
89
100
|
end
|
|
90
101
|
|
|
102
|
+
class SelectionListener
|
|
103
|
+
def initialize(controller)
|
|
104
|
+
@controller = controller
|
|
105
|
+
end
|
|
106
|
+
|
|
107
|
+
def widgetDefaultSelected(e)
|
|
108
|
+
@controller.selected
|
|
109
|
+
end
|
|
110
|
+
|
|
111
|
+
def widgetSelected(e)
|
|
112
|
+
@controller.text_focus
|
|
113
|
+
end
|
|
114
|
+
end
|
|
115
|
+
|
|
91
116
|
def attach_listeners
|
|
92
117
|
@dialog.text.add_modify_listener(ModifyListener.new(self))
|
|
93
118
|
@dialog.text.add_key_listener(KeyListener.new(self))
|
|
119
|
+
@dialog.list.add_selection_listener(SelectionListener.new(self))
|
|
94
120
|
end
|
|
95
121
|
|
|
96
122
|
def open
|
|
97
123
|
@dialog.open
|
|
98
|
-
@dialog = nil
|
|
124
|
+
@dialog = nil unless FilterListDialogController.test_mode?
|
|
99
125
|
end
|
|
100
126
|
|
|
101
127
|
def close
|
|
102
128
|
@dialog.close
|
|
129
|
+
ApplicationSWT.unregister_dialog(@dialog)
|
|
130
|
+
@dialog = nil
|
|
103
131
|
end
|
|
104
132
|
|
|
105
133
|
def update_list
|
|
106
134
|
@last_keypress = Time.now
|
|
107
135
|
pause_time = FilterListDialogController.storage['pause_before_update_seconds']
|
|
108
|
-
Swt::Widgets::Display.getCurrent.timerExec(pause_time*1000, Swt::RRunnable.new {
|
|
109
|
-
if @
|
|
136
|
+
Swt::Widgets::Display.getCurrent.timerExec(pause_time*1000, Swt::RRunnable.new {
|
|
137
|
+
if @last_keypress and (Time.now - @last_keypress + pause_time) > pause_time
|
|
110
138
|
@last_keypress = nil
|
|
111
|
-
|
|
112
|
-
list = @model.update_list(@dialog.text.get_text)
|
|
113
|
-
puts "update list took #{Time.now - s}s"
|
|
114
|
-
populate_list(list)
|
|
115
|
-
@dialog.list.set_selection(0)
|
|
139
|
+
update_list_sync
|
|
116
140
|
end
|
|
117
141
|
})
|
|
118
142
|
end
|
|
119
143
|
|
|
144
|
+
def update_list_sync
|
|
145
|
+
if @dialog
|
|
146
|
+
s = Time.now
|
|
147
|
+
list = @model.update_list(@dialog.text.get_text)
|
|
148
|
+
populate_list(list)
|
|
149
|
+
@dialog.list.set_selection(0)
|
|
150
|
+
text_focus
|
|
151
|
+
end
|
|
152
|
+
end
|
|
153
|
+
|
|
154
|
+
def text_focus
|
|
155
|
+
@dialog.text.set_focus
|
|
156
|
+
end
|
|
157
|
+
|
|
120
158
|
def selected
|
|
121
159
|
@model.selected(@dialog.list.get_selection.first, @dialog.list.get_selection_index)
|
|
122
160
|
end
|
|
@@ -20,6 +20,7 @@ module Redcar
|
|
|
20
20
|
end
|
|
21
21
|
@widget = @browser
|
|
22
22
|
@item.control = @widget
|
|
23
|
+
add_listeners
|
|
23
24
|
end
|
|
24
25
|
|
|
25
26
|
# Focuses the Browser tab within the CTabFolder, and gives the keyboard
|
|
@@ -34,6 +35,25 @@ module Redcar
|
|
|
34
35
|
@browser.dispose
|
|
35
36
|
super
|
|
36
37
|
end
|
|
38
|
+
|
|
39
|
+
class LocationListener
|
|
40
|
+
def initialize(html_tab)
|
|
41
|
+
@html_tab = html_tab
|
|
42
|
+
end
|
|
43
|
+
|
|
44
|
+
def changing(event)
|
|
45
|
+
if event.location =~ %r{file:///controller/([^/]*)(/(.*))?}
|
|
46
|
+
event.doit = false
|
|
47
|
+
@html_tab.controller_action($1, $2)
|
|
48
|
+
end
|
|
49
|
+
end
|
|
50
|
+
|
|
51
|
+
def changed(*_); end
|
|
52
|
+
end
|
|
53
|
+
|
|
54
|
+
def add_listeners
|
|
55
|
+
@browser.add_location_listener(LocationListener.new(@model))
|
|
56
|
+
end
|
|
37
57
|
end
|
|
38
58
|
end
|
|
39
59
|
end
|
|
@@ -16,17 +16,20 @@ module Redcar
|
|
|
16
16
|
end
|
|
17
17
|
|
|
18
18
|
def initialize(window, menu_model, keymap, type, options={})
|
|
19
|
+
s = Time.now
|
|
19
20
|
unless Menu.menu_types.include?(type)
|
|
20
21
|
raise "type should be in #{Menu.menu_types.inspect}"
|
|
21
22
|
end
|
|
22
23
|
@window = window
|
|
23
24
|
@keymap = keymap
|
|
24
25
|
@menu_bar = Swt::Widgets::Menu.new(window.shell, type)
|
|
26
|
+
@menu_bar.set_visible(false)
|
|
25
27
|
return unless menu_model
|
|
26
28
|
@handlers = []
|
|
27
29
|
@use_numbers = options[:numbers]
|
|
28
30
|
@number = 1
|
|
29
31
|
add_entries_to_menu(@menu_bar, menu_model)
|
|
32
|
+
#puts "ApplicationSWT::Menu initialize took #{Time.now - s}s"
|
|
30
33
|
end
|
|
31
34
|
|
|
32
35
|
def show
|
|
@@ -47,7 +50,16 @@ module Redcar
|
|
|
47
50
|
|
|
48
51
|
def add_entries_to_menu(menu, menu_model)
|
|
49
52
|
menu_model.each do |entry|
|
|
50
|
-
if entry.is_a?(Redcar::Menu)
|
|
53
|
+
if entry.is_a?(Redcar::Menu::LazyMenu)
|
|
54
|
+
menu_header = Swt::Widgets::MenuItem.new(menu, Swt::SWT::CASCADE)
|
|
55
|
+
menu_header.text = entry.text
|
|
56
|
+
new_menu = Swt::Widgets::Menu.new(@window.shell, Swt::SWT::DROP_DOWN)
|
|
57
|
+
menu_header.menu = new_menu
|
|
58
|
+
menu_header.add_arm_listener do
|
|
59
|
+
new_menu.get_items.each {|i| i.dispose }
|
|
60
|
+
add_entries_to_menu(new_menu, entry)
|
|
61
|
+
end
|
|
62
|
+
elsif entry.is_a?(Redcar::Menu)
|
|
51
63
|
menu_header = Swt::Widgets::MenuItem.new(menu, Swt::SWT::CASCADE)
|
|
52
64
|
menu_header.text = entry.text
|
|
53
65
|
new_menu = Swt::Widgets::Menu.new(@window.shell, Swt::SWT::DROP_DOWN)
|
|
@@ -67,6 +79,18 @@ module Redcar
|
|
|
67
79
|
end
|
|
68
80
|
end
|
|
69
81
|
end
|
|
82
|
+
|
|
83
|
+
class ProcSelectionListener
|
|
84
|
+
def initialize(entry)
|
|
85
|
+
@entry = entry
|
|
86
|
+
end
|
|
87
|
+
|
|
88
|
+
def widget_selected(e)
|
|
89
|
+
@entry.command.call
|
|
90
|
+
end
|
|
91
|
+
|
|
92
|
+
alias :widget_default_selected :widget_selected
|
|
93
|
+
end
|
|
70
94
|
|
|
71
95
|
def connect_proc_to_item(item, entry)
|
|
72
96
|
if use_numbers? and Redcar.platform == :osx
|
|
@@ -75,7 +99,7 @@ module Redcar
|
|
|
75
99
|
else
|
|
76
100
|
item.text = entry.text
|
|
77
101
|
end
|
|
78
|
-
item.
|
|
102
|
+
item.addSelectionListener(ProcSelectionListener.new(entry))
|
|
79
103
|
end
|
|
80
104
|
|
|
81
105
|
class SelectionListener
|
|
@@ -6,17 +6,16 @@ module Redcar
|
|
|
6
6
|
attr_reader :tab_folder
|
|
7
7
|
|
|
8
8
|
class CTabFolder2Listener
|
|
9
|
-
include ListenerHelpers
|
|
10
|
-
|
|
11
9
|
def initialize(controller)
|
|
12
10
|
@controller = controller
|
|
13
11
|
end
|
|
14
12
|
|
|
15
13
|
def close(event)
|
|
16
|
-
|
|
17
|
-
|
|
18
|
-
|
|
19
|
-
|
|
14
|
+
if event.item
|
|
15
|
+
tab = @controller.tab_widget_to_tab_model(event.item)
|
|
16
|
+
unless Redcar.app.events.ignore?(:tab_close, tab)
|
|
17
|
+
event.doit = false
|
|
18
|
+
Redcar.app.events.create(:tab_close, tab)
|
|
20
19
|
end
|
|
21
20
|
end
|
|
22
21
|
end
|
|
@@ -28,17 +27,16 @@ module Redcar
|
|
|
28
27
|
end
|
|
29
28
|
|
|
30
29
|
class SelectionListener
|
|
31
|
-
include ListenerHelpers
|
|
32
|
-
|
|
33
30
|
def initialize(controller)
|
|
34
31
|
@controller = controller
|
|
35
32
|
end
|
|
36
33
|
|
|
37
34
|
def widgetSelected(event)
|
|
38
|
-
|
|
39
|
-
|
|
40
|
-
|
|
41
|
-
|
|
35
|
+
if event.item
|
|
36
|
+
tab = @controller.tab_widget_to_tab_model(event.item)
|
|
37
|
+
unless Redcar.app.events.ignore?(:tab_focus, tab)
|
|
38
|
+
event.doit = false
|
|
39
|
+
Redcar.app.events.create(:tab_focus, tab)
|
|
42
40
|
end
|
|
43
41
|
end
|
|
44
42
|
end
|
|
@@ -5,23 +5,21 @@ module Redcar
|
|
|
5
5
|
attr_reader :shell, :window, :shell_listener
|
|
6
6
|
|
|
7
7
|
class ShellListener
|
|
8
|
-
include ReentryHelpers
|
|
9
|
-
|
|
10
8
|
def initialize(controller)
|
|
11
|
-
@
|
|
9
|
+
@win = controller.window
|
|
12
10
|
end
|
|
13
11
|
|
|
14
12
|
def shell_closed(e)
|
|
15
|
-
|
|
16
|
-
@controller.window.ignore(:closing) do
|
|
13
|
+
unless Redcar.app.events.ignore?(:window_close, @win)
|
|
17
14
|
e.doit = false
|
|
15
|
+
Redcar.app.events.create(:window_close, @win)
|
|
18
16
|
end
|
|
19
17
|
end
|
|
20
18
|
|
|
21
19
|
def shell_activated(e)
|
|
22
|
-
|
|
23
|
-
@controller.window.ignore(:focussing) do
|
|
20
|
+
unless Redcar.app.events.ignore?(:window_focus, @win)
|
|
24
21
|
e.doit = false
|
|
22
|
+
Redcar.app.events.create(:window_focus, @win)
|
|
25
23
|
end
|
|
26
24
|
end
|
|
27
25
|
|
|
@@ -112,14 +110,16 @@ module Redcar
|
|
|
112
110
|
end
|
|
113
111
|
|
|
114
112
|
def refresh_menu
|
|
115
|
-
|
|
113
|
+
old_menu_bar = shell.menu_bar
|
|
114
|
+
@menu_controller = ApplicationSWT::Menu.new(self, Redcar.app.main_menu, Redcar.app.main_keymap, Swt::SWT::BAR)
|
|
116
115
|
shell.menu_bar = @menu_controller.menu_bar
|
|
116
|
+
old_menu_bar.dispose if old_menu_bar
|
|
117
117
|
end
|
|
118
118
|
|
|
119
119
|
def set_icon(path)
|
|
120
|
-
|
|
121
|
-
|
|
122
|
-
|
|
120
|
+
icon = Swt::Graphics::Image.new(ApplicationSWT.display, path)
|
|
121
|
+
shell.image = icon
|
|
122
|
+
end
|
|
123
123
|
|
|
124
124
|
def bring_to_front
|
|
125
125
|
@shell.set_minimized(false) # unminimize, just in case
|
|
@@ -0,0 +1,313 @@
|
|
|
1
|
+
|
|
2
|
+
package com.redcareditor.application_swt;
|
|
3
|
+
|
|
4
|
+
import java.lang.reflect.InvocationTargetException;
|
|
5
|
+
import java.lang.reflect.Method;
|
|
6
|
+
|
|
7
|
+
import org.eclipse.swt.SWT;
|
|
8
|
+
import org.eclipse.swt.internal.C;
|
|
9
|
+
import org.eclipse.swt.internal.Callback;
|
|
10
|
+
import org.eclipse.swt.widgets.Display;
|
|
11
|
+
import org.eclipse.swt.widgets.Listener;
|
|
12
|
+
|
|
13
|
+
/**
|
|
14
|
+
* Provide a hook to connecting the Preferences, About and Quit menu items of the Mac OS X
|
|
15
|
+
* Application menu when using the SWT Cocoa bindings.
|
|
16
|
+
* <p>
|
|
17
|
+
* This code does not require the Cocoa SWT JAR in order to be compiled as it uses reflection to
|
|
18
|
+
* access the Cocoa specific API methods. It does, however, depend on JFace (for IAction), but you
|
|
19
|
+
* could easily modify the code to use SWT Listeners instead in order to use this class in SWT only
|
|
20
|
+
* applications.
|
|
21
|
+
* </p>
|
|
22
|
+
* <p>
|
|
23
|
+
* This code was influenced by the <a
|
|
24
|
+
* href="http://www.simidude.com/blog/2008/macify-a-swt-application-in-a-cross-platform-way/"
|
|
25
|
+
* >CarbonUIEnhancer from Agynami</a> with the implementation being modified from the <a href="http://dev.eclipse.org/viewcvs/index.cgi/org.eclipse.ui.cocoa/src/org/eclipse/ui/internal/cocoa/CocoaUIEnhancer.java"
|
|
26
|
+
* >org.eclipse.ui.internal.cocoa.CocoaUIEnhancer</a>.
|
|
27
|
+
* </p>
|
|
28
|
+
* <p>
|
|
29
|
+
* This class works with both the 32-bit and 64-bit versions of the SWT Cocoa bindings.
|
|
30
|
+
* <p>
|
|
31
|
+
* <p>
|
|
32
|
+
* This class is released under the Eclipse Public License (<a href="http://www.eclipse.org/legal/epl-v10.html">EPL</a>).
|
|
33
|
+
*/
|
|
34
|
+
public class CocoaUIEnhancer {
|
|
35
|
+
|
|
36
|
+
private static final long kAboutMenuItem = 0;
|
|
37
|
+
private static final long kPreferencesMenuItem = 2;
|
|
38
|
+
// private static final long kServicesMenuItem = 4;
|
|
39
|
+
// private static final long kHideApplicationMenuItem = 6;
|
|
40
|
+
private static final long kQuitMenuItem = 10;
|
|
41
|
+
|
|
42
|
+
static long sel_toolbarButtonClicked_;
|
|
43
|
+
static long sel_preferencesMenuItemSelected_;
|
|
44
|
+
static long sel_aboutMenuItemSelected_;
|
|
45
|
+
static Callback proc3Args;
|
|
46
|
+
|
|
47
|
+
final private String appName;
|
|
48
|
+
|
|
49
|
+
/**
|
|
50
|
+
* Class invoked via the Callback object to run the about and preferences actions.
|
|
51
|
+
* <p>
|
|
52
|
+
* If you don't use JFace in your application (SWT only), change the
|
|
53
|
+
* {@link org.eclipse.jface.action.IAction}s to {@link org.eclipse.swt.widgets.Listener}s.
|
|
54
|
+
* </p>
|
|
55
|
+
*/
|
|
56
|
+
private static class MenuHookObject {
|
|
57
|
+
final Listener about;
|
|
58
|
+
final Listener pref;
|
|
59
|
+
|
|
60
|
+
public MenuHookObject( Listener about, Listener pref ) {
|
|
61
|
+
this.about = about;
|
|
62
|
+
this.pref = pref;
|
|
63
|
+
}
|
|
64
|
+
|
|
65
|
+
/**
|
|
66
|
+
* Will be called on 32bit SWT.
|
|
67
|
+
*/
|
|
68
|
+
@SuppressWarnings( "unused" )
|
|
69
|
+
public int actionProc( int id, int sel, int arg0 ) {
|
|
70
|
+
return (int) actionProc( (long) id, (long) sel, (long) arg0 );
|
|
71
|
+
}
|
|
72
|
+
|
|
73
|
+
/**
|
|
74
|
+
* Will be called on 64bit SWT.
|
|
75
|
+
*/
|
|
76
|
+
public long actionProc( long id, long sel, long arg0 ) {
|
|
77
|
+
if ( sel == sel_aboutMenuItemSelected_ ) {
|
|
78
|
+
about.handleEvent(null);
|
|
79
|
+
} else if ( sel == sel_preferencesMenuItemSelected_ ) {
|
|
80
|
+
pref.handleEvent(null);
|
|
81
|
+
} else {
|
|
82
|
+
// Unknown selection!
|
|
83
|
+
}
|
|
84
|
+
// Return value is not used.
|
|
85
|
+
return 99;
|
|
86
|
+
}
|
|
87
|
+
}
|
|
88
|
+
|
|
89
|
+
/**
|
|
90
|
+
* Construct a new CocoaUIEnhancer.
|
|
91
|
+
*
|
|
92
|
+
* @param appName
|
|
93
|
+
* The name of the application. It will be used to customize the About and Quit menu
|
|
94
|
+
* items. If you do not wish to customize the About and Quit menu items, just pass
|
|
95
|
+
* <tt>null</tt> here.
|
|
96
|
+
*/
|
|
97
|
+
public CocoaUIEnhancer( String appName ) {
|
|
98
|
+
this.appName = appName;
|
|
99
|
+
}
|
|
100
|
+
|
|
101
|
+
/**
|
|
102
|
+
* Hook the given Listener to the Mac OS X application Quit menu and the IActions to the About
|
|
103
|
+
* and Preferences menus.
|
|
104
|
+
*
|
|
105
|
+
* @param display
|
|
106
|
+
* The Display to use.
|
|
107
|
+
* @param quitListener
|
|
108
|
+
* The listener to invoke when the Quit menu is invoked.
|
|
109
|
+
* @param aboutListener
|
|
110
|
+
* The listener to invoke when the About menu is invoked.
|
|
111
|
+
* @param preferencesListener
|
|
112
|
+
* The listener to invoke when the Preferences menu is invoked.
|
|
113
|
+
*/
|
|
114
|
+
public void hookApplicationMenu( Display display, Listener quitListener, Listener aboutListener,
|
|
115
|
+
Listener preferencesListener ) {
|
|
116
|
+
// This is our callbackObject whose 'actionProc' method will be called when the About or
|
|
117
|
+
// Preferences menuItem is invoked.
|
|
118
|
+
MenuHookObject target = new MenuHookObject( aboutListener, preferencesListener );
|
|
119
|
+
|
|
120
|
+
try {
|
|
121
|
+
// Initialize the menuItems.
|
|
122
|
+
initialize( target );
|
|
123
|
+
} catch ( Exception e ) {
|
|
124
|
+
throw new IllegalStateException( e );
|
|
125
|
+
}
|
|
126
|
+
|
|
127
|
+
// Connect the quit/exit menu.
|
|
128
|
+
if ( !display.isDisposed() ) {
|
|
129
|
+
display.addListener( SWT.Close, quitListener );
|
|
130
|
+
}
|
|
131
|
+
|
|
132
|
+
// Schedule disposal of callback object
|
|
133
|
+
display.disposeExec( new Runnable() {
|
|
134
|
+
public void run() {
|
|
135
|
+
invoke( proc3Args, "dispose" );
|
|
136
|
+
}
|
|
137
|
+
} );
|
|
138
|
+
}
|
|
139
|
+
|
|
140
|
+
private void initialize( Object callbackObject )
|
|
141
|
+
throws Exception {
|
|
142
|
+
|
|
143
|
+
Class<?> osCls = classForName( "org.eclipse.swt.internal.cocoa.OS" );
|
|
144
|
+
|
|
145
|
+
// Register names in objective-c.
|
|
146
|
+
if ( sel_toolbarButtonClicked_ == 0 ) {
|
|
147
|
+
// sel_toolbarButtonClicked_ = registerName( osCls, "toolbarButtonClicked:" ); //$NON-NLS-1$
|
|
148
|
+
sel_preferencesMenuItemSelected_ = registerName( osCls, "preferencesMenuItemSelected:" ); //$NON-NLS-1$
|
|
149
|
+
sel_aboutMenuItemSelected_ = registerName( osCls, "aboutMenuItemSelected:" ); //$NON-NLS-1$
|
|
150
|
+
}
|
|
151
|
+
|
|
152
|
+
// Create an SWT Callback object that will invoke the actionProc method of our internal
|
|
153
|
+
// callbackObject.
|
|
154
|
+
proc3Args = new Callback( callbackObject, "actionProc", 3 ); //$NON-NLS-1$
|
|
155
|
+
Method getAddress = Callback.class.getMethod( "getAddress", new Class[0] );
|
|
156
|
+
Object object = getAddress.invoke( proc3Args, (Object[]) null );
|
|
157
|
+
long proc3 = convertToLong( object );
|
|
158
|
+
if ( proc3 == 0 ) {
|
|
159
|
+
SWT.error( SWT.ERROR_NO_MORE_CALLBACKS );
|
|
160
|
+
}
|
|
161
|
+
|
|
162
|
+
Class<?> nsmenuCls = classForName( "org.eclipse.swt.internal.cocoa.NSMenu" );
|
|
163
|
+
Class<?> nsmenuitemCls = classForName( "org.eclipse.swt.internal.cocoa.NSMenuItem" );
|
|
164
|
+
Class<?> nsstringCls = classForName( "org.eclipse.swt.internal.cocoa.NSString" );
|
|
165
|
+
Class<?> nsapplicationCls = classForName( "org.eclipse.swt.internal.cocoa.NSApplication" );
|
|
166
|
+
|
|
167
|
+
// Instead of creating a new delegate class in objective-c,
|
|
168
|
+
// just use the current SWTApplicationDelegate. An instance of this
|
|
169
|
+
// is a field of the Cocoa Display object and is already the target
|
|
170
|
+
// for the menuItems. So just get this class and add the new methods
|
|
171
|
+
// to it.
|
|
172
|
+
object = invoke( osCls, "objc_lookUpClass", new Object[] { "SWTApplicationDelegate" } );
|
|
173
|
+
long cls = convertToLong( object );
|
|
174
|
+
|
|
175
|
+
// Add the action callbacks for Preferences and About menu items.
|
|
176
|
+
invoke( osCls, "class_addMethod", new Object[] {
|
|
177
|
+
wrapPointer( cls ),
|
|
178
|
+
wrapPointer( sel_preferencesMenuItemSelected_ ),
|
|
179
|
+
wrapPointer( proc3 ),
|
|
180
|
+
"@:@" } ); //$NON-NLS-1$
|
|
181
|
+
invoke( osCls, "class_addMethod", new Object[] {
|
|
182
|
+
wrapPointer( cls ),
|
|
183
|
+
wrapPointer( sel_aboutMenuItemSelected_ ),
|
|
184
|
+
wrapPointer( proc3 ),
|
|
185
|
+
"@:@" } ); //$NON-NLS-1$
|
|
186
|
+
|
|
187
|
+
// Get the Mac OS X Application menu.
|
|
188
|
+
Object sharedApplication = invoke( nsapplicationCls, "sharedApplication" );
|
|
189
|
+
Object mainMenu = invoke( sharedApplication, "mainMenu" );
|
|
190
|
+
Object mainMenuItem = invoke( nsmenuCls, mainMenu, "itemAtIndex", new Object[] { wrapPointer( 0 ) } );
|
|
191
|
+
Object appMenu = invoke( mainMenuItem, "submenu" );
|
|
192
|
+
|
|
193
|
+
// Create the About <application-name> menu command
|
|
194
|
+
Object aboutMenuItem =
|
|
195
|
+
invoke( nsmenuCls, appMenu, "itemAtIndex", new Object[] { wrapPointer( kAboutMenuItem ) } );
|
|
196
|
+
if ( appName != null ) {
|
|
197
|
+
Object nsStr = invoke( nsstringCls, "stringWith", new Object[] { "About " + appName } );
|
|
198
|
+
invoke( nsmenuitemCls, aboutMenuItem, "setTitle", new Object[] { nsStr } );
|
|
199
|
+
}
|
|
200
|
+
// Rename the quit action.
|
|
201
|
+
if ( appName != null ) {
|
|
202
|
+
Object quitMenuItem =
|
|
203
|
+
invoke( nsmenuCls, appMenu, "itemAtIndex", new Object[] { wrapPointer( kQuitMenuItem ) } );
|
|
204
|
+
Object nsStr = invoke( nsstringCls, "stringWith", new Object[] { "Quit " + appName } );
|
|
205
|
+
invoke( nsmenuitemCls, quitMenuItem, "setTitle", new Object[] { nsStr } );
|
|
206
|
+
}
|
|
207
|
+
|
|
208
|
+
// Enable the Preferences menuItem.
|
|
209
|
+
Object prefMenuItem =
|
|
210
|
+
invoke( nsmenuCls, appMenu, "itemAtIndex", new Object[] { wrapPointer( kPreferencesMenuItem ) } );
|
|
211
|
+
invoke( nsmenuitemCls, prefMenuItem, "setEnabled", new Object[] { true } );
|
|
212
|
+
|
|
213
|
+
// Set the action to execute when the About or Preferences menuItem is invoked.
|
|
214
|
+
//
|
|
215
|
+
// We don't need to set the target here as the current target is the SWTApplicationDelegate
|
|
216
|
+
// and we have registerd the new selectors on it. So just set the new action to invoke the
|
|
217
|
+
// selector.
|
|
218
|
+
invoke( nsmenuitemCls, prefMenuItem, "setAction",
|
|
219
|
+
new Object[] { wrapPointer( sel_preferencesMenuItemSelected_ ) } );
|
|
220
|
+
invoke( nsmenuitemCls, aboutMenuItem, "setAction",
|
|
221
|
+
new Object[] { wrapPointer( sel_aboutMenuItemSelected_ ) } );
|
|
222
|
+
}
|
|
223
|
+
|
|
224
|
+
private long registerName( Class<?> osCls, String name )
|
|
225
|
+
throws IllegalArgumentException, SecurityException, IllegalAccessException,
|
|
226
|
+
InvocationTargetException, NoSuchMethodException {
|
|
227
|
+
Object object = invoke( osCls, "sel_registerName", new Object[] { name } );
|
|
228
|
+
return convertToLong( object );
|
|
229
|
+
}
|
|
230
|
+
|
|
231
|
+
private long convertToLong( Object object ) {
|
|
232
|
+
if ( object instanceof Integer ) {
|
|
233
|
+
Integer i = (Integer) object;
|
|
234
|
+
return i.longValue();
|
|
235
|
+
}
|
|
236
|
+
if ( object instanceof Long ) {
|
|
237
|
+
Long l = (Long) object;
|
|
238
|
+
return l.longValue();
|
|
239
|
+
}
|
|
240
|
+
return 0;
|
|
241
|
+
}
|
|
242
|
+
|
|
243
|
+
private static Object wrapPointer( long value ) {
|
|
244
|
+
Class<?> PTR_CLASS = C.PTR_SIZEOF == 8 ? long.class : int.class;
|
|
245
|
+
if ( PTR_CLASS == long.class ) {
|
|
246
|
+
return new Long( value );
|
|
247
|
+
} else {
|
|
248
|
+
return new Integer( (int) value );
|
|
249
|
+
}
|
|
250
|
+
}
|
|
251
|
+
|
|
252
|
+
private static Object invoke( Class<?> clazz, String methodName, Object[] args ) {
|
|
253
|
+
return invoke( clazz, null, methodName, args );
|
|
254
|
+
}
|
|
255
|
+
|
|
256
|
+
private static Object invoke( Class<?> clazz, Object target, String methodName, Object[] args ) {
|
|
257
|
+
try {
|
|
258
|
+
Class<?>[] signature = new Class<?>[args.length];
|
|
259
|
+
for ( int i = 0; i < args.length; i++ ) {
|
|
260
|
+
Class<?> thisClass = args[i].getClass();
|
|
261
|
+
if ( thisClass == Integer.class )
|
|
262
|
+
signature[i] = int.class;
|
|
263
|
+
else if ( thisClass == Long.class )
|
|
264
|
+
signature[i] = long.class;
|
|
265
|
+
else if ( thisClass == Byte.class )
|
|
266
|
+
signature[i] = byte.class;
|
|
267
|
+
else if ( thisClass == Boolean.class )
|
|
268
|
+
signature[i] = boolean.class;
|
|
269
|
+
else
|
|
270
|
+
signature[i] = thisClass;
|
|
271
|
+
}
|
|
272
|
+
Method method = clazz.getMethod( methodName, signature );
|
|
273
|
+
return method.invoke( target, args );
|
|
274
|
+
} catch ( Exception e ) {
|
|
275
|
+
throw new IllegalStateException( e );
|
|
276
|
+
}
|
|
277
|
+
}
|
|
278
|
+
|
|
279
|
+
private Class<?> classForName( String classname ) {
|
|
280
|
+
try {
|
|
281
|
+
Class<?> cls = Class.forName( classname );
|
|
282
|
+
return cls;
|
|
283
|
+
} catch ( ClassNotFoundException e ) {
|
|
284
|
+
throw new IllegalStateException( e );
|
|
285
|
+
}
|
|
286
|
+
}
|
|
287
|
+
|
|
288
|
+
private Object invoke( Class<?> cls, String methodName ) {
|
|
289
|
+
return invoke( cls, methodName, (Class<?>[]) null, (Object[]) null );
|
|
290
|
+
}
|
|
291
|
+
|
|
292
|
+
private Object invoke( Class<?> cls, String methodName, Class<?>[] paramTypes, Object... arguments ) {
|
|
293
|
+
try {
|
|
294
|
+
Method m = cls.getDeclaredMethod( methodName, paramTypes );
|
|
295
|
+
return m.invoke( null, arguments );
|
|
296
|
+
} catch ( Exception e ) {
|
|
297
|
+
throw new IllegalStateException( e );
|
|
298
|
+
}
|
|
299
|
+
}
|
|
300
|
+
|
|
301
|
+
private Object invoke( Object obj, String methodName ) {
|
|
302
|
+
return invoke( obj, methodName, (Class<?>[]) null, (Object[]) null );
|
|
303
|
+
}
|
|
304
|
+
|
|
305
|
+
private Object invoke( Object obj, String methodName, Class<?>[] paramTypes, Object... arguments ) {
|
|
306
|
+
try {
|
|
307
|
+
Method m = obj.getClass().getDeclaredMethod( methodName, paramTypes );
|
|
308
|
+
return m.invoke( obj, arguments );
|
|
309
|
+
} catch ( Exception e ) {
|
|
310
|
+
throw new IllegalStateException( e );
|
|
311
|
+
}
|
|
312
|
+
}
|
|
313
|
+
}
|