OSG  3.4.0
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Macros Pages
EventInterface.h
Go to the documentation of this file.
1 /* -*-c++-*- OpenSceneGraph - Copyright (C) 1998-2008 Robert Osfield
2  *
3  * This library is open source and may be redistributed and/or modified under
4  * the terms of the OpenSceneGraph Public License (OSGPL) version 0.0 or
5  * (at your option) any later version. The full license is in LICENSE file
6  * included with this distribution, and on the openscenegraph.org website.
7  *
8  * This library is distributed in the hope that it will be useful,
9  * but WITHOUT ANY WARRANTY; without even the implied warranty of
10  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
11  * OpenSceneGraph Public License for more details.
12 */
13 
14 // Code by: Jeremy Moles (cubicool) 2007-2008
15 
16 #ifndef OSGWIDGET_EVENT_INTERFACE
17 #define OSGWIDGET_EVENT_INTERFACE
18 
19 #include <list>
20 #include <osg/ref_ptr>
21 #include <osg/observer_ptr>
22 #include <osg/Referenced>
23 
24 #include <osgWidget/Export>
25 
26 namespace osgWidget {
27 
28 class WindowManager;
29 class Window;
30 class Widget;
31 
33 {
34  EVENT_NONE = 0x0000,
35  EVENT_FOCUS = 0x0001,
36  EVENT_UNFOCUS = 0x0002,
38  EVENT_MOUSE_OVER = 0x0008,
40  EVENT_MOUSE_DRAG = 0x0020,
41  EVENT_MOUSE_PUSH = 0x0040,
44  EVENT_KEY_DOWN = 0x0200,
45  EVENT_KEY_UP = 0x0400,
46  EVENT_ALL = 0xFFFF
47 };
48 
49 // Helpful wrapper around using the raw types, since it often doesn't make sense to
50 // use some without the others.
52 {
58 };
59 
61 {
62  public:
64  double x;
65  double y;
66  int key;
67  int keyMask;
68 
70  type (_type),
71  x (0.0f),
72  y (0.0f),
73  key (-1),
74  keyMask (-1),
75  _wm (wm),
76  _window (0),
77  _widget (0),
78  _data (0) {
79  }
80 
82  if(_type != EVENT_NONE) type = _type;
83 
84  return *this;
85  }
86 
87  Event& makeMouse(double _x, double _y, EventType _type = EVENT_NONE) {
88  x = _x;
89  y = _y;
90 
91  if(_type != EVENT_NONE) type = _type;
92 
93  return *this;
94  }
95 
96  Event& makeKey(int _key, int _keyMask, EventType _type = EVENT_NONE) {
97  key = _key;
98  keyMask = _keyMask;
99 
100  if(_type != EVENT_NONE) type = _type;
101 
102  return *this;
103  }
104 
105  WindowManager* getWindowManager() { return _wm; }
106 
108  return _wm;
109  }
110 
112  return _window;
113  }
114 
115  const Window* getWindow() const {
116  return _window;
117  }
118 
120  return _widget;
121  }
122 
123  const Widget* getWidget() const {
124  return _widget;
125  }
126 
127  void* getData() {
128  return _data;
129  }
130 
131  const void* getData() const {
132  return _data;
133  }
134 
135  void setData(void* data) {
136  _data = data;
137  }
138 
139  protected:
140 
141  friend class WindowManager;
142  friend class Window;
143 
147  void* _data;
148 
149 };
150 
151 // The Callback interface was inspired by the CEGUI project:
152 //
153 // http://www.cegui.org.uk/wiki/index.php/Main_Page
154 //
155 // It's a great little way to cleanly implement callbacks for events, although
156 // I did change the names a bit to make them more appropriate for OSG. MANY THANKS
157 // to the CEGUI project!
158 
159 // The CallbackInterface, which the highest-level functor keeps a pointer to.
161 {
162  virtual ~CallbackInterface() {}
163 
164  virtual const char* className() const { return "osgWidget::CallbackInterface"; }
165 
166  virtual bool operator()(Event&) = 0;
167 };
168 
169 // The object that facilitates a class method as a callback.
170 template<typename T>
172 {
173  public:
174  typedef bool (T::*ObjectCallbackType)(Event&);
175 
177  _object (obj),
178  _callback (callback) {}
179 
180  virtual bool operator()(Event& ev) {
181  return (_object->*_callback)(ev);
182  }
183 
184  private:
185  T* _object;
186  ObjectCallbackType _callback;
187 };
188 
189 // The object that facilitates general functions as callbacks.
190 template<typename T>
192 {
193  public:
194  FunctionCallback(T* callback):
195  _callback(callback) {
196  }
197 
198  virtual bool operator()(Event& ev) {
199  return (*_callback)(ev);
200  }
201  protected:
203 };
204 
205 // The highlevel functor.
207 {
208  public:
209  Callback(): _type(EVENT_NONE), _data(0), _callback(0) {}
210  Callback(const Callback& rhs): osg::Referenced(rhs), _type(rhs._type), _data(rhs._data), _callback(rhs._callback) {}
211 
212  virtual const char* className() const { return "osgWidget::Callback"; }
213 
214  // The more traditional style of OSG Callbacks.
215  Callback(EventType type, void* data=0):
216  _type (type),
217  _data (data),
218  _callback (0) {
219  }
220 
221  // Creates a Callback that is bound to a member function.
222  template<typename T>
223  Callback(bool (T::*function)(Event&), T* obj, EventType type, void* data=0):
224  _type (type),
225  _data (data),
226  _callback (new ObjectCallback<T>(function, obj)) {
227  }
228 
229  // Creates a Callback that is bound to a functor pointer.
230  template<typename T>
231  Callback(T* functor, EventType type, void* data=0):
232  _type (type),
233  _data (data),
234  _callback (new FunctionCallback<T>(functor)) {
235  }
236 
237  virtual ~Callback() {}
238 
239  virtual bool operator()(Event& ev) {
240  if(!_callback) return false;
241 
242  return (*_callback)(ev);
243  }
244 
245  EventType getType() const {
246  return _type;
247  }
248 
249  void* getData() {
250  return _data;
251  }
252 
253  const void* getData() const {
254  return _data;
255  }
256 
257  protected:
259  void* _data;
260 
261  // We use a ref_ptr here so that we don't have to worry about memory.
263 
264 };
265 
266 
268 {
269  public:
270  EventInterface(): _eventMask(EVENT_NONE) {}
271 
273  _eventMask (ei._eventMask),
274  _callbacks (ei._callbacks) {}
275 
276  virtual ~EventInterface() {}
277 
278  // These functions take as their final argument the WindowManager which issued the
279  // request. This is sometimes useful to get information about key state, etc.
280 
281  // Notify the EventInterface object that is has been focused or unfocused; since
282  // this isn't always bound to a mouse event (i.e., if you want to be able to use
283  // the TAB key to focus), we need separate events here.
284  virtual bool focus (const WindowManager*) { return false; }
285  virtual bool unfocus (const WindowManager*) { return false; }
286 
287  // Mouse events, pretty self-explanatory.
288  virtual bool mouseEnter (double, double, const WindowManager*) { return false; }
289  virtual bool mouseOver (double, double, const WindowManager*) { return false; }
290  virtual bool mouseLeave (double, double, const WindowManager*) { return false; }
291  virtual bool mouseDrag (double, double, const WindowManager*) { return false; }
292  virtual bool mousePush (double, double, const WindowManager*) { return false; }
293  virtual bool mouseRelease (double, double, const WindowManager*) { return false; }
294  virtual bool mouseScroll (double, double, const WindowManager*) { return false; }
295 
296  // These functions pass the osgGA::GUIEventAdapter::KeySymbol and KeyModMask and,
297  // as above, the WindowManager.
298  virtual bool keyDown (int, int, const WindowManager*) { return false; }
299  virtual bool keyUp (int, int, const WindowManager*) { return false; }
300 
301  void setEventMask(unsigned int mask) {
302  _eventMask = mask;
303  }
304 
305  void addEventMask(unsigned int mask) {
306  _eventMask |= mask;
307  }
308 
309  void removeEventMask(unsigned int mask) {
310  _eventMask ^= mask;
311  }
312 
313  unsigned int getEventMask() const {
314  return _eventMask;
315  }
316 
317  typedef std::list<osg::ref_ptr<Callback> > CallbackList;
318 
319  inline CallbackList& getCallbacks() { return _callbacks; }
320  inline const CallbackList& getCallbacks() const { return _callbacks; }
321 
322  void addCallback(Callback* cb) {
323  _callbacks.push_back(cb);
324  }
325 
326  bool callCallbacks(Event& ev) {
327  if(ev.type == EVENT_NONE || !(_eventMask & ev.type)) return false;
328 
329  for(CallbackList::iterator i = _callbacks.begin(); i != _callbacks.end(); i++) {
330  // This is the OLD method; testing a new method below.
331  // if(i->getType() == ev.type && (*i)(ev)) return true;
332 
333  if(i->get()->getType() & ev.type) {
334  ev.setData(i->get()->getData());
335 
336  if((*i->get())(ev)) return true;
337  }
338  }
339 
340  return false;
341  }
342 
344  if(ev.type == EVENT_NONE || !(_eventMask & ev.type)) return false;
345 
346  bool handled = false;
347 
348  if(ev.type == EVENT_FOCUS) handled = focus(ev.getWindowManager());
349 
350  else if(ev.type == EVENT_UNFOCUS) handled = unfocus(ev.getWindowManager());
351 
352  else if(ev.type == EVENT_MOUSE_ENTER)
353  handled = mouseEnter(ev.x, ev.y, ev.getWindowManager())
354  ;
355 
356  else if(ev.type == EVENT_MOUSE_OVER)
357  handled = mouseOver(ev.x, ev.y, ev.getWindowManager())
358  ;
359 
360  else if(ev.type == EVENT_MOUSE_LEAVE)
361  handled = mouseLeave(ev.x, ev.y, ev.getWindowManager())
362  ;
363 
364  else if(ev.type == EVENT_MOUSE_DRAG)
365  handled = mouseDrag(ev.x, ev.y, ev.getWindowManager())
366  ;
367 
368  else if(ev.type == EVENT_MOUSE_PUSH)
369  handled = mousePush(ev.x, ev.y, ev.getWindowManager())
370  ;
371 
372  else if(ev.type == EVENT_MOUSE_RELEASE)
373  handled = mouseRelease(ev.x, ev.y, ev.getWindowManager())
374  ;
375 
376  else if(ev.type == EVENT_MOUSE_SCROLL)
377  handled = mouseScroll(ev.x, ev.y, ev.getWindowManager())
378  ;
379 
380  else if(ev.type == EVENT_KEY_DOWN)
381  handled = keyDown(ev.key, ev.keyMask, ev.getWindowManager())
382  ;
383 
384  else if(ev.type == EVENT_KEY_UP)
385  handled = keyUp(ev.key, ev.keyMask, ev.getWindowManager())
386  ;
387 
388  else return false;
389 
390  return callCallbacks(ev) || handled;
391  }
392 
393  bool canFocus () const { return (_eventMask & EVENT_FOCUS) != 0; }
394  bool canUnfocus () const { return (_eventMask & EVENT_UNFOCUS) != 0; }
395 
396  bool canMouseEnter () const { return (_eventMask & EVENT_MOUSE_ENTER) != 0; }
397  bool canMouseOver () const { return (_eventMask & EVENT_MOUSE_OVER) != 0; }
398  bool canMouseLeave () const { return (_eventMask & EVENT_MOUSE_LEAVE) != 0; }
399  bool canMouseDrag () const { return (_eventMask & EVENT_MOUSE_DRAG) != 0; }
400  bool canMousePush () const { return (_eventMask & EVENT_MOUSE_PUSH) != 0; }
401  bool canMouseRelease () const { return (_eventMask & EVENT_MOUSE_RELEASE) != 0; }
402  bool canMouseScroll () const { return (_eventMask & EVENT_MOUSE_SCROLL) != 0; }
403 
404  bool canKeyDown () const { return (_eventMask & EVENT_KEY_DOWN) != 0; }
405  bool canKeyUp () const { return (_eventMask & EVENT_KEY_UP) != 0; }
406 
407  private:
408 
409  unsigned int _eventMask;
410  CallbackList _callbacks;
411 
412 };
413 
414 }
415 
416 #endif
Event & makeType(EventType _type)
Widget * getWidget()
virtual bool mouseScroll(double, double, const WindowManager *)
Window * getWindow()
bool(T::* ObjectCallbackType)(Event &)
virtual bool mouseOver(double, double, const WindowManager *)
const void * getData() const
virtual bool mouseRelease(double, double, const WindowManager *)
CallbackList & getCallbacks()
virtual bool keyDown(int, int, const WindowManager *)
Event & makeKey(int _key, int _keyMask, EventType _type=EVENT_NONE)
Event(WindowManager *wm, EventType _type=EVENT_NONE)
const Window * getWindow() const
virtual bool keyUp(int, int, const WindowManager *)
ObjectCallback(ObjectCallbackType callback, T *obj)
const WindowManager * getWindowManager() const
Definition: Box.h:21
#define OSGWIDGET_EXPORT
Definition: Export.h:42
EventType getType() const
Callback(T *functor, EventType type, void *data=0)
osg::ref_ptr< CallbackInterface > _callback
EventInterface(const EventInterface &ei)
virtual bool operator()(Event &)=0
const CallbackList & getCallbacks() const
unsigned int getEventMask() const
virtual bool mouseDrag(double, double, const WindowManager *)
WindowManager * _wm
virtual const char * className() const
WindowManager * getWindowManager()
virtual bool focus(const WindowManager *)
std::list< osg::ref_ptr< Callback > > CallbackList
void addCallback(Callback *cb)
virtual bool mousePush(double, double, const WindowManager *)
virtual bool mouseEnter(double, double, const WindowManager *)
void addEventMask(unsigned int mask)
virtual bool unfocus(const WindowManager *)
virtual bool operator()(Event &ev)
virtual bool mouseLeave(double, double, const WindowManager *)
Callback(bool(T::*function)(Event &), T *obj, EventType type, void *data=0)
void setEventMask(unsigned int mask)
void removeEventMask(unsigned int mask)
Event & makeMouse(double _x, double _y, EventType _type=EVENT_NONE)
GLint GLenum GLsizei GLsizei GLsizei GLint GLenum GLenum type
Definition: GLU.h:71
void setData(void *data)
virtual bool operator()(Event &ev)
virtual bool operator()(Event &ev)
const void * getData() const
const Widget * getWidget() const
Definition: AlphaFunc.h:19
bool callMethodAndCallbacks(Event &ev)
Callback(EventType type, void *data=0)
Callback(const Callback &rhs)
bool callCallbacks(Event &ev)
virtual const char * className() const