wxruby3-shapes 0.9.0.pre.beta.3
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.
- checksums.yaml +7 -0
- data/.yardopts +12 -0
- data/CREDITS.md +18 -0
- data/INSTALL.md +39 -0
- data/LICENSE +21 -0
- data/README.md +118 -0
- data/assets/screenshot.png +0 -0
- data/bin/wx-shapes +9 -0
- data/lib/wx/shapes/arrow_base.rb +86 -0
- data/lib/wx/shapes/arrows/circle_arrow.rb +39 -0
- data/lib/wx/shapes/arrows/diamond_arrow.rb +33 -0
- data/lib/wx/shapes/arrows/open_arrow.rb +56 -0
- data/lib/wx/shapes/arrows/solid_arrow.rb +69 -0
- data/lib/wx/shapes/art/shape_canvas/page.xpm +73 -0
- data/lib/wx/shapes/auto_layout.rb +358 -0
- data/lib/wx/shapes/base.rb +33 -0
- data/lib/wx/shapes/canvas_history.rb +84 -0
- data/lib/wx/shapes/connection_point.rb +238 -0
- data/lib/wx/shapes/core.rb +19 -0
- data/lib/wx/shapes/diagram.rb +659 -0
- data/lib/wx/shapes/events.rb +389 -0
- data/lib/wx/shapes/printout.rb +136 -0
- data/lib/wx/shapes/serializable.rb +440 -0
- data/lib/wx/shapes/serialize/core.rb +40 -0
- data/lib/wx/shapes/serialize/id.rb +82 -0
- data/lib/wx/shapes/serialize/wx.rb +104 -0
- data/lib/wx/shapes/serializer/json.rb +258 -0
- data/lib/wx/shapes/serializer/yaml.rb +125 -0
- data/lib/wx/shapes/shape.rb +2129 -0
- data/lib/wx/shapes/shape_canvas.rb +3285 -0
- data/lib/wx/shapes/shape_data_object.rb +43 -0
- data/lib/wx/shapes/shape_handle.rb +287 -0
- data/lib/wx/shapes/shape_list.rb +161 -0
- data/lib/wx/shapes/shapes/bitmap_shape.rb +257 -0
- data/lib/wx/shapes/shapes/circle_shape.rb +136 -0
- data/lib/wx/shapes/shapes/control_shape.rb +483 -0
- data/lib/wx/shapes/shapes/curve_shape.rb +231 -0
- data/lib/wx/shapes/shapes/diamond_shape.rb +62 -0
- data/lib/wx/shapes/shapes/edit_text_shape.rb +317 -0
- data/lib/wx/shapes/shapes/ellipse_shape.rb +106 -0
- data/lib/wx/shapes/shapes/flex_grid_shape.rb +78 -0
- data/lib/wx/shapes/shapes/grid_shape.rb +404 -0
- data/lib/wx/shapes/shapes/line_shape.rb +907 -0
- data/lib/wx/shapes/shapes/multi_sel_rect.rb +214 -0
- data/lib/wx/shapes/shapes/ortho_shape.rb +357 -0
- data/lib/wx/shapes/shapes/polygon_shape.rb +294 -0
- data/lib/wx/shapes/shapes/rect_shape.rb +378 -0
- data/lib/wx/shapes/shapes/round_ortho_shape.rb +131 -0
- data/lib/wx/shapes/shapes/round_rect_shape.rb +142 -0
- data/lib/wx/shapes/shapes/square_shape.rb +119 -0
- data/lib/wx/shapes/shapes/text_shape.rb +324 -0
- data/lib/wx/shapes/thumbnail.rb +234 -0
- data/lib/wx/shapes/version.rb +12 -0
- data/lib/wx/shapes/wx.rb +29 -0
- data/lib/wx/shapes.rb +18 -0
- data/lib/wx/wx-shapes/base.rb +87 -0
- data/lib/wx/wx-shapes/cmd/sampler.rb +58 -0
- data/lib/wx/wx-shapes/cmd/test.rb +27 -0
- data/rakelib/yard/templates/default/fulldoc/html/css/wxruby3.css +7 -0
- data/rakelib/yard/templates/default/layout/html/setup.rb +5 -0
- data/rakelib/yard/yard/relative_markdown_links/version.rb +8 -0
- data/rakelib/yard/yard/relative_markdown_links.rb +39 -0
- data/rakelib/yard/yard-custom-templates.rb +2 -0
- data/rakelib/yard/yard-relative_markdown_links.rb +4 -0
- data/samples/demo/art/AlignBottom.xpm +35 -0
- data/samples/demo/art/AlignCenter.xpm +35 -0
- data/samples/demo/art/AlignLeft.xpm +35 -0
- data/samples/demo/art/AlignMiddle.xpm +35 -0
- data/samples/demo/art/AlignRight.xpm +35 -0
- data/samples/demo/art/AlignTop.xpm +35 -0
- data/samples/demo/art/Bitmap.xpm +25 -0
- data/samples/demo/art/Circle.xpm +22 -0
- data/samples/demo/art/Curve.xpm +21 -0
- data/samples/demo/art/Diamond.xpm +22 -0
- data/samples/demo/art/EditText.xpm +21 -0
- data/samples/demo/art/Ellipse.xpm +22 -0
- data/samples/demo/art/FixedRect.xpm +22 -0
- data/samples/demo/art/FlexGrid.xpm +22 -0
- data/samples/demo/art/GC.xpm +23 -0
- data/samples/demo/art/Grid.xpm +22 -0
- data/samples/demo/art/Line.xpm +21 -0
- data/samples/demo/art/NoSource.xpm +69 -0
- data/samples/demo/art/OrthoLine.xpm +21 -0
- data/samples/demo/art/Rect.xpm +22 -0
- data/samples/demo/art/RoundOrthoLine.xpm +21 -0
- data/samples/demo/art/RoundRect.xpm +22 -0
- data/samples/demo/art/Shadow.xpm +23 -0
- data/samples/demo/art/StandAloneLine.xpm +22 -0
- data/samples/demo/art/Text.xpm +21 -0
- data/samples/demo/art/Tool.xpm +23 -0
- data/samples/demo/art/sample.xpm +251 -0
- data/samples/demo/demo.rb +658 -0
- data/samples/demo/frame_canvas.rb +422 -0
- data/samples/demo/images/motyl.bmp +0 -0
- data/samples/demo/images/motyl2.bmp +0 -0
- data/samples/sample1/art/sample.xpm +251 -0
- data/samples/sample1/sample.rb +263 -0
- data/samples/sample2/art/sample.xpm +251 -0
- data/samples/sample2/sample.rb +133 -0
- data/samples/sample2/sample_canvas.rb +35 -0
- data/samples/sample2/sample_shape.rb +108 -0
- data/samples/sample3/art/sample.xpm +251 -0
- data/samples/sample3/sample.rb +281 -0
- data/samples/sample4/art/sample.xpm +251 -0
- data/samples/sample4/sample.rb +180 -0
- data/tests/art/motyl.bmp +0 -0
- data/tests/lib/wxapp_runner.rb +64 -0
- data/tests/serializer_tests.rb +521 -0
- data/tests/test_grid_shapes.rb +42 -0
- data/tests/test_serialize.rb +7 -0
- data/tests/test_serialize_yaml.rb +17 -0
- metadata +242 -0
|
@@ -0,0 +1,62 @@
|
|
|
1
|
+
# Wx::SF::DiamondShape - Diamond shape class
|
|
2
|
+
# Copyright (c) M.J.N. Corino, The Netherlands
|
|
3
|
+
|
|
4
|
+
require 'wx/shapes/shapes/polygon_shape'
|
|
5
|
+
|
|
6
|
+
module Wx::SF
|
|
7
|
+
|
|
8
|
+
class DiamondShape < PolygonShape
|
|
9
|
+
|
|
10
|
+
class << self
|
|
11
|
+
def diamond
|
|
12
|
+
@diamond ||= [Wx::RealPoint.new(0,25), Wx::RealPoint.new(50,0), Wx::RealPoint.new(100, 25), Wx::RealPoint.new(50, 50)]
|
|
13
|
+
end
|
|
14
|
+
end
|
|
15
|
+
|
|
16
|
+
# do not serialize because the vertices are assigned fixed in ctor
|
|
17
|
+
excludes :vertices
|
|
18
|
+
|
|
19
|
+
# @overload initialize()
|
|
20
|
+
# Default constructor.
|
|
21
|
+
# @overload initialize(pos, size, diagram)
|
|
22
|
+
# User constructor.
|
|
23
|
+
# @param [Wx::RealPoint] pos Initial position
|
|
24
|
+
# @param [Wx::SF::Diagram] diagram parent diagram
|
|
25
|
+
def initialize(*args)
|
|
26
|
+
if args.empty?
|
|
27
|
+
super
|
|
28
|
+
set_vertices(DiamondShape.diamond)
|
|
29
|
+
else
|
|
30
|
+
super(DiamondShape.diamond, *args)
|
|
31
|
+
end
|
|
32
|
+
end
|
|
33
|
+
|
|
34
|
+
# Test whether the given point is inside the shape. The function
|
|
35
|
+
# can be overridden if necessary.
|
|
36
|
+
# @param [Wx::Point] pos Examined point
|
|
37
|
+
# @return [Boolean] true if the point is inside the shape area, otherwise false
|
|
38
|
+
def contains?(pos)
|
|
39
|
+
bb_rct = get_bounding_box
|
|
40
|
+
return false unless bb_rct.contains?(pos)
|
|
41
|
+
|
|
42
|
+
center = get_center
|
|
43
|
+
k = (bb_rct.height/2).to_f/(bb_rct.width/2).to_f
|
|
44
|
+
|
|
45
|
+
if pos.x <= center.x
|
|
46
|
+
# test left-top quadrant
|
|
47
|
+
return true if (pos.y <= center.y) && (pos.y >= (center.y - (pos.x - bb_rct.left)*k))
|
|
48
|
+
# test left-bottom quadrant
|
|
49
|
+
return true if (pos.y >= center.y) && (pos.y <= (center.y + (pos.x - bb_rct.left)*k))
|
|
50
|
+
else
|
|
51
|
+
# test right-top quadrant
|
|
52
|
+
return true if (pos.y <= center.y) && (pos.y >= (bb_rct.top + (pos.x - center.x)*k))
|
|
53
|
+
# test left-bottom quadrant
|
|
54
|
+
return true if (pos.y >= center.y) && (pos.y <= (bb_rct.bottom - (pos.x - center.x)*k))
|
|
55
|
+
end
|
|
56
|
+
|
|
57
|
+
false
|
|
58
|
+
end
|
|
59
|
+
|
|
60
|
+
end
|
|
61
|
+
|
|
62
|
+
end
|
|
@@ -0,0 +1,317 @@
|
|
|
1
|
+
# Wx::SF::EditTextShape - edit text shape class
|
|
2
|
+
# Copyright (c) M.J.N. Corino, The Netherlands
|
|
3
|
+
|
|
4
|
+
require 'wx/shapes/shapes/text_shape'
|
|
5
|
+
|
|
6
|
+
module Wx::SF
|
|
7
|
+
|
|
8
|
+
CANCEL_TEXT_CHANGES = false
|
|
9
|
+
APPLY_TEXT_CHANGES = true
|
|
10
|
+
|
|
11
|
+
class ContentCtrl < Wx::TextCtrl
|
|
12
|
+
|
|
13
|
+
# Constructor.
|
|
14
|
+
# @param [Wx::Window] parent Pointer to the parent window
|
|
15
|
+
# @param [Integer] id ID of the text control window
|
|
16
|
+
# @param [Wx::SF::EditTextShape] parent_shape Pointer to the parent editable text shape
|
|
17
|
+
# @param [String] content Initial content of the text control
|
|
18
|
+
# @param [Wx::Point] pos Initial position
|
|
19
|
+
# @param [Wx::Size] size Initial size
|
|
20
|
+
# @param [Integer] style Window style
|
|
21
|
+
def initialize(parent, id, parent_shape, content, pos, size, style)
|
|
22
|
+
super(parent, id, content, pos, size, Wx::TE_PROCESS_ENTER | Wx::TE_PROCESS_TAB | Wx::NO_BORDER | style)
|
|
23
|
+
@parent = parent
|
|
24
|
+
@parent_shape = parent_shape
|
|
25
|
+
@prev_content = content
|
|
26
|
+
|
|
27
|
+
evt_kill_focus :on_kill_focus
|
|
28
|
+
evt_key_down :on_key_down
|
|
29
|
+
|
|
30
|
+
set_insertion_point_end
|
|
31
|
+
if @parent_shape
|
|
32
|
+
# update the font size in accordance to the canvas scale
|
|
33
|
+
font = @parent_shape.get_font
|
|
34
|
+
font.set_point_size((font.get_point_size * @parent_shape.get_parent_canvas.get_scale).to_i)
|
|
35
|
+
|
|
36
|
+
set_font(font)
|
|
37
|
+
set_background_colour(Wx::Colour.new(200, 200, 200))
|
|
38
|
+
set_focus
|
|
39
|
+
end
|
|
40
|
+
end
|
|
41
|
+
|
|
42
|
+
# Finish the editing process/
|
|
43
|
+
# @param [Boolean] apply If true then changes made in edited text will be applied on text shape, otherwise it will be canceled
|
|
44
|
+
def quit(apply = APPLY_TEXT_CHANGES)
|
|
45
|
+
self.hide
|
|
46
|
+
|
|
47
|
+
if @parent_shape
|
|
48
|
+
@parent_shape.send(:set_text_ctrl, nil)
|
|
49
|
+
@parent_shape.set_style(@parent_shape.send(:get_current_state))
|
|
50
|
+
|
|
51
|
+
# save canvas state if the textctrl content has changed...
|
|
52
|
+
if apply && @prev_content != get_value
|
|
53
|
+
@parent_shape.set_text(get_value)
|
|
54
|
+
@prev_content = get_value
|
|
55
|
+
|
|
56
|
+
# inform parent shape canvas about text change...
|
|
57
|
+
@parent_shape.get_parent_canvas.on_text_change(@parent_shape)
|
|
58
|
+
@parent_shape.get_parent_canvas.save_canvas_state
|
|
59
|
+
end
|
|
60
|
+
|
|
61
|
+
@parent_shape.update
|
|
62
|
+
@parent_shape.get_parent_canvas.refresh
|
|
63
|
+
end
|
|
64
|
+
|
|
65
|
+
self.destroy
|
|
66
|
+
end
|
|
67
|
+
|
|
68
|
+
protected
|
|
69
|
+
|
|
70
|
+
# Event handler called if the text control lost the focus.
|
|
71
|
+
# @param [Wx::FocusEvent] _event Reference to the event class instance
|
|
72
|
+
def on_kill_focus(_event)
|
|
73
|
+
# noop
|
|
74
|
+
end
|
|
75
|
+
|
|
76
|
+
# Event handler called if the key was pressed in the text control.
|
|
77
|
+
# @param [Wx::KeyEvent] event Reference to the event class instance
|
|
78
|
+
def on_key_down(event)
|
|
79
|
+
case event.get_key_code
|
|
80
|
+
when Wx::K_ESCAPE
|
|
81
|
+
quit(CANCEL_TEXT_CHANGES)
|
|
82
|
+
when Wx::K_TAB
|
|
83
|
+
quit(APPLY_TEXT_CHANGES)
|
|
84
|
+
when Wx::K_RETURN
|
|
85
|
+
# enter new line if SHIFT key was pressed together with the ENTER key
|
|
86
|
+
if Wx::get_key_state(Wx::K_SHIFT)
|
|
87
|
+
event.skip
|
|
88
|
+
else
|
|
89
|
+
quit(APPLY_TEXT_CHANGES)
|
|
90
|
+
end
|
|
91
|
+
else
|
|
92
|
+
event.skip
|
|
93
|
+
end
|
|
94
|
+
end
|
|
95
|
+
|
|
96
|
+
end
|
|
97
|
+
|
|
98
|
+
# Auxiliary class providing necessary functionality needed for dialog-based
|
|
99
|
+
# modification of a content of the text shape.
|
|
100
|
+
# @see EditTextShape
|
|
101
|
+
class DetachedContentCtrl < Wx::Dialog
|
|
102
|
+
|
|
103
|
+
# Constructor.
|
|
104
|
+
# @param [Wx::Window] parent Pointer to the parent window
|
|
105
|
+
# @param [Integer] id ID of the text control window
|
|
106
|
+
# @param [String] title Dialog's title
|
|
107
|
+
# @param [Wx::Point] pos Initial position
|
|
108
|
+
# @param [Wx::Size] size Initial size
|
|
109
|
+
# @param [Integer] style Window style
|
|
110
|
+
def initialize(parent, id = Wx::ID_ANY, title = 'Edit content',
|
|
111
|
+
pos = Wx::DEFAULT_POSITION, size = Wx::DEFAULT_SIZE,
|
|
112
|
+
style = Wx::DEFAULT_DIALOG_STYLE|Wx::RESIZE_BORDER)
|
|
113
|
+
set_size_hints(Wx::Size.new(-1,-1), Wx::DEFAULT_SIZE)
|
|
114
|
+
|
|
115
|
+
main_sizer = Wx::VBoxSizer.new
|
|
116
|
+
|
|
117
|
+
@text = Wx::TextCtrl.new(self, Wx::ID_ANY, '', Wx::DEFAULT_POSITION, [350,100], Wx::TE_MULTILINE)
|
|
118
|
+
@text.set_min_size([350,100])
|
|
119
|
+
|
|
120
|
+
main_sizer.add(@text, 1, Wx::ALL|Wx::EXPAND, 5)
|
|
121
|
+
|
|
122
|
+
button_sizer = Wx::StdDialogButtonSizer.new
|
|
123
|
+
button_sizer_ok = Wx::Button.new(self, Wx::ID_OK)
|
|
124
|
+
button_sizer.add_button(button_sizer_ok)
|
|
125
|
+
button_sizer_cancel = Wx::Button.new(self, Wx::ID_CANCEL)
|
|
126
|
+
button_sizer.add_button(button_sizer_cancel)
|
|
127
|
+
button_sizer.realize
|
|
128
|
+
main_sizer.add(button_sizer, 0, Wx::ALIGN_RIGHT|Wx::BOTTOM|Wx::RIGHT, 5)
|
|
129
|
+
|
|
130
|
+
set_sizer(main_sizer)
|
|
131
|
+
layout
|
|
132
|
+
main_sizer.fit(self)
|
|
133
|
+
|
|
134
|
+
centre(Wx::BOTH)
|
|
135
|
+
end
|
|
136
|
+
|
|
137
|
+
# Set content of dialog's text edit control.
|
|
138
|
+
# @param [String] txt Text content
|
|
139
|
+
def set_content(txt)
|
|
140
|
+
@text.set_value(txt)
|
|
141
|
+
end
|
|
142
|
+
|
|
143
|
+
# Get content of dialog's text edit control.
|
|
144
|
+
# @return [String] Edited text
|
|
145
|
+
def get_content
|
|
146
|
+
@text.get_value
|
|
147
|
+
end
|
|
148
|
+
|
|
149
|
+
end
|
|
150
|
+
|
|
151
|
+
# Class encapsulating the editable text shape. It extends the basic text shape.
|
|
152
|
+
# @see Wx::SF::TextShape
|
|
153
|
+
class EditTextShape < TextShape
|
|
154
|
+
|
|
155
|
+
class EDITTYPE < Wx::Enum
|
|
156
|
+
INPLACE = self.new(0)
|
|
157
|
+
DIALOG = self.new(1)
|
|
158
|
+
DISABLED = self.new(1)
|
|
159
|
+
end
|
|
160
|
+
|
|
161
|
+
# Default values
|
|
162
|
+
module DEFAULT
|
|
163
|
+
# Default value of EditTextShape @force_multiline data member
|
|
164
|
+
FORCE_MULTILINE = false
|
|
165
|
+
# Default value of EditTextShape @edit_type data member
|
|
166
|
+
EDIT_TYPE = EDITTYPE::INPLACE
|
|
167
|
+
end
|
|
168
|
+
|
|
169
|
+
property :force_multiline, :edit_type
|
|
170
|
+
|
|
171
|
+
# @overload initialize()
|
|
172
|
+
# Default constructor.
|
|
173
|
+
# @overload initialize(pos, txt, diagram)
|
|
174
|
+
# User constructor.
|
|
175
|
+
# @param [Wx::RealPoint] pos Initial position
|
|
176
|
+
# @param [String] txt Initial content
|
|
177
|
+
# @param [Wx::SF::Diagram] diagram parent diagram
|
|
178
|
+
def initialize(*args)
|
|
179
|
+
super
|
|
180
|
+
@text_ctrl = nil
|
|
181
|
+
@force_multiline = DEFAULT::FORCE_MULTILINE
|
|
182
|
+
@edit_type = DEFAULT::EDIT_TYPE
|
|
183
|
+
@current_state = 0
|
|
184
|
+
end
|
|
185
|
+
|
|
186
|
+
attr_reader :force_multiline
|
|
187
|
+
|
|
188
|
+
# Set way how the text shape's content can be edited.
|
|
189
|
+
# @param [EDITTYPE] type Edit control type
|
|
190
|
+
# @see EDITTYPE
|
|
191
|
+
def set_edit_type(type)
|
|
192
|
+
@edit_type = type
|
|
193
|
+
end
|
|
194
|
+
alias :edit_type= :set_edit_type
|
|
195
|
+
|
|
196
|
+
# Get current type of text shape's edit control.
|
|
197
|
+
# @return [EDITTYPE] Type of edit control
|
|
198
|
+
# @see EDITTYPE
|
|
199
|
+
def get_edit_type
|
|
200
|
+
@edit_type
|
|
201
|
+
end
|
|
202
|
+
alias :edit_type :get_edit_type
|
|
203
|
+
|
|
204
|
+
# Get assigned text control allowing user to change the
|
|
205
|
+
# shape's content directly in the canvas.
|
|
206
|
+
# @return [ContentCtrl] instance of wxSFContentCtrl class
|
|
207
|
+
def get_text_ctrl
|
|
208
|
+
@text_ctrl
|
|
209
|
+
end
|
|
210
|
+
alias :text_ctrl :get_text_ctrl
|
|
211
|
+
|
|
212
|
+
def set_text_ctrl(txt_ctrl)
|
|
213
|
+
@text_ctrl = txt_ctrl
|
|
214
|
+
end
|
|
215
|
+
private :set_text_ctrl
|
|
216
|
+
|
|
217
|
+
# Switch the shape to a label editing mode.
|
|
218
|
+
def edit_label
|
|
219
|
+
if get_parent_canvas
|
|
220
|
+
shp_pos = get_absolute_position
|
|
221
|
+
scale = get_parent_canvas.get_scale
|
|
222
|
+
dx, dy = get_parent_canvas.calc_unscrolled_position(0, 0)
|
|
223
|
+
|
|
224
|
+
case @edit_type
|
|
225
|
+
when EDITTYPE::INPLACE
|
|
226
|
+
shp_bb = get_bounding_box
|
|
227
|
+
style = 0
|
|
228
|
+
style = Wx::TE_MULTILINE if @force_multiline || @text.index("\n")
|
|
229
|
+
|
|
230
|
+
# set minimal control size
|
|
231
|
+
shp_bb.set_width(50) if @text == '' || (style == Wx::TE_MULTILINE && shp_bb.width < 50)
|
|
232
|
+
|
|
233
|
+
@current_state = get_style
|
|
234
|
+
remove_style(STYLE::SIZE_CHANGE)
|
|
235
|
+
|
|
236
|
+
@text_ctrl = ContentCtrl.new(get_parent_canvas, Wx::ID_ANY, self, @text,
|
|
237
|
+
[((shp_pos.x * scale) - dx).to_i, ((shp_pos.y * scale) - dy).to_i],
|
|
238
|
+
[(shp_bb.width * scale).to_i, (shp_bb.height * scale).to_i], style)
|
|
239
|
+
|
|
240
|
+
when EDITTYPE::DIALOG
|
|
241
|
+
prev_text = get_text
|
|
242
|
+
|
|
243
|
+
DetachedContentCtrl(get_parent_canvas) do |text_dlg|
|
|
244
|
+
text_dlg.set_content(prev_text)
|
|
245
|
+
|
|
246
|
+
if text_dlg.show_modal == Wx::ID_OK
|
|
247
|
+
if text_dlg.get_content != prev_text
|
|
248
|
+
set_text(text_dlg.get_content)
|
|
249
|
+
|
|
250
|
+
get_parent_canvas.on_text_change(self)
|
|
251
|
+
get_parent_canvas.save_canvas_state
|
|
252
|
+
|
|
253
|
+
update
|
|
254
|
+
get_parent_canvas.refresh(false)
|
|
255
|
+
end
|
|
256
|
+
end
|
|
257
|
+
end
|
|
258
|
+
end
|
|
259
|
+
end
|
|
260
|
+
end
|
|
261
|
+
|
|
262
|
+
# Force the edit text control to be multiline
|
|
263
|
+
# @param [Boolean] multiline If true then the associated text control will be always multiline
|
|
264
|
+
def set_force_multiline(multiline)
|
|
265
|
+
@force_multiline = multiline
|
|
266
|
+
end
|
|
267
|
+
alias :force_multiline= :set_force_multiline
|
|
268
|
+
|
|
269
|
+
# Event handler called when the shape was double-clicked.
|
|
270
|
+
# The function can be overridden if necessary.
|
|
271
|
+
# @param [Wx::Point] pos Mouse position.
|
|
272
|
+
def on_left_double_click(pos)
|
|
273
|
+
# HINT: override it if necessary...
|
|
274
|
+
edit_label
|
|
275
|
+
end
|
|
276
|
+
|
|
277
|
+
# Event handler called when any key is pressed (in the shape canvas).
|
|
278
|
+
# The function can be overridden if necessary.
|
|
279
|
+
#
|
|
280
|
+
# The function is called by the framework (by the shape canvas).
|
|
281
|
+
# @param [Integer] key The key code
|
|
282
|
+
# @return [Boolean] The function must return true if the default event routine should be called
|
|
283
|
+
# as well, otherwise false
|
|
284
|
+
# @see Shape#on_key
|
|
285
|
+
def on_key(key)
|
|
286
|
+
# HINT: override it if necessary...
|
|
287
|
+
if key == Wx::K_F2
|
|
288
|
+
edit_label if active? && visible?
|
|
289
|
+
end
|
|
290
|
+
super
|
|
291
|
+
end
|
|
292
|
+
|
|
293
|
+
protected
|
|
294
|
+
|
|
295
|
+
# Event handler called by ShapeCanvas to request,report canvas changes.
|
|
296
|
+
# @param [ShapeCanvas::CHANGE] change change type indicator
|
|
297
|
+
# @param [Array] _args any additional arguments
|
|
298
|
+
# @return [Boolean,nil]
|
|
299
|
+
def _on_canvas(change, *_args)
|
|
300
|
+
if change == ShapeCanvas::CHANGE::FOCUS
|
|
301
|
+
text_ctrl = get_text_ctrl
|
|
302
|
+
text_ctrl.quit(APPLY_TEXT_CHANGES) if text_ctrl
|
|
303
|
+
end
|
|
304
|
+
super
|
|
305
|
+
end
|
|
306
|
+
|
|
307
|
+
private
|
|
308
|
+
|
|
309
|
+
# Return cached state
|
|
310
|
+
# @return [Integer]
|
|
311
|
+
def get_current_state
|
|
312
|
+
@current_state
|
|
313
|
+
end
|
|
314
|
+
|
|
315
|
+
end
|
|
316
|
+
|
|
317
|
+
end
|
|
@@ -0,0 +1,106 @@
|
|
|
1
|
+
# Wx::SF::EllipseShape - ellipse shape class
|
|
2
|
+
# Copyright (c) M.J.N. Corino, The Netherlands
|
|
3
|
+
|
|
4
|
+
module Wx::SF
|
|
5
|
+
|
|
6
|
+
# Class encapsulating the ellipse shape. It extends the basic rectangular shape.
|
|
7
|
+
class EllipseShape < RectShape
|
|
8
|
+
|
|
9
|
+
# @overload initialize()
|
|
10
|
+
# Default constructor.
|
|
11
|
+
# @overload initialize(pos, size, diagram)
|
|
12
|
+
# User constructor.
|
|
13
|
+
# @param [Wx::RealPoint] pos Initial position
|
|
14
|
+
# @param [Wx::RealPoint] size Initial size
|
|
15
|
+
# @param [Wx::SF::Diagram] diagram parent diagram
|
|
16
|
+
def initialize(*args)
|
|
17
|
+
super
|
|
18
|
+
end
|
|
19
|
+
|
|
20
|
+
# Test whether the given point is inside the shape. The function
|
|
21
|
+
# can be overridden if necessary.
|
|
22
|
+
# @param [Wx::Point] pos Examined point
|
|
23
|
+
# @return [Boolean] true if the point is inside the shape area, otherwise false
|
|
24
|
+
def contains?(pos)
|
|
25
|
+
a = get_rect_size.x/2
|
|
26
|
+
b = get_rect_size.y/2
|
|
27
|
+
apos = get_absolute_position
|
|
28
|
+
|
|
29
|
+
m = apos.x + a
|
|
30
|
+
n = apos.y + b
|
|
31
|
+
|
|
32
|
+
pos = pos.to_point
|
|
33
|
+
(((pos.x - m)*(pos.x - m))/(a*a) + ((pos.y - n)*(pos.y - n))/(b*b)) < 1
|
|
34
|
+
end
|
|
35
|
+
|
|
36
|
+
# Get intersection point of the shape border and a line leading from
|
|
37
|
+
# 'start' point to 'end_pt' point. The function can be overridden if necessary.
|
|
38
|
+
# @param [Wx::RealPoint] start Starting point of the virtual intersection line
|
|
39
|
+
# @param [Wx::RealPoint] end_pt Ending point of the virtual intersection line
|
|
40
|
+
# @return [Wx::RealPoint] Intersection point
|
|
41
|
+
def get_border_point(start, end_pt)
|
|
42
|
+
start = start.to_real_point; end_pt.to_real_point
|
|
43
|
+
dist = start.distance_to(end_pt)
|
|
44
|
+
center = get_absolute_position + [@rect_size.x/2, @rect_size.y/2]
|
|
45
|
+
|
|
46
|
+
if dist != 0.0
|
|
47
|
+
src_dx = @rect_size.x/2*(end_pt.x-start.x)/dist - (start.x-center.x)
|
|
48
|
+
src_dy = @rect_size.y/2*(end_pt.y-start.y)/dist - (start.y-center.y)
|
|
49
|
+
|
|
50
|
+
Wx::RealPoint.new(start.x + src_dx, start.y + src_dy)
|
|
51
|
+
else
|
|
52
|
+
center
|
|
53
|
+
end
|
|
54
|
+
end
|
|
55
|
+
|
|
56
|
+
protected
|
|
57
|
+
|
|
58
|
+
# Draw the shape in the normal way. The function can be overridden if necessary.
|
|
59
|
+
# @param [Wx::DC] dc Reference to device context where the shape will be drawn to
|
|
60
|
+
def draw_normal(dc)
|
|
61
|
+
dc.with_pen(@border) do
|
|
62
|
+
dc.with_brush(@fill) do
|
|
63
|
+
dc.draw_ellipse(get_absolute_position.to_point, @rect_size.to_size)
|
|
64
|
+
end
|
|
65
|
+
end
|
|
66
|
+
end
|
|
67
|
+
|
|
68
|
+
# Draw the shape in the hover mode (the mouse cursor is above the shape).
|
|
69
|
+
# The function can be overridden if necessary.
|
|
70
|
+
# @param [Wx::DC] dc Reference to device context where the shape will be drawn to
|
|
71
|
+
def draw_hover(dc)
|
|
72
|
+
dc.with_pen(Wx::Pen.new(@hover_color, 1)) do
|
|
73
|
+
dc.with_brush(@fill) do
|
|
74
|
+
dc.draw_ellipse(get_absolute_position.to_point, @rect_size.to_size)
|
|
75
|
+
end
|
|
76
|
+
end
|
|
77
|
+
end
|
|
78
|
+
|
|
79
|
+
# Draw the shape in the highlighted mode (another shape is dragged over this
|
|
80
|
+
# shape and this shape will accept the dragged one if it will be dropped on it).
|
|
81
|
+
# The function can be overridden if necessary.
|
|
82
|
+
# @param [Wx::DC] dc Reference to device context where the shape will be drawn to
|
|
83
|
+
def draw_highlighted(dc)
|
|
84
|
+
dc.with_pen(Wx::Pen.new(@hover_color, 2)) do
|
|
85
|
+
dc.with_brush(@fill) do
|
|
86
|
+
dc.draw_ellipse(get_absolute_position.to_point, @rect_size.to_size)
|
|
87
|
+
end
|
|
88
|
+
end
|
|
89
|
+
end
|
|
90
|
+
|
|
91
|
+
# Draw shadow under the shape. The function can be overridden if necessary.
|
|
92
|
+
# @param [Wx::DC] dc Reference to device context where the shadow will be drawn to
|
|
93
|
+
def draw_shadow(dc)
|
|
94
|
+
if @fill.style != Wx::BrushStyle::BRUSHSTYLE_TRANSPARENT
|
|
95
|
+
dc.with_pen(Wx::TRANSPARENT_PEN) do
|
|
96
|
+
dc.with_brush(get_parent_canvas.get_shadow_fill) do
|
|
97
|
+
dc.draw_ellipse((get_absolute_position + get_parent_canvas.get_shadow_offset).to_point,
|
|
98
|
+
@rect_size.to_size)
|
|
99
|
+
end
|
|
100
|
+
end
|
|
101
|
+
end
|
|
102
|
+
end
|
|
103
|
+
|
|
104
|
+
end
|
|
105
|
+
|
|
106
|
+
end
|
|
@@ -0,0 +1,78 @@
|
|
|
1
|
+
# Wx::SF::FlexGridShape - flexible grid shape class
|
|
2
|
+
# Copyright (c) M.J.N. Corino, The Netherlands
|
|
3
|
+
|
|
4
|
+
require 'wx/shapes/shapes/grid_shape'
|
|
5
|
+
|
|
6
|
+
module Wx::SF
|
|
7
|
+
|
|
8
|
+
# Class encapsulates a rectangular shape derived from {GridShape} class which acts as a flexible grid-based
|
|
9
|
+
# container able to manage other assigned child shapes (it can control their position). The managed
|
|
10
|
+
# shapes are aligned into defined grid with a behaviour similar to classic Wx::FlexGridSizer class.
|
|
11
|
+
class FlexGridShape < GridShape
|
|
12
|
+
|
|
13
|
+
|
|
14
|
+
# @overload initialize()
|
|
15
|
+
# Default constructor.
|
|
16
|
+
# @overload initialize(pos, size, rows, cols, cell_space, diagram)
|
|
17
|
+
# User constructor.
|
|
18
|
+
# @param [Wx::RealPoint] pos Initial position
|
|
19
|
+
# @param [Wx::RealPoint] size Initial size
|
|
20
|
+
# @param [Integer] cols Number of grid rows
|
|
21
|
+
# @param [Integer] rows Number of grid columns
|
|
22
|
+
# @param [Integer] cell_space Additional space between managed shapes
|
|
23
|
+
# @param [Wx::SF::Diagram] diagram parent diagram
|
|
24
|
+
def initialize(*args)
|
|
25
|
+
super
|
|
26
|
+
end
|
|
27
|
+
|
|
28
|
+
# Do layout of assigned child shapes
|
|
29
|
+
def do_children_layout
|
|
30
|
+
return if @cols == 0 || @rows == 0
|
|
31
|
+
|
|
32
|
+
# initialize size arrays
|
|
33
|
+
row_sizes = ::Array.new(@rows, 0)
|
|
34
|
+
col_sizes = ::Array.new(@cols, 0)
|
|
35
|
+
|
|
36
|
+
# prepare a storage for processed shapes pointers
|
|
37
|
+
grid_shapes = ::Array.new(@cells.size)
|
|
38
|
+
|
|
39
|
+
# get maximum size of all managed (child) shapes per row and column
|
|
40
|
+
@cells.each_with_index do |id, i|
|
|
41
|
+
if id
|
|
42
|
+
col = (i % @cols)
|
|
43
|
+
row = (i / @cols)
|
|
44
|
+
|
|
45
|
+
grid_shapes[i] = shape = @child_shapes[id]
|
|
46
|
+
curr_rect = shape.get_bounding_box
|
|
47
|
+
|
|
48
|
+
# update maximum rows and columns sizes
|
|
49
|
+
col_sizes[col] = curr_rect.width if (shape.get_h_align != HALIGN::EXPAND) && (curr_rect.width > col_sizes[col])
|
|
50
|
+
row_sizes[row] = curr_rect.height if (shape.get_v_align != VALIGN::EXPAND) && (curr_rect.height > row_sizes[row])
|
|
51
|
+
end
|
|
52
|
+
end
|
|
53
|
+
|
|
54
|
+
total_x = total_y = 0
|
|
55
|
+
|
|
56
|
+
# put managed shapes to appropriate positions
|
|
57
|
+
grid_shapes.each_with_index do |shape, i|
|
|
58
|
+
if shape
|
|
59
|
+
col = (i % @cols)
|
|
60
|
+
row = (i / @cols)
|
|
61
|
+
if col == 0
|
|
62
|
+
total_x = 0
|
|
63
|
+
total_y += row_sizes[row-1] if row > 0
|
|
64
|
+
else
|
|
65
|
+
total_x += col_sizes[col-1]
|
|
66
|
+
end
|
|
67
|
+
|
|
68
|
+
fit_shape_to_rect(shape,
|
|
69
|
+
Wx::Rect.new(total_x + (col+1)*@cell_space,
|
|
70
|
+
total_y + (row+1)*@cell_space,
|
|
71
|
+
col_sizes[col], row_sizes[row]))
|
|
72
|
+
end
|
|
73
|
+
end
|
|
74
|
+
end
|
|
75
|
+
|
|
76
|
+
end
|
|
77
|
+
|
|
78
|
+
end
|