Planet
navi homePPSaboutscreenshotsdownloaddevelopmentforum

source: orxonox.OLD/orxonox/trunk/src/lib/event/event_handler.cc @ 4782

Last change on this file since 4782 was 4782, checked in by bensch, 19 years ago

orxonox/trunk: orxonox-events registered, solved an error in ClassList

File size: 7.4 KB
Line 
1/*
2   orxonox - the future of 3D-vertical-scrollers
3
4   Copyright (C) 2004 orx
5
6   This program is free software; you can redistribute it and/or modify
7   it under the terms of the GNU General Public License as published by
8   the Free Software Foundation; either version 2, or (at your option)
9   any later version.
10
11   ### File Specific:
12   main-programmer: Patrick Boenzli
13   co-programmer:
14*/
15
16#define DEBUG_SPECIAL_MODULE DEBUG_MODULE_EVENT
17
18#include "event_handler.h"
19
20#include "event_listener.h"
21#include "event.h"
22#include "key_mapper.h"
23
24#include "compiler.h"
25#include "debug.h"
26
27using namespace std;
28
29
30/**
31   \brief standard constructor
32*/
33EventHandler::EventHandler ()
34{
35  this->setClassID(CL_EVENT_HANDLER, "EventHandler");
36
37  this->listeners = new EventListener**[ES_NUMBER];
38  for(int i = 0; i < ES_NUMBER; ++i)
39    this->listeners[i] = new EventListener*[EV_NUMBER];
40
41  /* now initialize them all to zero */
42  for(int i = 0; i < ES_NUMBER; ++i)
43    {
44      for(int j = 0; j < SDLK_LAST; ++j)
45        {
46          this->listeners[i][j] = NULL;
47        }
48    }
49  this->state = ES_GAME;
50}
51
52
53/**
54   \brief the singleton reference to this class
55*/
56EventHandler* EventHandler::singletonRef = NULL;
57
58
59/**
60   \brief standard deconstructor
61
62*/
63EventHandler::~EventHandler ()
64{
65  EventHandler::singletonRef = NULL;
66  delete this->keyMapper;
67}
68
69
70/**
71   \brief initializes the event handler
72
73   this has to be called before the use of the event handler
74*/
75void EventHandler::init()
76{
77  this->keyMapper = new KeyMapper();
78  this->keyMapper->loadKeyBindings();
79}
80
81
82/**
83   \brief set the state of the event handler
84   \param state: to which the event handler shall change
85*/
86void EventHandler::setState(elState state)
87{
88  this->state = state;
89}
90
91
92/**
93   \brief subscribe to an event
94   \param el: the event listener that wants to subscribe itself, the listener that will be called when the evetn occures
95   \param state: for which the listener wants to receive events
96   \param eventType: the event type that wants to be listened for.
97
98   This is one of the most important function of the EventHandler. If you would like to subscribe for more
99   than one state, you have to subscribe for each state again. If you want to subscribe for all states, use
100   state = ES_ALL, which will subscribe your listener for all states together.
101 *
102 * \todo this can also be done with the & operator, and checking for states, just set the esState to 1,2,4,8, and then 15 is equal to ES_ALL
103*/
104void EventHandler::subscribe(EventListener* el, elState state, int eventType)
105{
106  PRINTF(4)("Subscribing event type: %i\n", eventType);
107  if( state == ES_ALL )
108    {
109      for(int i = 0; i < ES_NUMBER; ++i)
110        if( likely(this->listeners[state][eventType] == NULL))
111          this->listeners[i][eventType] = el;
112        else
113          PRINTF(1)("%s of class %s tried to subscribe to event %i @ state %i but this event has already been subscribed\n", el->getName(), el->getClassName(), eventType, state);
114    }
115  else
116    if( likely(this->listeners[state][eventType] == NULL))
117      {
118        this->listeners[state][eventType] = el;
119      }
120    else
121      PRINTF(1)("% of class %s tried to subscribe to event %i @ state %i but this event has already been subscribed\n", el->getName(), el->getClassName(), eventType, state);
122}
123
124
125/**
126   \brief unsubscribe from the EventHandler
127   \param state: the stat in which it has been subscribed
128   \param eventType: the event, that shall be unsubscribed
129
130   if you want to unsubscribe an event listener from all subscribed events, just use the
131   unsubscribe(EventListener* el, elState state) function
132*/
133void EventHandler::unsubscribe(elState state, int eventType)
134{
135  PRINTF(4)("Unsubscribing event type nr: %i\n", eventType);
136  this->listeners[state][eventType] = NULL;
137}
138
139
140/**
141   \brief unsubscribe all events from a specific listener
142   \param el: the listener that wants to unsubscribe itself
143   \param state: the state in which the events shall be unsubscribed
144
145*/
146void EventHandler::unsubscribe(EventListener* el, elState state)
147{
148  if( state == ES_ALL)
149    {
150      for(int i = 0; i < ES_NUMBER; ++i)
151        {
152          for(int j = 0; j < EV_NUMBER; ++j)
153            {
154              if( this->listeners[i][j] == el )
155                this->listeners[i][j] = NULL;
156            }
157        }
158    }
159  else
160    {
161      for(int j = 0; j < EV_NUMBER; ++j)
162        {
163          if( this->listeners[state][j] == el )
164            this->listeners[state][j] = NULL;
165        }
166    }
167}
168
169
170/**
171   \brief flush all registered events
172   \param state: a specific state
173*/
174void EventHandler::flush(elState state)
175{
176  if( state == ES_ALL)
177    {
178      for(int i = 0; i < ES_NUMBER; ++i)
179        {
180          for(int j = 0; j < EV_NUMBER; ++j)
181            {
182              this->listeners[i][j] = NULL;
183            }
184        }
185    }
186  else
187    {
188      for(int j = 0; j < EV_NUMBER; ++j)
189        {
190          this->listeners[state][j] = NULL;
191        }
192    }
193}
194
195
196/**
197   \brief core function of event handler: receives all events from SDL
198
199   The event from the SDL framework are collected here and distributed to all listeners.
200*/
201void EventHandler::process()
202{
203  SDL_Event event;
204  Event ev;
205  EventListener* listener = NULL;
206  while( SDL_PollEvent (&event))
207    {
208      switch( event.type)
209        {
210        case SDL_KEYDOWN:
211          ev.bPressed = true;
212          ev.type = event.key.keysym.sym;
213          break;
214        case SDL_KEYUP:
215          ev.bPressed = false;
216          ev.type = event.key.keysym.sym;
217          break;
218        case SDL_MOUSEMOTION:
219          ev.bPressed = false;
220          ev.type = EV_MOUSE_MOTION;
221          ev.x = event.motion.x;
222          ev.y = event.motion.y;
223          ev.xRel = event.motion.xrel;
224          ev.yRel = event.motion.yrel;
225          break;
226        case SDL_MOUSEBUTTONUP:
227          ev.bPressed = false;
228          ev.type = event.button.button + SDLK_LAST;
229          break;
230        case SDL_MOUSEBUTTONDOWN:
231          ev.bPressed = true;
232          ev.type = event.button.button + SDLK_LAST;
233          break;
234        case SDL_JOYAXISMOTION:
235          ev.bPressed = false;
236          ev.type = EV_JOY_AXIS_MOTION;
237          break;
238        case SDL_JOYBALLMOTION:
239          ev.bPressed = false;
240          ev.type = EV_JOY_BALL_MOTION;
241          break;
242        case SDL_JOYHATMOTION:
243          ev.bPressed = false;
244          ev.type = EV_JOY_HAT_MOTION;
245          break;
246        case SDL_JOYBUTTONDOWN:
247          ev.bPressed = true;
248          ev.type = EV_JOY_BUTTON;
249          break;
250        case SDL_JOYBUTTONUP:
251          ev.bPressed = true;
252          ev.type = EV_JOY_BUTTON;
253          break;
254        case SDL_VIDEORESIZE:
255          ev.resize = event.resize;
256          break;
257        default:
258          ev.type = EV_UNKNOWN;
259          break;
260        }
261
262      /* small debug routine: shows all events dispatched by the event handler */
263      PRINT(4)("\n==========================| EventHandler::process () |===\n");
264      PRINT(4)("=  Got Event nr %i, for state %i", ev.type, this->state);
265
266      listener = this->listeners[this->state][ev.type];
267      if( listener != NULL)
268        {
269          PRINT(4)("=  Event dispatcher msg: This event has been consumed\n");
270          PRINT(4)("=======================================================\n");
271          listener->process(ev);
272        }
273      else
274        {
275          PRINT(4)("=  Event dispatcher msg: This event has NOT been consumed\n");
276          PRINT(4)("=======================================================\n");
277        }
278    }
279}
280
Note: See TracBrowser for help on using the repository browser.