ruber 0.0.1.1

Sign up to get free protection for your applications and to get access to all the features.
Files changed (166) hide show
  1. data/COPYING +339 -0
  2. data/INSTALL +137 -0
  3. data/LICENSE +8 -0
  4. data/bin/ruber +65 -0
  5. data/data/share/apps/ruber/core_components.yaml +31 -0
  6. data/data/share/apps/ruber/ruberui.rc +109 -0
  7. data/data/share/icons/ruber.png +0 -0
  8. data/data/share/pixmaps/ruby.png +0 -0
  9. data/icons/ruber-16.png +0 -0
  10. data/icons/ruber-32.png +0 -0
  11. data/icons/ruber-48.png +0 -0
  12. data/icons/ruber-8.png +0 -0
  13. data/lib/ruber/application/application.rb +288 -0
  14. data/lib/ruber/application/plugin.yaml +11 -0
  15. data/lib/ruber/component_manager.rb +899 -0
  16. data/lib/ruber/config/config.rb +82 -0
  17. data/lib/ruber/config/plugin.yaml +3 -0
  18. data/lib/ruber/document_project.rb +209 -0
  19. data/lib/ruber/documents/document_list.rb +416 -0
  20. data/lib/ruber/documents/plugin.yaml +4 -0
  21. data/lib/ruber/editor/document.rb +506 -0
  22. data/lib/ruber/editor/editor_view.rb +167 -0
  23. data/lib/ruber/editor/ktexteditor_wrapper.rb +202 -0
  24. data/lib/ruber/exception_widgets.rb +245 -0
  25. data/lib/ruber/external_program_plugin.rb +397 -0
  26. data/lib/ruber/filtered_output_widget.rb +342 -0
  27. data/lib/ruber/gui_states_handler.rb +231 -0
  28. data/lib/ruber/kde_config_option_backend.rb +167 -0
  29. data/lib/ruber/kde_sugar.rb +249 -0
  30. data/lib/ruber/main_window/choose_plugins_dlg.rb +353 -0
  31. data/lib/ruber/main_window/main_window.rb +524 -0
  32. data/lib/ruber/main_window/main_window_actions.rb +537 -0
  33. data/lib/ruber/main_window/main_window_internal.rb +239 -0
  34. data/lib/ruber/main_window/open_file_in_project_dlg.rb +212 -0
  35. data/lib/ruber/main_window/output_color_widget.rb +35 -0
  36. data/lib/ruber/main_window/plugin.yaml +58 -0
  37. data/lib/ruber/main_window/save_modified_files_dlg.rb +89 -0
  38. data/lib/ruber/main_window/status_bar.rb +156 -0
  39. data/lib/ruber/main_window/ui/choose_plugins_widget.rb +90 -0
  40. data/lib/ruber/main_window/ui/choose_plugins_widget.ui +77 -0
  41. data/lib/ruber/main_window/ui/main_window_settings_widget.rb +108 -0
  42. data/lib/ruber/main_window/ui/main_window_settings_widget.ui +89 -0
  43. data/lib/ruber/main_window/ui/new_project_widget.rb +119 -0
  44. data/lib/ruber/main_window/ui/new_project_widget.ui +178 -0
  45. data/lib/ruber/main_window/ui/open_file_in_project_dlg.rb +109 -0
  46. data/lib/ruber/main_window/ui/open_file_in_project_dlg.ui +168 -0
  47. data/lib/ruber/main_window/ui/output_color_widget.rb +241 -0
  48. data/lib/ruber/main_window/ui/output_color_widget.ui +204 -0
  49. data/lib/ruber/main_window/workspace.rb +442 -0
  50. data/lib/ruber/output_widget.rb +1093 -0
  51. data/lib/ruber/plugin.rb +264 -0
  52. data/lib/ruber/plugin_like.rb +589 -0
  53. data/lib/ruber/plugin_specification.rb +106 -0
  54. data/lib/ruber/plugin_specification_reader.rb +451 -0
  55. data/lib/ruber/project.rb +493 -0
  56. data/lib/ruber/project_backend.rb +105 -0
  57. data/lib/ruber/projects/plugin.yaml +11 -0
  58. data/lib/ruber/projects/project_files_list.rb +314 -0
  59. data/lib/ruber/projects/project_files_widget.rb +301 -0
  60. data/lib/ruber/projects/project_list.rb +314 -0
  61. data/lib/ruber/projects/ui/project_files_rule_chooser_widget.rb +74 -0
  62. data/lib/ruber/projects/ui/project_files_rule_chooser_widget.ui +61 -0
  63. data/lib/ruber/projects/ui/project_files_widget.rb +117 -0
  64. data/lib/ruber/projects/ui/project_files_widget.ui +123 -0
  65. data/lib/ruber/qt_sugar.rb +673 -0
  66. data/lib/ruber/settings_container.rb +515 -0
  67. data/lib/ruber/settings_dialog.rb +244 -0
  68. data/lib/ruber/settings_dialog_manager.rb +503 -0
  69. data/lib/ruber/utils.rb +414 -0
  70. data/lib/ruber/yaml_option_backend.rb +159 -0
  71. data/outsider_files +15 -0
  72. data/plugins/autosave/autosave.rb +404 -0
  73. data/plugins/autosave/plugin.yaml +16 -0
  74. data/plugins/autosave/ui/autosave_config_widget.rb +83 -0
  75. data/plugins/autosave/ui/autosave_config_widget.ui +68 -0
  76. data/plugins/command/command.png +0 -0
  77. data/plugins/command/command.rb +74 -0
  78. data/plugins/command/plugin.yaml +11 -0
  79. data/plugins/find_in_files/find_in_files.rb +337 -0
  80. data/plugins/find_in_files/find_in_files_dlg.rb +411 -0
  81. data/plugins/find_in_files/find_in_files_ui.rc +11 -0
  82. data/plugins/find_in_files/find_in_files_widgets.rb +485 -0
  83. data/plugins/find_in_files/plugin.yaml +23 -0
  84. data/plugins/find_in_files/ui/config_widget.rb +58 -0
  85. data/plugins/find_in_files/ui/config_widget.ui +41 -0
  86. data/plugins/find_in_files/ui/find_in_files_widget.rb +260 -0
  87. data/plugins/find_in_files/ui/find_in_files_widget.ui +324 -0
  88. data/plugins/project_browser/plugin.yaml +10 -0
  89. data/plugins/project_browser/project_browser.rb +245 -0
  90. data/plugins/rake/plugin.yaml +39 -0
  91. data/plugins/rake/rake.png +0 -0
  92. data/plugins/rake/rake.rb +567 -0
  93. data/plugins/rake/rake_extension.rb +153 -0
  94. data/plugins/rake/rake_widgets.rb +615 -0
  95. data/plugins/rake/rakeui.rc +27 -0
  96. data/plugins/rake/ui/add_quick_task_widget.rb +71 -0
  97. data/plugins/rake/ui/add_quick_task_widget.ui +59 -0
  98. data/plugins/rake/ui/choose_task_widget.rb +77 -0
  99. data/plugins/rake/ui/choose_task_widget.ui +72 -0
  100. data/plugins/rake/ui/config_widget.rb +127 -0
  101. data/plugins/rake/ui/config_widget.ui +123 -0
  102. data/plugins/rake/ui/project_widget.rb +217 -0
  103. data/plugins/rake/ui/project_widget.ui +246 -0
  104. data/plugins/rspec/plugin.yaml +30 -0
  105. data/plugins/rspec/rspec.png +0 -0
  106. data/plugins/rspec/rspec.rb +945 -0
  107. data/plugins/rspec/rspec.svg +90 -0
  108. data/plugins/rspec/rspecui.rc +20 -0
  109. data/plugins/rspec/ruber_rspec_formatter.rb +312 -0
  110. data/plugins/rspec/ui/rspec_project_widget.rb +170 -0
  111. data/plugins/rspec/ui/rspec_project_widget.ui +193 -0
  112. data/plugins/ruby_development/plugin.yaml +27 -0
  113. data/plugins/ruby_development/ruby_development.png +0 -0
  114. data/plugins/ruby_development/ruby_development.rb +453 -0
  115. data/plugins/ruby_development/ruby_developmentui.rc +19 -0
  116. data/plugins/ruby_development/ui/project_widget.rb +112 -0
  117. data/plugins/ruby_development/ui/project_widget.ui +108 -0
  118. data/plugins/ruby_runner/config_widget.rb +116 -0
  119. data/plugins/ruby_runner/plugin.yaml +26 -0
  120. data/plugins/ruby_runner/project_widget.rb +62 -0
  121. data/plugins/ruby_runner/ruby.png +0 -0
  122. data/plugins/ruby_runner/ruby_interpretersui.rc +26 -0
  123. data/plugins/ruby_runner/ruby_runner.rb +411 -0
  124. data/plugins/ruby_runner/ui/config_widget.rb +92 -0
  125. data/plugins/ruby_runner/ui/config_widget.ui +91 -0
  126. data/plugins/ruby_runner/ui/project_widget.rb +60 -0
  127. data/plugins/ruby_runner/ui/project_widget.ui +48 -0
  128. data/plugins/ruby_runner/ui/ruby_runnner_plugin_option_widget.rb +59 -0
  129. data/plugins/ruby_runner/ui/ruby_runnner_plugin_option_widget.ui +44 -0
  130. data/plugins/state/plugin.yaml +28 -0
  131. data/plugins/state/state.rb +520 -0
  132. data/plugins/state/ui/config_widget.rb +92 -0
  133. data/plugins/state/ui/config_widget.ui +89 -0
  134. data/plugins/syntax_checker/plugin.yaml +18 -0
  135. data/plugins/syntax_checker/syntax_checker.rb +662 -0
  136. data/ruber.desktop +10 -0
  137. data/spec/annotation_model_spec.rb +174 -0
  138. data/spec/common.rb +119 -0
  139. data/spec/component_manager_spec.rb +1259 -0
  140. data/spec/document_list_spec.rb +626 -0
  141. data/spec/document_project_spec.rb +373 -0
  142. data/spec/document_spec.rb +779 -0
  143. data/spec/editor_view_spec.rb +167 -0
  144. data/spec/external_program_plugin_spec.rb +676 -0
  145. data/spec/filtered_output_widget_spec.rb +642 -0
  146. data/spec/gui_states_handler_spec.rb +304 -0
  147. data/spec/kde_config_option_backend_spec.rb +214 -0
  148. data/spec/kde_sugar_spec.rb +101 -0
  149. data/spec/ktexteditor_wrapper_spec.rb +305 -0
  150. data/spec/output_widget_spec.rb +1703 -0
  151. data/spec/plugin_spec.rb +1393 -0
  152. data/spec/plugin_specification_reader_spec.rb +1765 -0
  153. data/spec/plugin_specification_spec.rb +401 -0
  154. data/spec/project_backend_spec.rb +172 -0
  155. data/spec/project_files_list_spec.rb +401 -0
  156. data/spec/project_list_spec.rb +511 -0
  157. data/spec/project_spec.rb +990 -0
  158. data/spec/qt_sugar_spec.rb +328 -0
  159. data/spec/settings_container_spec.rb +617 -0
  160. data/spec/settings_dialog_manager_spec.rb +773 -0
  161. data/spec/settings_dialog_spec.rb +419 -0
  162. data/spec/state_spec.rb +991 -0
  163. data/spec/utils_spec.rb +406 -0
  164. data/spec/workspace_spec.rb +869 -0
  165. data/spec/yaml_option_backend_spec.rb +246 -0
  166. metadata +284 -0
