00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019 #include "pent_include.h"
00020 #include "HIDManager.h"
00021
00022 #include "SDL_timer.h"
00023 #include "SettingManager.h"
00024 #include "Console.h"
00025 #include "util.h"
00026
00027 #include "ConfigFileManager.h"
00028
00029 HIDManager* HIDManager::hidmanager = 0;
00030
00031 HIDManager::HIDManager()
00032 {
00033 con.Print(MM_INFO, "Creating HIDManager...\n");
00034
00035 assert(hidmanager == 0);
00036 hidmanager = this;
00037
00038 InitJoystick();
00039
00040 resetBindings();
00041 double_timeout = 200;
00042 }
00043
00044 HIDManager::~HIDManager()
00045 {
00046 std::vector<Console::ArgvType *>::iterator it;
00047 con.Print(MM_INFO, "Destroying HIDManager...\n");
00048
00049 for (it = commands.begin(); it != commands.end(); ++it)
00050 {
00051 if (*it)
00052 {
00053 delete *it;
00054 }
00055 }
00056 commands.clear();
00057
00058 ShutdownJoystick();
00059 hidmanager = 0;
00060 }
00061
00062 bool HIDManager::handleEvent(const SDL_Event & event)
00063 {
00064 bool handled = false;
00065 HID_Key key = HID_LAST;
00066 HID_Event evn = HID_EVENT_LAST;
00067 Console::ArgvType * command = 0;
00068 switch (event.type) {
00069 case SDL_KEYDOWN:
00070 key = HID_translateSDLKey(event.key.keysym.sym);
00071 evn = HID_EVENT_DEPRESS;
00072 break;
00073 case SDL_KEYUP:
00074 key = HID_translateSDLKey(event.key.keysym.sym);
00075 evn = HID_EVENT_RELEASE;
00076 break;
00077 case SDL_MOUSEBUTTONDOWN:
00078 key = HID_translateSDLMouseButton(event.button.button);
00079 evn = HID_EVENT_DEPRESS;
00080 break;
00081 case SDL_MOUSEBUTTONUP:
00082 key = HID_translateSDLMouseButton(event.button.button);
00083 evn = HID_EVENT_RELEASE;
00084 break;
00085 case SDL_JOYBUTTONDOWN:
00086 key = HID_translateSDLJoystickButton(event.jbutton.button);
00087 evn = HID_EVENT_DEPRESS;
00088 break;
00089 case SDL_JOYBUTTONUP:
00090 key = HID_translateSDLJoystickButton(event.jbutton.button);
00091 evn = HID_EVENT_RELEASE;
00092 break;
00093 }
00094
00095 if (key < HID_LAST && evn < HID_EVENT_LAST)
00096 {
00097 command = bindings[key][evn];
00098 }
00099
00100 if (command)
00101 {
00102 con.ExecuteConsoleCommand(*command);
00103 handled = true;
00104 }
00105
00106
00107 if (key < HID_LAST && evn == HID_EVENT_DEPRESS )
00108 {
00109 uint32 now = SDL_GetTicks();
00110 if (now - lastDown[key] < double_timeout &&
00111 lastDown[key] != 0)
00112 {
00113 lastDown[key] = 0;
00114 command = bindings[key][HID_EVENT_DOUBLE];
00115 if (command)
00116 {
00117 con.ExecuteConsoleCommand(*command);
00118 handled = true;
00119 }
00120 }
00121 else
00122 {
00123 lastDown[key] = now;
00124 }
00125 }
00126
00127 return handled;
00128 }
00129
00130 void HIDManager::handleDelayedEvents()
00131 {
00132 uint16 key;
00133 uint32 now = SDL_GetTicks();
00134 Console::ArgvType * command = 0;
00135
00136 for (key=0; key < HID_LAST; ++key)
00137 {
00138 if (now - lastDown[key] > double_timeout &&
00139 lastDown[key] != 0)
00140 {
00141 lastDown[key] = 0;
00142 command = bindings[key][HID_EVENT_CLICK];
00143 if (command)
00144 con.ExecuteConsoleCommand(*command);
00145 }
00146 }
00147 }
00148
00149 void HIDManager::resetBindings()
00150 {
00151 uint16 key, event;
00152 Console::ArgvType * cmd;
00153 std::vector<Console::ArgvType *>::iterator it;
00154
00155 for (key=0; key < HID_LAST; ++key)
00156 {
00157 lastDown[key] = 0;
00158 for (event=0; event < HID_EVENT_LAST; ++event)
00159 {
00160 bindings[key][event]=0;
00161 }
00162 }
00163
00164 for (it = commands.begin(); it != commands.end(); ++it)
00165 {
00166 if (*it)
00167 {
00168 delete *it;
00169 }
00170 }
00171 commands.clear();
00172
00173 cmd = new Console::ArgvType;
00174 cmd->push_back("ConsoleGump::toggle");
00175 commands.push_back(cmd);
00176
00177 bindings[HID_BACKQUOTE][HID_EVENT_DEPRESS]= commands.back();
00178 bindings[HID_F5][HID_EVENT_DEPRESS]= commands.back();
00179 }
00180
00181 void HIDManager::loadBindings()
00182 {
00183 Console::ArgsType args;
00184 Console::ArgvType argv;
00185
00186 con.Print(MM_INFO, "Loading HIDBindings...\n");
00187
00188 SettingManager* settings = SettingManager::get_instance();
00189 std::map<Pentagram::istring, std::string> keys;
00190 keys = settings->listDataValues("keys");
00191
00192 std::map<Pentagram::istring, std::string>::iterator i = keys.begin();
00193 std::map<Pentagram::istring, std::string>::iterator end = keys.end();
00194
00195 if (i == end)
00196 {
00197 con.Print(MM_INFO, "Loading default HIDBindings...\n");
00198 ConfigFileManager* config = ConfigFileManager::get_instance();
00199 keys = config->listKeyValues("bindings/bindings");
00200 i = keys.begin();
00201 end = keys.end();
00202 }
00203
00204 while (i != keys.end())
00205 {
00206 args = i->second.c_str();
00207 argv.clear();
00208
00209 Pentagram::StringToArgv(args, argv);
00210 bind(i->first, argv);
00211 ++i;
00212 }
00213 listBindings();
00214 }
00215
00216 void HIDManager::saveBindings()
00217 {
00218 uint16 key, event;
00219 SettingManager* settings = SettingManager::get_instance();
00220 Pentagram::istring section = "keys/";
00221 Pentagram::istring confkey;
00222
00223 for (key=0; key < HID_LAST; ++key)
00224 {
00225 for (event=0; event < HID_EVENT_LAST; ++event)
00226 {
00227 confkey = section +
00228 HID_GetEventName((HID_Event) event) +
00229 HID_GetKeyName((HID_Key) key);
00230 if (bindings[key][event])
00231 {
00232 Console::ArgsType command;
00233 Pentagram::ArgvToString(*bindings[key][event], command);
00234 settings->set(confkey, command);
00235 }
00236 else if (settings->exists(confkey))
00237 {
00238 settings->unset(confkey);
00239 }
00240 }
00241 }
00242 }
00243
00244 void HIDManager::bind(const Pentagram::istring& control, const Console::ArgvType& argv)
00245 {
00246 HID_Key key = HID_LAST;
00247 HID_Event event = HID_EVENT_DEPRESS;
00248 std::vector<Pentagram::istring> ctrl_argv;
00249 Console::ArgvType * command = 0;
00250
00251 if (! argv.empty())
00252 {
00253 std::vector<Console::ArgvType *>::iterator it;
00254 for (it = commands.begin(); it != commands.end(); ++it)
00255 {
00256 if (argv == (**it))
00257 {
00258
00259 command = *it;
00260 break;
00261 }
00262 }
00263
00264 if (!command)
00265 {
00266 command = new Console::ArgvType(argv);
00267 commands.push_back(command);
00268 }
00269 }
00270
00271 Pentagram::StringToArgv(control, ctrl_argv);
00272 if (ctrl_argv.size() == 1)
00273 {
00274 key = HID_GetKeyFromName(ctrl_argv[0]);
00275 }
00276 else if (ctrl_argv.size() > 1)
00277 {
00278 event = HID_GetEventFromName(ctrl_argv[0]);
00279 key = HID_GetKeyFromName(ctrl_argv[1]);
00280 }
00281
00282 if (event < HID_EVENT_LAST && key < HID_LAST && key != HID_BACKQUOTE)
00283 {
00284 bindings[key][event] = command;
00285 }
00286 else
00287 {
00288 pout << "Error: Cannot bind " << control << std::endl;
00289 }
00290 }
00291
00292 void HIDManager::unbind(const Pentagram::istring& control)
00293 {
00294
00295 Console::ArgvType command;
00296 bind(control, command);
00297 }
00298
00299 void HIDManager::ConCmd_bind(const Console::ArgvType &argv)
00300 {
00301 Console::ArgvType argv2;
00302 Console::ArgvType::const_iterator it;
00303 if (argv.size() < 3)
00304 {
00305 if (! argv.empty())
00306 pout << "Usage: " << argv[0] << " <key> <action> [<arg> ...]: binds a key or button to an action" << std::endl;
00307 return;
00308 }
00309 HIDManager * hidmanager = HIDManager::get_instance();
00310
00311 Pentagram::istring control(argv[1]);
00312
00313 it = argv.begin();
00314 ++it;
00315 ++it;
00316 argv2.assign(it, argv.end());
00317
00318 hidmanager->bind(control, argv2);
00319 }
00320
00321 void HIDManager::ConCmd_unbind(const Console::ArgvType &argv)
00322 {
00323 if (argv.size() != 2)
00324 {
00325 if (! argv.empty())
00326 pout << "Usage: " << argv[0] << " <key>: unbinds a key or button" << std::endl;
00327 return;
00328 }
00329 HIDManager * hidmanager = HIDManager::get_instance();
00330
00331 Pentagram::istring control(argv[1]);
00332
00333 hidmanager->unbind(control);
00334 }
00335
00336 void HIDManager::ConCmd_listbinds(const Console::ArgvType &argv)
00337 {
00338 HIDManager * hidmanager = HIDManager::get_instance();
00339 hidmanager->listBindings();
00340 }
00341
00342 void HIDManager::ConCmd_save(const Console::ArgvType &argv)
00343 {
00344 HIDManager * hidmanager = HIDManager::get_instance();
00345 hidmanager->saveBindings();
00346
00347 SettingManager* settings = SettingManager::get_instance();
00348 settings->write();
00349 }
00350
00351 void HIDManager::listBindings()
00352 {
00353 uint16 key, event;
00354 Console::ArgsType command;
00355
00356 for (key=0; key < HID_LAST; ++key)
00357 {
00358 for (event=0; event < HID_EVENT_LAST; ++event)
00359 {
00360 if (bindings[key][event])
00361 {
00362 Pentagram::ArgvToString(*bindings[key][event], command);
00363 if (event != HID_EVENT_DEPRESS)
00364 {
00365 pout << HID_GetEventName((HID_Event) event) << ' ' <<
00366 HID_GetKeyName((HID_Key) key) <<
00367 " = " << command << std::endl;
00368 }
00369 else
00370 {
00371 pout << HID_GetKeyName((HID_Key) key) <<
00372 " = " << command << std::endl;
00373 }
00374 }
00375 }
00376 }
00377 }
00378