1 /***********************************************************************
2 created: 25/4/2004
3 author: Paul D Turner
4
5 purpose: Implements common parts of the Thumb base class widget
6 *************************************************************************/
7 /***************************************************************************
8 * Copyright (C) 2004 - 2006 Paul D Turner & The CEGUI Development Team
9 *
10 * Permission is hereby granted, free of charge, to any person obtaining
11 * a copy of this software and associated documentation files (the
12 * "Software"), to deal in the Software without restriction, including
13 * without limitation the rights to use, copy, modify, merge, publish,
14 * distribute, sublicense, and/or sell copies of the Software, and to
15 * permit persons to whom the Software is furnished to do so, subject to
16 * the following conditions:
17 *
18 * The above copyright notice and this permission notice shall be
19 * included in all copies or substantial portions of the Software.
20 *
21 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
22 * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
23 * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
24 * IN NO EVENT SHALL THE AUTHORS BE LIABLE FOR ANY CLAIM, DAMAGES OR
25 * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
26 * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
27 * OTHER DEALINGS IN THE SOFTWARE.
28 ***************************************************************************/
29 #include "CEGUI/widgets/Thumb.h"
30 #include "CEGUI/CoordConverter.h"
31
32 // Start of CEGUI namespace section
33 namespace CEGUI
34 {
35 const String Thumb::EventNamespace("Thumb");
36 const String Thumb::WidgetTypeName("CEGUI/Thumb");
37
38 /*************************************************************************
39 Event name constants
40 *************************************************************************/
41 // generated internally by Window
42 const String Thumb::EventThumbPositionChanged( "ThumbPositionChanged" );
43 const String Thumb::EventThumbTrackStarted( "ThumbTrackStarted" );
44 const String Thumb::EventThumbTrackEnded( "ThumbTrackEnded" );
45
46
47 /*************************************************************************
48 Constructor for Thumb objects
49 *************************************************************************/
Thumb(const String & type,const String & name)50 Thumb::Thumb(const String& type, const String& name) :
51 PushButton(type, name),
52 d_hotTrack(true),
53 d_vertFree(false),
54 d_horzFree(false),
55 d_vertMin(0.0f),
56 d_vertMax(1.0f),
57 d_horzMin(0.0f),
58 d_horzMax(1.0f),
59 d_beingDragged(false)
60 {
61 addThumbProperties();
62 }
63
64
65 /*************************************************************************
66 Destructor for Thumb objects
67 *************************************************************************/
~Thumb(void)68 Thumb::~Thumb(void)
69 {
70 }
71
72
73 /*************************************************************************
74 set the movement range of the thumb for the vertical axis.
75 *************************************************************************/
setVertRange(float min,float max)76 void Thumb::setVertRange(float min, float max)
77 {
78 // ensure min <= max, swap if not.
79 if (min > max)
80 {
81 float tmp = min;
82 max = min;
83 min = tmp;
84 }
85
86 d_vertMax = max;
87 d_vertMin = min;
88
89 // validate current position.
90 const float cp = CoordConverter::asRelative(getYPosition(), getParentPixelSize().d_height);
91
92 if (cp < min)
93 {
94 setYPosition(cegui_reldim(min));
95 }
96 else if (cp > max)
97 {
98 setYPosition(cegui_reldim(max));
99 }
100
101 }
102
103 /*************************************************************************
104 set the movement range of the thumb for the vertical axis.
105 *************************************************************************/
setVertRange(const std::pair<float,float> & range)106 void Thumb::setVertRange(const std::pair<float, float> &range)
107 {
108 setVertRange(range.first,range.second);
109 }
110 /*************************************************************************
111 set the movement range of the thumb for the horizontal axis.
112 *************************************************************************/
setHorzRange(float min,float max)113 void Thumb::setHorzRange(float min, float max)
114 {
115 Sizef parentSize(getParentPixelSize());
116
117 // ensure min <= max, swap if not.
118 if (min > max)
119 {
120 float tmp = min;
121 max = min;
122 min = tmp;
123 }
124
125 d_horzMax = max;
126 d_horzMin = min;
127
128 // validate current position.
129 const float cp = CoordConverter::asAbsolute(getXPosition(), parentSize.d_width);
130
131 if (cp < min)
132 {
133 setXPosition(cegui_absdim(min));
134 }
135 else if (cp > max)
136 {
137 setXPosition(cegui_absdim(max));
138 }
139
140 }
141 /*************************************************************************
142 set the movement range of the thumb for the horizontal axis.
143 *************************************************************************/
setHorzRange(const std::pair<float,float> & range)144 void Thumb::setHorzRange(const std::pair<float, float> &range)
145 {
146 setHorzRange(range.first,range.second);
147 }
148
149
150 /*************************************************************************
151 event triggered internally when the position of the thumb
152 *************************************************************************/
onThumbPositionChanged(WindowEventArgs & e)153 void Thumb::onThumbPositionChanged(WindowEventArgs& e)
154 {
155 fireEvent(EventThumbPositionChanged, e, EventNamespace);
156 }
157
158
159 /*************************************************************************
160 Handler triggered when the user begins to drag the thumb.
161 *************************************************************************/
onThumbTrackStarted(WindowEventArgs & e)162 void Thumb::onThumbTrackStarted(WindowEventArgs& e)
163 {
164 fireEvent(EventThumbTrackStarted, e, EventNamespace);
165 }
166
167
168 /*************************************************************************
169 Handler triggered when the thumb is released
170 *************************************************************************/
onThumbTrackEnded(WindowEventArgs & e)171 void Thumb::onThumbTrackEnded(WindowEventArgs& e)
172 {
173 fireEvent(EventThumbTrackEnded, e, EventNamespace);
174 }
175
176
177 /*************************************************************************
178 Handler for mouse movement events
179 *************************************************************************/
onMouseMove(MouseEventArgs & e)180 void Thumb::onMouseMove(MouseEventArgs& e)
181 {
182 // default processing
183 PushButton::onMouseMove(e);
184
185 // only react if we are being dragged
186 if (d_beingDragged)
187 {
188 Sizef parentSize(getParentPixelSize());
189
190 Vector2f delta;
191 float hmin, hmax, vmin, vmax;
192
193 delta = CoordConverter::screenToWindow(*this, e.position);
194
195 hmin = d_horzMin;
196 hmax = d_horzMax;
197 vmin = d_vertMin;
198 vmax = d_vertMax;
199
200 // calculate amount of movement
201 delta -= d_dragPoint;
202 delta.d_x /= parentSize.d_width;
203 delta.d_y /= parentSize.d_height;
204
205 //
206 // Calculate new (pixel) position for thumb
207 //
208 UVector2 newPos(getPosition());
209
210 if (d_horzFree)
211 {
212 newPos.d_x.d_scale += delta.d_x;
213
214 // limit value to within currently set range
215 newPos.d_x.d_scale = (newPos.d_x.d_scale < hmin) ? hmin : (newPos.d_x.d_scale > hmax) ? hmax : newPos.d_x.d_scale;
216 }
217
218 if (d_vertFree)
219 {
220 newPos.d_y.d_scale += delta.d_y;
221
222 // limit new position to within currently set range
223 newPos.d_y.d_scale = (newPos.d_y.d_scale < vmin) ? vmin : (newPos.d_y.d_scale > vmax) ? vmax : newPos.d_y.d_scale;
224 }
225
226 // update thumb position if needed
227 if (newPos != getPosition())
228 {
229 setPosition(newPos);
230
231 // send notification as required
232 if (d_hotTrack)
233 {
234 WindowEventArgs args(this);
235 onThumbPositionChanged(args);
236 }
237
238 }
239
240 }
241
242 ++e.handled;
243 }
244
245
246 /*************************************************************************
247 Handler for mouse button down events
248 *************************************************************************/
onMouseButtonDown(MouseEventArgs & e)249 void Thumb::onMouseButtonDown(MouseEventArgs& e)
250 {
251 // default processing
252 PushButton::onMouseButtonDown(e);
253
254 if (e.button == LeftButton)
255 {
256 // initialise the dragging state
257 d_beingDragged = true;
258 d_dragPoint = CoordConverter::screenToWindow(*this, e.position);
259
260 // trigger tracking started event
261 WindowEventArgs args(this);
262 onThumbTrackStarted(args);
263
264 ++e.handled;
265 }
266
267 }
268
269
270 /*************************************************************************
271 Handler for event triggered when we lose capture of mouse input
272 *************************************************************************/
onCaptureLost(WindowEventArgs & e)273 void Thumb::onCaptureLost(WindowEventArgs& e)
274 {
275 // default handling
276 PushButton::onCaptureLost(e);
277
278 d_beingDragged = false;
279
280 // trigger tracking ended event
281 WindowEventArgs args(this);
282 onThumbTrackEnded(args);
283
284 // send notification whenever thumb is released
285 onThumbPositionChanged(args);
286 }
287
288
289 /*************************************************************************
290 Return a std::pair that describes the current range set for the
291 vertical movement.
292 *************************************************************************/
getVertRange(void) const293 std::pair<float, float> Thumb::getVertRange(void) const
294 {
295 return std::make_pair(d_vertMin, d_vertMax);
296 }
297
298
299 /*************************************************************************
300 Return a std::pair that describes the current range set for the
301 horizontal movement.
302 *************************************************************************/
getHorzRange(void) const303 std::pair<float, float> Thumb::getHorzRange(void) const
304 {
305 return std::make_pair(d_horzMin, d_horzMax);
306 }
307
308
309 /*************************************************************************
310 Add thumb specifiec properties
311 *************************************************************************/
addThumbProperties(void)312 void Thumb::addThumbProperties(void)
313 {
314 const String& propertyOrigin = WidgetTypeName;
315
316 CEGUI_DEFINE_PROPERTY(Thumb, bool,
317 "HotTracked", "Property to get/set the state of the state of the 'hot-tracked' setting for the thumb."
318 " Value is either \"true\" or \"false\".",
319 &Thumb::setHotTracked, &Thumb::isHotTracked, true
320 );
321
322 typedef std::pair<float,float> range;
323
324 CEGUI_DEFINE_PROPERTY(Thumb, range,
325 "VertRange", "Property to get/set the vertical movement range for the thumb. Value is \"min:[float] max:[float]\".",
326 &Thumb::setVertRange, &Thumb::getVertRange, range(0.0f, 1.0f)
327 );
328
329 CEGUI_DEFINE_PROPERTY(Thumb, range,
330 "HorzRange", "Property to get/set the horizontal movement range for the thumb. Value is \"min:[float] max:[float]\".",
331 &Thumb::setHorzRange, &Thumb::getHorzRange, range(0.0f, 1.0f)
332 );
333
334 CEGUI_DEFINE_PROPERTY(Thumb, bool,
335 "VertFree", "Property to get/set the state the setting to free the thumb vertically. Value is either \"true\" or \"false\".",
336 &Thumb::setVertFree, &Thumb::isVertFree, false
337 );
338
339 CEGUI_DEFINE_PROPERTY(Thumb, bool,
340 "HorzFree", "Property to get/set the state the setting to free the thumb horizontally. Value is either \"true\" or \"false\".",
341 &Thumb::setHorzFree, &Thumb::isHorzFree, false
342 );
343 }
344
345 //----------------------------------------------------------------------------//
banPropertiesForAutoWindow()346 void Thumb::banPropertiesForAutoWindow()
347 {
348 PushButton::banPropertiesForAutoWindow();
349
350 banPropertyFromXML("VertRange");
351 banPropertyFromXML("HorzRange");
352 banPropertyFromXML("VertFree");
353 banPropertyFromXML("HorzFree");
354 }
355
356 //----------------------------------------------------------------------------//
357
358 } // End of CEGUI namespace section
359