@@ -0,0 +1,204 @@
1
+ <?xml version="1.0" encoding="UTF-8"?>
2
+ <ui version="4.0">
3
+ <class>OutputColorWidget</class>
4
+ <widget class="QWidget" name="OutputColorWidget">
5
+ <property name="geometry">
6
+ <rect>
7
+ <x>0</x>
8
+ <y>0</y>
9
+ <width>392</width>
10
+ <height>189</height>
11
+ </rect>
12
+ </property>
13
+ <property name="windowTitle">
14
+ <string>Form</string>
15
+ </property>
16
+ <layout class="QVBoxLayout" name="verticalLayout">
17
+ <item>
18
+ <layout class="QGridLayout" name="gridLayout">
19
+ <item row="0" column="1">
20
+ <widget class="QLabel" name="label_9">
21
+ <property name="text">
22
+ <string>Default</string>
23
+ </property>
24
+ <property name="alignment">
25
+ <set>Qt::AlignCenter</set>
26
+ </property>
27
+ </widget>
28
+ </item>
29
+ <item row="0" column="2">
30
+ <widget class="QLabel" name="label_8">
31
+ <property name="text">
32
+ <string>Good</string>
33
+ </property>
34
+ <property name="alignment">
35
+ <set>Qt::AlignCenter</set>
36
+ </property>
37
+ </widget>
38
+ </item>
39
+ <item row="1" column="0">
40
+ <widget class="QLabel" name="label_7">
41
+ <property name="text">
42
+ <string>Message</string>
43
+ </property>
44
+ </widget>
45
+ </item>
46
+ <item row="1" column="1">
47
+ <widget class="KColorButton" name="_output_colors__message"/>
48
+ </item>
49
+ <item row="1" column="2">
50
+ <widget class="KColorButton" name="_output_colors__message_good"/>
51
+ </item>
52
+ <item row="1" column="3">
53
+ <widget class="KColorButton" name="_output_colors__message_bad"/>
54
+ </item>
55
+ <item row="0" column="3">
56
+ <widget class="QLabel" name="label_10">
57
+ <property name="text">
58
+ <string>Bad</string>
59
+ </property>
60
+ <property name="alignment">
61
+ <set>Qt::AlignCenter</set>
62
+ </property>
63
+ </widget>
64
+ </item>
65
+ </layout>
66
+ </item>
67
+ <item>
68
+ <widget class="Line" name="line">
69
+ <property name="orientation">
70
+ <enum>Qt::Horizontal</enum>
71
+ </property>
72
+ </widget>
73
+ </item>
74
+ <item>
75
+ <layout class="QGridLayout" name="gridLayout_2">
76
+ <item row="0" column="1">
77
+ <widget class="QLabel" name="label">
78
+ <property name="text">
79
+ <string>Default</string>
80
+ </property>
81
+ <property name="alignment">
82
+ <set>Qt::AlignCenter</set>
83
+ </property>
84
+ </widget>
85
+ </item>
86
+ <item row="0" column="2">
87
+ <widget class="QLabel" name="label_2">
88
+ <property name="text">
89
+ <string>Variant 1</string>
90
+ </property>
91
+ <property name="alignment">
92
+ <set>Qt::AlignCenter</set>
93
+ </property>
94
+ </widget>
95
+ </item>
96
+ <item row="0" column="3">
97
+ <widget class="QLabel" name="label_3">
98
+ <property name="text">
99
+ <string>Variant 2</string>
100
+ </property>
101
+ <property name="alignment">
102
+ <set>Qt::AlignCenter</set>
103
+ </property>
104
+ </widget>
105
+ </item>
106
+ <item row="1" column="0">
107
+ <widget class="QLabel" name="label_5">
108
+ <property name="text">
109
+ <string>Output</string>
110
+ </property>
111
+ </widget>
112
+ </item>
113
+ <item row="1" column="1">
114
+ <widget class="KColorButton" name="_output_colors__output"/>
115
+ </item>
116
+ <item row="1" column="2">
117
+ <widget class="KColorButton" name="_output_colors__output1"/>
118
+ </item>
119
+ <item row="1" column="3">
120
+ <widget class="KColorButton" name="_output_colors__output2"/>
121
+ </item>
122
+ <item row="2" column="0">
123
+ <widget class="QLabel" name="label_6">
124
+ <property name="text">
125
+ <string>Error</string>
126
+ </property>
127
+ </widget>
128
+ </item>
129
+ <item row="2" column="1">
130
+ <widget class="KColorButton" name="_output_colors__error"/>
131
+ </item>
132
+ <item row="2" column="2">
133
+ <widget class="KColorButton" name="_output_colors__error1"/>
134
+ </item>
135
+ <item row="2" column="3">
136
+ <widget class="KColorButton" name="_output_colors__error2"/>
137
+ </item>
138
+ <item row="3" column="0">
139
+ <widget class="QLabel" name="label_4">
140
+ <property name="text">
141
+ <string>Warning</string>
142
+ </property>
143
+ </widget>
144
+ </item>
145
+ <item row="3" column="1">
146
+ <widget class="KColorButton" name="_output_colors__warning"/>
147
+ </item>
148
+ <item row="3" column="2">
149
+ <widget class="KColorButton" name="_output_colors__warning1"/>
150
+ </item>
151
+ <item row="3" column="3">
152
+ <widget class="KColorButton" name="_output_colors__warning2"/>
153
+ </item>
154
+ </layout>
155
+ </item>
156
+ <item>
157
+ <spacer name="verticalSpacer">
158
+ <property name="orientation">
159
+ <enum>Qt::Vertical</enum>
160
+ </property>
161
+ <property name="sizeHint" stdset="0">
162
+ <size>
163
+ <width>20</width>
164
+ <height>40</height>
165
+ </size>
166
+ </property>
167
+ </spacer>
168
+ </item>
169
+ </layout>
170
+ <zorder>label</zorder>
171
+ <zorder>label_2</zorder>
172
+ <zorder>label_3</zorder>
173
+ <zorder>label_5</zorder>
174
+ <zorder>_output_colors__output</zorder>
175
+ <zorder>_output_colors__output1</zorder>
176
+ <zorder>_output_colors__output2</zorder>
177
+ <zorder>label_6</zorder>
178
+ <zorder>_output_colors__error</zorder>
179
+ <zorder>_output_colors__error1</zorder>
180
+ <zorder>_output_colors__error2</zorder>
181
+ <zorder>_output_colors__warning2</zorder>
182
+ <zorder>label_4</zorder>
183
+ <zorder>_output_colors__warning1</zorder>
184
+ <zorder>_output_colors__warning</zorder>
185
+ <zorder>line</zorder>
186
+ <zorder>_output_colors__message</zorder>
187
+ <zorder>_output_colors__message_bad</zorder>
188
+ <zorder>label_7</zorder>
189
+ <zorder>label_8</zorder>
190
+ <zorder>label_9</zorder>
191
+ <zorder>label_10</zorder>
192
+ <zorder>_output_colors__message_good</zorder>
193
+ <zorder>label_10</zorder>
194
+ </widget>
195
+ <customwidgets>
196
+ <customwidget>
197
+ <class>KColorButton</class>
198
+ <extends>QPushButton</extends>
199
+ <header>kcolorbutton.h</header>
200
+ </customwidget>
201
+ </customwidgets>
202
+ <resources/>
203
+ <connections/>
204
+ </ui>
@@ -0,0 +1,442 @@
1
+ =begin
2
+ Copyright (C) 2010 by Stefano Crocco
3
+ stefano.crocco@alice.it
4
+
5
+ This program is free software; you can redistribute it andor modify
6
+ it under the terms of the GNU General Public License as published by
7
+ the Free Software Foundation; either version 2 of the License, or
8
+ (at your option) any later version.
9
+
10
+ This program is distributed in the hope that it will be useful,
11
+ but WITHOUT ANY WARRANTY; without even the implied warranty of
12
+ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13
+ GNU General Public License for more details.
14
+
15
+ You should have received a copy of the GNU General Public License
16
+ along with this program; if not, write to the
17
+ Free Software Foundation, Inc.,
18
+ 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
19
+ =end
20
+
21
+ require 'facets/enumerable/sum'
22
+
23
+ module Ruber
24
+
25
+ =begin rdoc
26
+ Widget representing the main area of Ruber's main window, containing the tool
27
+ widgets, together with their tab bars, and the tab widget containing the views.
28
+
29
+ ===Tool Widgets
30
+ The workspace provides three <i>tool widgets containers</i>, on all sides of the
31
+ editor views except above them. The container on each side is indipendent from the
32
+ others.
33
+
34
+ A tool widget can be
35
+ * +raised+ or +lowered+: a raised tool widget is the only one which can bee seen
36
+ and interact with the user. There can be only one raised tool widget for side.
37
+ All other tool widgets are said to be lowered.
38
+ * +visible+ or +hidden+: while a lowered tool widget is can never be seen, the
39
+ opposite is not necessarily true. A raised tool widget will be visible only if
40
+ its container is visible, otherwise it will be hidden, too
41
+ * +active+ or +inactive+: a tool widget is active only if it has focus, otherwise
42
+ it's inactive. Obviously, only visible tool widgets can be active and there can
43
+ be at most one active tool widget in all the workspace.
44
+ =end
45
+ class Workspace < Qt::Widget
46
+
47
+ =begin rdoc
48
+ Class used by +ToolManager+ to display the currently selected widget. It's a
49
+ <tt>Qt::WidgetStack</tt> which handles the +keyPressEvent+ when the key is either
50
+ Esc or Shift+Esc. In the former case, the tool widget is hidden; in the latter
51
+ the focus is given back to the editor.
52
+
53
+ ===TODO
54
+ See whether this can somehow managed using shortcuts
55
+ =end
56
+ class StackedWidget < Qt::StackedWidget
57
+
58
+ protected
59
+
60
+ =begin rdoc
61
+ Handles the key press event. First, it calls the method of the parent class,
62
+ then if the event hasn't been accepted, activates the editor if the key was
63
+ <tt>Shift + Esc</tt> or hides the current tool (thus activating the editor) if
64
+ the key was +Esc+ with no modifiers.
65
+ =====Arguments
66
+ _e_:: the event (<tt>Qt::KeyEvent</tt>)
67
+ =end
68
+ def keyPressEvent e
69
+ super e
70
+ return if e.accepted?
71
+ if e.key == Qt::Key_Q and e.modifiers == Qt::ShiftModifier.to_i
72
+ Ruber[:main_window].activate_editor
73
+ elsif e.key == Qt::Key_Q and e.modifiers == Qt::NoModifier.to_i
74
+ Ruber[:main_window].hide_tool current_widget
75
+ else e.ignore
76
+ end
77
+ end
78
+
79
+ end
80
+
81
+ =begin rdoc
82
+ Internal class used to store information about the position of a tool widget
83
+ =end
84
+ ToolData = Struct.new(:side, :id)
85
+
86
+ ##
87
+ # :method: tool_raised(tool)
88
+ #
89
+ # <b>Signal</b>
90
+ #
91
+ # <b>Signature:</b> <tt>tool_raised(QWidget*)</tt>
92
+ #
93
+ # Signal emitted when a tool widget is raised. _tool_ is the widget which
94
+ # has been raised
95
+ signals 'tool_raised(QWidget*)'
96
+
97
+ ##
98
+ # :method: removing_tool(tool)
99
+ #
100
+ # *Signal*
101
+ #
102
+ # <b>Signature:</b> <tt>removing_tool(QWidget*)</tt>
103
+ #
104
+ # Signal emitted just before the tool widget _tool_ is removed
105
+ signals 'removing_tool(QWidget*)'
106
+
107
+ ##
108
+ # :method: tool_shown
109
+ # <b>Signal: <tt>tool_shown(QWidget*)</tt></b>
110
+ #
111
+ # Signal emitted when a tool widget is shown programmaticaly.
112
+ signals 'tool_shown(QWidget*)'
113
+
114
+ slots 'toggle_tool(int)'
115
+
116
+ =begin rdoc
117
+ The tab widget containing the editor views
118
+ =end
119
+ # attr_reader :views
120
+
121
+ =begin rdoc
122
+ Creates a new Workspace. _parent_ is the workspace's parent widget
123
+ =end
124
+ def initialize parent = nil
125
+ super
126
+ @button_bars = {}
127
+ @splitters = {}
128
+ @stacks = {}
129
+ @widgets = {}
130
+ @next_id = 0
131
+ @tool_sizes = {}
132
+ @sizes = Ruber[:config][:workspace, :tools_sizes].dup
133
+ create_skeleton
134
+ end
135
+
136
+ =begin rdoc
137
+ Adds a tool widget to the workspace. _side_ is the side where the widget should
138
+ be put. It can be <tt>:left</tt>, <tt>:right</tt> or <tt>:bottom</tt>. _widget_
139
+ is the widget to add; _icon_ is the <tt>Qt::Pixmap</tt> containing the icon to
140
+ put on the tab bar and _caption_ is the text to display on the same caption.
141
+
142
+ If _widget_ had already been added as a tool widget (either on the same side or
143
+ another side, then ArgumentError is raised).
144
+ =end
145
+ def add_tool_widget side, widget, icon, caption
146
+ if @stacks.values.include? widget.parent
147
+ Kernel.raise ArgumentError, "This widget has already been added as tool widget"
148
+ end
149
+ bar = @button_bars[side]
150
+ id = @next_id
151
+ bar.append_tab icon, id, caption
152
+ @widgets[widget] = ToolData.new side, id
153
+ @stacks[side].add_widget widget
154
+ connect bar.tab(id), SIGNAL('clicked(int)'), self, SLOT('toggle_tool(int)')
155
+ @next_id += 1
156
+ end
157
+
158
+ =begin rdoc
159
+ Removes a tool widget. _arg_ can be either the widget itself or its <tt>object_name</tt>,
160
+ either as a string or as a symbol. If the widget isn't a tool widget, nothing
161
+ happens.
162
+ =end
163
+ def remove_tool_widget arg
164
+ widget, data = if arg.is_a? String or arg.is_a? Symbol
165
+ @widgets.find{|k, v| k.object_name == arg.to_s}
166
+ else [arg, @widgets[arg]]
167
+ end
168
+ return unless widget and data
169
+ emit removing_tool(widget)
170
+ stack = @stacks[data.side]
171
+ raised = stack.current_widget.equal?(widget)
172
+ stack.remove_widget widget
173
+ if stack.empty? then stack.hide
174
+ else raise_tool stack.current_widget
175
+ end
176
+ @button_bars[data.side].remove_tab data.id
177
+ end
178
+
179
+ =begin rdoc
180
+ Raises the tool widget _tool_, which can be either the tool widget itself or its
181
+ <tt>object_name</tt>, either as a string or symbol. If _tool_ is not a tool widget
182
+ (or if no tool widget with that <tt>object_name</tt> exists), nothing is done. If
183
+ _tool_ is a string or symbol and more than one tool widget exist with that <tt>object_name</tt>,
184
+ which one is raised is undefined.
185
+
186
+ <b>Note:</b> this method doesn't make the container of _tool_ visible if it's hidden
187
+ =end
188
+ def raise_tool tool
189
+ tool, data = tool_and_data tool
190
+ return unless tool
191
+ bar = @button_bars[data.side]
192
+ stack = @stacks[data.side]
193
+ old = stack.current_widget
194
+ if old and old.visible?
195
+ store_tool_size old
196
+ old_data = @widgets[old]
197
+ bar.set_tab old_data.id, false
198
+ end
199
+ bar.set_tab data.id, true
200
+ if old != tool
201
+ stack.current_widget = tool
202
+ emit tool_raised(tool)
203
+ emit tool_shown(tool) if stack.visible?
204
+ end
205
+ resize_tool tool
206
+ end
207
+
208
+ =begin rdoc
209
+ Shows the tool widget _tool_. This means that _tool_ will become the current widget
210
+ in its stack and that the stack will become visible (if it's not already visible).
211
+ _tool_ won't receive focus, unless the previously current widget of its stack had
212
+ focus.
213
+
214
+ _tool_ can be either the tool widget itself or its <tt>object_name</tt>, either as
215
+ string or as symbol. In the latter cases, it there's more than one tool widget with
216
+ the same <tt>object_name</tt>, it's undefined which one will be shown.
217
+
218
+ If _tool_ isn't a tool widget, nothing happens.
219
+ =end
220
+ def show_tool tool
221
+ tool, data = tool_and_data tool
222
+ return unless tool
223
+ data = @widgets[tool]
224
+ stack = @stacks[data.side]
225
+ visible = tool.visible?
226
+ give_focus = stack.find_children(Qt::Widget).any?{|w| w.has_focus}
227
+ raise_tool tool
228
+ stack.show unless stack.visible?
229
+ emit tool_shown(tool) unless visible
230
+ tool.set_focus if give_focus
231
+ end
232
+
233
+ =begin rdoc
234
+ Gives focus to the tool widget _tool_ (raising and showing it if necessary). _tool_
235
+ can be either the tool widget itself or its <tt>object_name</tt> (as either a string
236
+ or symbol). If _tool_ doesn't represent a valid tool widget, nothing happens. If
237
+ _tool_ is a string or symbol and more than one tool widget with the same name exists,
238
+ which one will obtain focus is undefined.
239
+ =end
240
+ def activate_tool tool
241
+ tool, data = tool_and_data tool
242
+ return unless tool
243
+ show_tool tool unless tool.visible?
244
+ tool.set_focus
245
+ end
246
+
247
+ =begin rdoc
248
+ <b>Slot</b>
249
+
250
+ Activates the tool _tool_ if it's not visibile and hides its stack if instead it's
251
+ visible.
252
+
253
+ _tool_ can be either the tool widget itself or its <tt>object_name</tt> (as either a string
254
+ or symbol) or the id of the tab associated with the tool widget. If _tool_ doesn't
255
+ represent a valid tool widget, nothing happens. If
256
+ _tool_ is a string or symbol and more than one tool widget with the same name exists,
257
+ which one will obtain focus is undefined.
258
+
259
+ <b>Note:</b> the use of the id of the tab as argument is only for internal use.
260
+ =end
261
+ def toggle_tool tool
262
+ tool, data = tool_and_data tool
263
+ return unless tool
264
+ if !tool.visible? then activate_tool tool
265
+ else hide_tool tool
266
+ end
267
+ end
268
+
269
+ =begin rdoc
270
+ Hides the stack containing the tool widget _tool_, giving focus to the active editor,
271
+ if _tool_ is raised (that is, if it is the current widget of its stack).
272
+
273
+ _tool_ can be either the tool widget itself or its <tt>object_name</tt> (as
274
+ either a string or symbol). If _tool_ doesn't represent a valid tool widget,
275
+ nothing happens. If _tool_ is a string or symbol and more than one tool widget
276
+ with the same name exists, which one will be used is undefined.
277
+ =end
278
+ def hide_tool tool
279
+ tool, data = tool_and_data tool
280
+ return unless tool
281
+ store_tool_size tool if tool.visible?
282
+ stack = tool.parent
283
+ if stack.current_widget == tool
284
+ @button_bars[data.side].set_tab data.id, false
285
+ if stack.visible?
286
+ stack.hide
287
+ Ruber[:main_window].focus_on_editor
288
+ end
289
+ end
290
+ end
291
+
292
+
293
+ =begin rdoc
294
+ Stores the tool widgets size in the configuration manager. It reads the sizes of
295
+ the splitters for the tool widgets which are visible and uses the values stored
296
+ previously for the others.
297
+ =end
298
+ def store_sizes
299
+ @stacks.each_value do |s|
300
+ w = s.current_widget
301
+ next unless w
302
+ store_tool_size w if w.visible?
303
+ end
304
+ Ruber[:config][:workspace, :tools_sizes] = @sizes
305
+ end
306
+
307
+ =begin rdoc
308
+ Returns a hash having all the tool widgets as keys and the side each of them is
309
+ (<tt>:left</tt>, <tt>:right</tt>, <tt>:bottom</tt>) as values.
310
+ =end
311
+ def tool_widgets
312
+ res = {}
313
+ @widgets.each_pair{|w, data| res[w] = data.side}
314
+ res
315
+ end
316
+
317
+ def current_widget side
318
+ @stacks[side].current_widget
319
+ end
320
+
321
+ =begin
322
+ Returns the active tool widget, or *nil* if there's no active tool widget.
323
+ =end
324
+ def active_tool
325
+ fw = KDE::Application.focus_widget
326
+ if @widgets.include? fw then fw
327
+ else @widgets.keys.find{|w| w.find_children(Qt::Widget).include? fw}
328
+ end
329
+ end
330
+
331
+ private
332
+
333
+ =begin rdoc
334
+ Helper method which creates the structure of the workspace (layout, button bars,
335
+ splitters and tab view)
336
+ =end
337
+ def create_skeleton
338
+ self.layout = Qt::GridLayout.new self
339
+ layout.set_contents_margins 0,0,0,0
340
+ layout.vertical_spacing = 0
341
+ %w[left right bottom].each do |side|
342
+ @button_bars[side.to_sym] =
343
+ KDE::MultiTabBar.new(KDE::MultiTabBar.const_get(side.capitalize), self)
344
+ end
345
+ layout.add_widget @button_bars[:left], 0, 0
346
+ layout.add_widget @button_bars[:right], 0, 2
347
+ layout.add_widget @button_bars[:bottom], 1, 0, 1, -1
348
+ v = Qt::Splitter.new Qt::Vertical, self
349
+ h = Qt::Splitter.new Qt::Horizontal, v
350
+ layout.add_widget v, 0,1
351
+ @splitters[:vertical] = v
352
+ @splitters[:horizontal] = h
353
+ [:left, :right, :bottom].each do |s|
354
+ stack = StackedWidget.new{|w| w.hide}
355
+ @stacks[s] = stack
356
+ end
357
+ v.add_widget h
358
+ v.add_widget @stacks[:bottom]
359
+ h.add_widget @stacks[:left]
360
+ @views = KDE::TabWidget.new(h){self.document_mode = true}
361
+ h.add_widget @views
362
+ h.add_widget @stacks[:right]
363
+ end
364
+
365
+ =begin rdoc
366
+ Resizes the splitter where the tool widget _tool_ is so that the size of _tool_
367
+ matches that of the last time it was used. The space needed to do so is taken
368
+ from the editor.
369
+
370
+ If no size is recorded for _tool_, nothing is done.
371
+ =end
372
+ def resize_tool tool
373
+ data = @widgets[tool]
374
+ side = data.side
375
+ caption = @button_bars[side].tab(data.id).text
376
+ size = @sizes[caption] #|| 150
377
+ return unless size
378
+ case side
379
+ when :bottom
380
+ splitter = @splitters[:vertical]
381
+ total = splitter.sizes.sum
382
+ new_sizes = [[total - size, 0].max, size]
383
+ splitter.sizes = new_sizes
384
+ when :left
385
+ splitter = @splitters[:horizontal]
386
+ old_sizes = splitter.sizes
387
+ total = old_sizes[0..1].sum
388
+ new_sizes = [size, [total - size, 0].max, old_sizes[-1]]
389
+ splitter.sizes = new_sizes
390
+ when :right
391
+ splitter = @splitters[:horizontal]
392
+ old_sizes = splitter.sizes
393
+ total = old_sizes[1..-1].sum
394
+ new_sizes = [old_sizes[0], [total - size, 0].max, size]
395
+ splitter.sizes = new_sizes
396
+ end
397
+ end
398
+
399
+ =begin rdoc
400
+ Stores the size of the splitter slot where the tool widget _tool_ is in the
401
+ <tt>@sizes</tt> instance variable.
402
+ =end
403
+ def store_tool_size tool
404
+ data = @widgets[tool]
405
+ side = data.side
406
+ caption = @button_bars[side].tab(data.id).text
407
+ splitter, pos = case side
408
+ when :bottom then [@splitters[:vertical], 1]
409
+ when :left then [@splitters[:horizontal], 0]
410
+ when :right then [@splitters[:horizontal], 2]
411
+ end
412
+ @sizes[caption] = splitter.sizes[pos]
413
+ end
414
+
415
+ =begin rdoc
416
+ Returns an array containing the tool widget corresponding to _arg_ and its data
417
+ (that is, the entry in the <tt>@widgets</tt> hash corresponding to the tool widget).
418
+ _arg_ can be:
419
+ * the tool widget itself
420
+ * a string or symbol containing the <tt>object_name</tt> of the widget
421
+ * an +Integer+ containing the id of the tab associated with the tool widget.
422
+ If a suitable tool widget can't be found (or if _arg_ is of another class), *nil*
423
+ is returned.
424
+ =end
425
+ def tool_and_data arg
426
+ case arg
427
+ when String, Symbol
428
+ name = arg.to_s
429
+ @widgets.find{|w, data| w.object_name == name}
430
+ when Integer
431
+ @widgets.find{|w, data| data.id == arg}
432
+ else
433
+ if arg.is_a? Qt::Widget
434
+ data = @widgets[arg]
435
+ [arg, data] if data
436
+ end
437
+ end
438
+ end
439
+
440
+ end
441
+
442
+ end