Vegastrike 0.5.1 rc1  1.0
Original sources for Vegastrike Evolved
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Macros Groups Pages
in_kb.cpp
Go to the documentation of this file.
1 /*
2  * Vega Strike
3  * Copyright (C) 2001-2002 Daniel Horn
4  *
5  * http://vegastrike.sourceforge.net/
6  *
7  * This program is free software; you can redistribute it and/or
8  * modify it under the terms of the GNU General Public License
9  * as published by the Free Software Foundation; either version 2
10  * of the License, or (at your option) any later version.
11  *
12  * This program is distributed in the hope that it will be useful,
13  * but WITHOUT ANY WARRANTY; without even the implied warranty of
14  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15  * GNU General Public License for more details.
16  *
17  * You should have received a copy of the GNU General Public License
18  * along with this program; if not, write to the Free Software
19  * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
20  */
21 
22 #include <queue>
23 #include <list>
24 #include "vegastrike.h"
25 #include "vs_globals.h"
26 #include "in_kb.h"
27 #include "in_handler.h"
28 #include "gldrv/winsys.h"
29 #include "in_kb_data.h"
30 
31 static void DefaultKBHandler( const KBData&, KBSTATE newState ) // FIXME ?
32 {
33  //do nothing
34 }
36 {
37  KBHandler function;
40  {
41  function = DefaultKBHandler;
42  }
43 };
45 static unsigned int playerBindings[LAST_MODIFIER][WSK_LAST];
47 
48 static void kbGetInput( int key, int modifiers, bool release, int x, int y )
49 {
51  if (key < 0 || key >= WSK_LAST)
52  return;
53  int i = _Universe->CurrentCockpit();
54  _Universe->SetActiveCockpit( playerBindings[modifiers][key] );
55  if ( (keyState[modifiers][key] == RESET || keyState[modifiers][key] == UP) && !release )
56  keyBindings[modifiers][key].function( keyBindings[modifiers][key].data, PRESS );
57  if ( (keyState[modifiers][key] == DOWN || keyState[modifiers][key] == RESET) && release )
58  keyBindings[modifiers][key].function( keyBindings[modifiers][key].data, RELEASE );
59  keyState[modifiers][key] = release ? UP : DOWN;
61 }
62 
63 static bool kbHasBinding( int key, int modifiers )
64 {
65  static HandlerCall defaultHandler;
66  return keyBindings[modifiers][key].function != defaultHandler.function;
67 }
68 
69 static const char _lomap[] = "0123456789-=\';/.,`\\";
70 static const char _himap[] = ")!@#$%^&*(_+\":?><~|";
71 
72 int shiftup( int ch )
73 {
74  if ( ch == (ch&0xFF) ) {
75  const char *c = strchr( _lomap, ch );
76  if (c)
77  return _himap[c-_lomap];
78 
79  else
80  return toupper( ch );
81  } else {return ch; }}
82 
83 int shiftdown( int ch )
84 {
85  if ( ch == (ch&0xFF) ) {
86  const char *c = strchr( _himap, ch );
87  if (c)
88  return _lomap[c-_himap];
89 
90  else
91  return tolower( ch );
92  } else {return ch; }}
93 
94 static unsigned int _activeModifiers = 0;
95 
96 void setActiveModifiers( unsigned int mask )
97 {
98  _activeModifiers = mask;
99 }
100 #ifdef SDL_WINDOWING
101 void setActiveModifiersSDL( SDLMod mask )
102 {
104  ( ( mask&(KMOD_LSHIFT|KMOD_RSHIFT) ) ? KB_MOD_SHIFT : 0 )
105  |( ( mask&(KMOD_LCTRL|KMOD_RCTRL) ) ? KB_MOD_CTRL : 0 )
106  |( ( mask&(KMOD_LALT|KMOD_RALT) ) ? KB_MOD_ALT : 0 ) );
107 }
108 #endif
109 unsigned int getActiveModifiers()
110 {
111  return _activeModifiers;
112 }
113 unsigned int pullActiveModifiers()
114 {
115 #ifdef SDL_WINDOWING
116  setActiveModifiersSDL( SDL_GetModState() );
117 #endif
118  return getActiveModifiers();
119 }
120 unsigned int getModifier( const char *mod_name )
121 {
122  if (mod_name[0] == '\0')
123  return 0;
124  unsigned int rv = 0;
125  if ( strstr( mod_name, "shift" ) || strstr( mod_name, "uppercase" ) || strstr( mod_name, "caps" ) )
126  rv |= KB_MOD_SHIFT;
127  if ( strstr( mod_name, "ctrl" ) || strstr( mod_name, "cntrl" ) || strstr( mod_name, "control" ) )
128  rv |= KB_MOD_CTRL;
129  if ( strstr( mod_name, "alt" ) || strstr( mod_name, "alternate" ) )
130  rv |= KB_MOD_ALT;
131  return rv;
132 }
133 int getModifier( bool alton, bool cntrlon, bool shifton )
134 {
135  return cntrlon ? KB_MOD_CTRL : ( alton ? KB_MOD_ALT : (shifton ? KB_MOD_SHIFT : 0) );
136 }
137 void glut_keyboard_cb( unsigned int ch, unsigned int mod, bool release, int x, int y )
138 {
139  bool shifton = false;
140  int alton = false;
141  int ctrlon = false;
142 
143  unsigned int modmask = KB_MOD_MASK;
144  if ( ( WSK_MOD_LSHIFT == (mod&WSK_MOD_LSHIFT) ) || ( WSK_MOD_RSHIFT == (mod&WSK_MOD_RSHIFT) ) ) {
145  //This is ugly, but we have to support legacy config files...
146  //...maybe add config option to disable this soooo ugly thing...
147  if ( !kbHasBinding( ch, KB_MOD_SHIFT ) ) {
148  ch = shiftup( ch );
149  modmask &= ~KB_MOD_SHIFT;
150  }
151  shifton = true;
152  }
153  if ( ( WSK_MOD_LALT == (mod&WSK_MOD_LALT) ) || ( WSK_MOD_RALT == (mod&WSK_MOD_RALT) ) )
154  alton = true;
155  if ( ( WSK_MOD_LCTRL == (mod&WSK_MOD_LCTRL) ) || ( WSK_MOD_RCTRL == (mod&WSK_MOD_RCTRL) ) )
156  ctrlon = true;
157  //Polling state
159  (shifton ? KB_MOD_SHIFT : 0)
160  |(alton ? KB_MOD_ALT : 0)
161  |(ctrlon ? KB_MOD_CTRL : 0) );
162 
163  int curmod = getModifier( alton, ctrlon, shifton )&modmask;
164  kbGetInput( ch, curmod, release, x, y );
165  if (release) {
166  for (int i = 0; i < LAST_MODIFIER; ++i) {
167  if (i != curmod) {
168  if (keyState[i][shiftdown( ch )] == DOWN)
169  kbGetInput( shiftdown( ch ), i, release, x, y );
170  if (keyState[i][shiftup( ch )] == DOWN)
171  kbGetInput( shiftup( ch ), i, release, x, y );
172  } else {
173  if (shifton) {
174  if ( ( (unsigned int) shiftdown( ch ) ) != ch && keyState[i][shiftdown( ch )] == DOWN )
175  kbGetInput( shiftdown( ch ), i, release, x, y );
176  } else if ( ( (unsigned int) shiftup( ch ) ) != ch && keyState[i][shiftup( ch )] == DOWN ) {
177  kbGetInput( shiftup( ch ), i, release, x, y );
178  }
179  }
180  }
181  }
182 }
183 
184 void RestoreKB()
185 {
186  for (int i = 0; i < LAST_MODIFIER; ++i)
187  for (int a = 0; a < KEYMAP_SIZE; a++)
188  if (keyState[i][a] == DOWN) {
189  keyBindings[i][a].function( keyBindings[i][a].data, RELEASE );
190  keyState[i][a] = UP;
191  }
193 }
194 
195 void InitKB()
196 {
197  for (int i = 0; i < LAST_MODIFIER; ++i)
198  for (int a = 0; a < KEYMAP_SIZE; a++) {
199  keyState[i][a] = UP;
200  UnbindKey( a, i );
201  }
202  RestoreKB();
203 }
204 
205 void ProcessKB( unsigned int player )
206 {
207  for (int mod = 0; mod < LAST_MODIFIER; mod++)
208  for (int a = 0; a < KEYMAP_SIZE; a++)
209  if (playerBindings[mod][a] == player)
210  keyBindings[mod][a].function( keyBindings[mod][a].data, keyState[mod][a] );
211 }
212 
213 void BindKey( int key, unsigned int mod, unsigned int player, KBHandler handler, const KBData &data )
214 {
215  keyBindings[mod][key].function = handler;
216  keyBindings[mod][key].data = data;
217  playerBindings[mod][key] = player;
218  handler( std::string(), RESET ); //key is not used in handler
219 }
220 
221 void UnbindKey( int key, unsigned int mod )
222 {
223  keyBindings[mod][key] = HandlerCall();
224 }
225