2 // Copyright (C) 2006 Matthias Braun <matze@braunis.de>,
3 // 2007 Ingo Ruhnke <grumbel@gmx.de>
5 // This program is free software: you can redistribute it and/or modify
6 // it under the terms of the GNU General Public License as published by
7 // the Free Software Foundation, either version 3 of the License, or
8 // (at your option) any later version.
10 // This program is distributed in the hope that it will be useful,
11 // but WITHOUT ANY WARRANTY; without even the implied warranty of
12 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13 // GNU General Public License for more details.
15 // You should have received a copy of the GNU General Public License
16 // along with this program. If not, see <http://www.gnu.org/licenses/>.
18 #include "control/joystickkeyboardcontroller.hpp"
22 #include "gui/menu.hpp"
23 #include "gui/menu_item.hpp"
24 #include "util/writer.hpp"
25 #include "lisp/list_iterator.hpp"
26 #include "supertux/gameconfig.hpp"
27 #include "supertux/console.hpp"
28 #include "util/gettext.hpp"
31 const int SCAN_JOYSTICKS = Controller::CONTROLCOUNT + 1;
34 class JoystickKeyboardController::JoystickMenu : public Menu
37 JoystickMenu(JoystickKeyboardController* controller);
38 virtual ~JoystickMenu();
41 std::string get_button_name(int button);
42 void update_menu_item(Control id);
43 virtual void menu_action(MenuItem* item);
44 JoystickKeyboardController* controller;
50 JoystickMenu(const JoystickMenu&);
51 JoystickMenu& operator=(const JoystickMenu&);
54 class JoystickKeyboardController::KeyboardMenu : public Menu
57 KeyboardMenu(JoystickKeyboardController* controller);
61 std::string get_key_name(SDLKey key);
62 virtual void menu_action(MenuItem* item);
63 JoystickKeyboardController* controller;
66 KeyboardMenu(const KeyboardMenu&);
67 KeyboardMenu& operator=(const KeyboardMenu&);
70 JoystickKeyboardController::JoystickKeyboardController() :
86 wait_for_joystick(-1),
88 joystick_options_menu(0)
90 // initialize default keyboard map
91 keymap[SDLK_LEFT] = LEFT;
92 keymap[SDLK_RIGHT] = RIGHT;
94 keymap[SDLK_DOWN] = DOWN;
95 keymap[SDLK_SPACE] = JUMP;
96 keymap[SDLK_LCTRL] = ACTION;
97 keymap[SDLK_LALT] = ACTION;
98 keymap[SDLK_ESCAPE] = PAUSE_MENU;
99 keymap[SDLK_p] = PAUSE_MENU;
100 keymap[SDLK_PAUSE] = PAUSE_MENU;
101 keymap[SDLK_RETURN] = MENU_SELECT;
102 keymap[SDLK_KP_ENTER] = MENU_SELECT;
103 keymap[SDLK_CARET] = CONSOLE;
104 keymap[SDLK_DELETE] = PEEK_LEFT;
105 keymap[SDLK_PAGEDOWN] = PEEK_RIGHT;
106 keymap[SDLK_HOME] = PEEK_UP;
107 keymap[SDLK_END] = PEEK_DOWN;
109 jump_with_up_joy = false;
110 jump_with_up_kbd = false;
112 updateAvailableJoysticks();
116 // Default joystick button configuration
117 joy_button_map[0] = JUMP;
118 joy_button_map[1] = ACTION;
120 if( min_joybuttons > 5 ){
121 joy_button_map[4] = PEEK_LEFT;
122 joy_button_map[5] = PEEK_RIGHT;
124 if(min_joybuttons > 7)
125 joy_button_map[min_joybuttons-1] = PAUSE_MENU;
127 // map the last 2 buttons to menu and pause
128 if(min_joybuttons > 2)
129 joy_button_map[min_joybuttons-1] = PAUSE_MENU;
130 // map all remaining joystick buttons to MENU_SELECT
131 for(int i = 2; i < max_joybuttons; ++i) {
132 if(i != min_joybuttons-1)
133 joy_button_map[i] = MENU_SELECT;
137 // Default joystick axis configuration
138 joy_axis_map[-1] = LEFT;
139 joy_axis_map[ 1] = RIGHT;
140 joy_axis_map[-2] = UP;
141 joy_axis_map[ 2] = DOWN;
144 JoystickKeyboardController::~JoystickKeyboardController()
146 for(std::vector<SDL_Joystick*>::iterator i = joysticks.begin();
147 i != joysticks.end(); ++i) {
149 SDL_JoystickClose(*i);
152 delete key_options_menu;
153 delete joystick_options_menu;
157 JoystickKeyboardController::updateAvailableJoysticks()
159 for(std::vector<SDL_Joystick*>::iterator i = joysticks.begin();
160 i != joysticks.end(); ++i) {
162 SDL_JoystickClose(*i);
166 SDL_QuitSubSystem(SDL_INIT_JOYSTICK);
167 SDL_InitSubSystem(SDL_INIT_JOYSTICK);
169 int joystick_count = SDL_NumJoysticks();
175 if( joystick_count > 0 ){
176 for(int i = 0; i < joystick_count; ++i) {
177 SDL_Joystick* joystick = SDL_JoystickOpen(i);
179 if(SDL_JoystickNumButtons(joystick) < 2) {
180 log_info << "Joystick " << i << ": " << SDL_JoystickName(i) << " has less than 2 buttons" << std::endl;
183 if(SDL_JoystickNumAxes(joystick) < 2
184 && SDL_JoystickNumHats(joystick) == 0) {
185 log_info << "Joystick " << i << ": " << SDL_JoystickName(i) << " has less than 2 axes and no hat" << std::endl;
189 SDL_JoystickClose(joystick);
193 if(min_joybuttons < 0 || SDL_JoystickNumButtons(joystick) < min_joybuttons)
194 min_joybuttons = SDL_JoystickNumButtons(joystick);
196 if(SDL_JoystickNumButtons(joystick) > max_joybuttons)
197 max_joybuttons = SDL_JoystickNumButtons(joystick);
199 if(SDL_JoystickNumAxes(joystick) > max_joyaxis)
200 max_joyaxis = SDL_JoystickNumAxes(joystick);
202 if(SDL_JoystickNumHats(joystick) > max_joyhats)
203 max_joyhats = SDL_JoystickNumHats(joystick);
205 joysticks.push_back(joystick);
209 // some joysticks or SDL seem to produce some bogus events after being opened
210 Uint32 ticks = SDL_GetTicks();
211 while(SDL_GetTicks() - ticks < 200) {
213 SDL_PollEvent(&event);
218 JoystickKeyboardController::read(const Reader& lisp)
220 const lisp::Lisp* keymap_lisp = lisp.get_lisp("keymap");
223 keymap_lisp->get("jump-with-up", jump_with_up_kbd);
224 lisp::ListIterator iter(keymap_lisp);
226 if(iter.item() == "map") {
229 const lisp::Lisp* map = iter.lisp();
230 map->get("key", key);
231 map->get("control", control);
232 if(key < SDLK_FIRST || key >= SDLK_LAST) {
233 log_info << "Invalid key '" << key << "' in keymap" << std::endl;
238 for(i = 0; controlNames[i] != 0; ++i) {
239 if(control == controlNames[i])
242 if(controlNames[i] == 0) {
243 log_info << "Invalid control '" << control << "' in keymap" << std::endl;
246 keymap[(SDLKey) key] = (Control)i;
251 const lisp::Lisp* joystick_lisp = lisp.get_lisp("joystick");
253 joystick_lisp->get("dead-zone", dead_zone);
254 joystick_lisp->get("jump-with-up", jump_with_up_joy);
255 lisp::ListIterator iter(joystick_lisp);
257 if(iter.item() == "map") {
262 const lisp::Lisp* map = iter.lisp();
264 map->get("control", control);
266 for(i = 0; controlNames[i] != 0; ++i) {
267 if(control == controlNames[i])
270 if(controlNames[i] == 0) {
271 log_info << "Invalid control '" << control << "' in buttonmap" << std::endl;
275 if (map->get("button", button)) {
276 if(button < 0 || button >= max_joybuttons) {
277 log_info << "Invalid button '" << button << "' in buttonmap" << std::endl;
280 bind_joybutton(button, (Control) i);
283 if (map->get("axis", axis)) {
284 if (axis == 0 || abs(axis) > max_joyaxis) {
285 log_info << "Invalid axis '" << axis << "' in axismap" << std::endl;
288 bind_joyaxis(axis, (Control) i);
291 if (map->get("hat", hat)) {
292 if (hat != SDL_HAT_UP &&
293 hat != SDL_HAT_DOWN &&
294 hat != SDL_HAT_LEFT &&
295 hat != SDL_HAT_RIGHT) {
296 log_info << "Invalid axis '" << axis << "' in axismap" << std::endl;
299 bind_joyhat(hat, (Control) i);
308 JoystickKeyboardController::write(Writer& writer)
310 writer.start_list("keymap");
311 writer.write("jump-with-up", jump_with_up_kbd);
312 for(KeyMap::iterator i = keymap.begin(); i != keymap.end(); ++i) {
313 writer.start_list("map");
314 writer.write("key", (int) i->first);
315 writer.write("control", controlNames[i->second]);
316 writer.end_list("map");
318 writer.end_list("keymap");
320 writer.start_list("joystick");
321 writer.write("dead-zone", dead_zone);
322 writer.write("jump-with-up", jump_with_up_joy);
324 for(ButtonMap::iterator i = joy_button_map.begin(); i != joy_button_map.end();
326 writer.start_list("map");
327 writer.write("button", i->first);
328 writer.write("control", controlNames[i->second]);
329 writer.end_list("map");
332 for(HatMap::iterator i = joy_hat_map.begin(); i != joy_hat_map.end(); ++i) {
333 writer.start_list("map");
334 writer.write("hat", i->first);
335 writer.write("control", controlNames[i->second]);
336 writer.end_list("map");
339 for(AxisMap::iterator i = joy_axis_map.begin(); i != joy_axis_map.end(); ++i) {
340 writer.start_list("map");
341 writer.write("axis", i->first);
342 writer.write("control", controlNames[i->second]);
343 writer.end_list("map");
346 writer.end_list("joystick");
350 JoystickKeyboardController::reset()
356 JoystickKeyboardController::set_joy_controls(Control id, bool value)
358 if (jump_with_up_joy && id == Controller::UP)
359 controls[Controller::JUMP] = value;
361 controls[(Control)id] = value;
365 JoystickKeyboardController::process_event(const SDL_Event& event)
370 process_key_event(event);
373 case SDL_JOYAXISMOTION:
374 process_axis_event(event.jaxis);
377 case SDL_JOYHATMOTION:
378 process_hat_event(event.jhat);
381 case SDL_JOYBUTTONDOWN:
382 case SDL_JOYBUTTONUP:
383 process_button_event(event.jbutton);
392 JoystickKeyboardController::process_button_event(const SDL_JoyButtonEvent& jbutton)
394 if(wait_for_joystick >= 0)
396 if(jbutton.state == SDL_PRESSED)
398 bind_joybutton(jbutton.button, (Control)wait_for_joystick);
399 joystick_options_menu->update();
401 wait_for_joystick = -1;
406 ButtonMap::iterator i = joy_button_map.find(jbutton.button);
407 if(i == joy_button_map.end()) {
408 log_debug << "Unmapped joybutton " << (int)jbutton.button << " pressed" << std::endl;
410 set_joy_controls(i->second, (jbutton.state == SDL_PRESSED));
416 JoystickKeyboardController::process_axis_event(const SDL_JoyAxisEvent& jaxis)
418 if (wait_for_joystick >= 0)
420 if (abs(jaxis.value) > dead_zone) {
422 bind_joyaxis(-(jaxis.axis + 1), Control(wait_for_joystick));
424 bind_joyaxis(jaxis.axis + 1, Control(wait_for_joystick));
426 joystick_options_menu->update();
427 wait_for_joystick = -1;
432 // Split the axis into left and right, so that both can be
433 // mapped separately (needed for jump/down vs up/down)
434 int axis = jaxis.axis + 1;
436 AxisMap::iterator left = joy_axis_map.find(-axis);
437 AxisMap::iterator right = joy_axis_map.find(axis);
439 if(left == joy_axis_map.end()) {
440 std::cout << "Unmapped joyaxis " << (int)jaxis.axis << " moved" << std::endl;
442 if (jaxis.value < -dead_zone)
443 set_joy_controls(left->second, true);
444 else if (jaxis.value > dead_zone)
445 set_joy_controls(left->second, false);
447 set_joy_controls(left->second, false);
450 if(right == joy_axis_map.end()) {
451 std::cout << "Unmapped joyaxis " << (int)jaxis.axis << " moved" << std::endl;
453 if (jaxis.value < -dead_zone)
454 set_joy_controls(right->second, false);
455 else if (jaxis.value > dead_zone)
456 set_joy_controls(right->second, true);
458 set_joy_controls(right->second, false);
464 JoystickKeyboardController::process_hat_event(const SDL_JoyHatEvent& jhat)
466 Uint8 changed = hat_state ^ jhat.value;
468 if (wait_for_joystick >= 0)
470 if (changed & SDL_HAT_UP && jhat.value & SDL_HAT_UP)
471 bind_joyhat(SDL_HAT_UP, (Control)wait_for_joystick);
473 if (changed & SDL_HAT_DOWN && jhat.value & SDL_HAT_DOWN)
474 bind_joyhat(SDL_HAT_DOWN, (Control)wait_for_joystick);
476 if (changed & SDL_HAT_LEFT && jhat.value & SDL_HAT_LEFT)
477 bind_joyhat(SDL_HAT_LEFT, (Control)wait_for_joystick);
479 if (changed & SDL_HAT_RIGHT && jhat.value & SDL_HAT_RIGHT)
480 bind_joyhat(SDL_HAT_RIGHT, (Control)wait_for_joystick);
482 joystick_options_menu->update();
483 wait_for_joystick = -1;
487 if (changed & SDL_HAT_UP)
489 HatMap::iterator it = joy_hat_map.find(SDL_HAT_UP);
490 if (it != joy_hat_map.end())
491 set_joy_controls(it->second, jhat.value & SDL_HAT_UP);
494 if (changed & SDL_HAT_DOWN)
496 HatMap::iterator it = joy_hat_map.find(SDL_HAT_DOWN);
497 if (it != joy_hat_map.end())
498 set_joy_controls(it->second, jhat.value & SDL_HAT_DOWN);
501 if (changed & SDL_HAT_LEFT)
503 HatMap::iterator it = joy_hat_map.find(SDL_HAT_LEFT);
504 if (it != joy_hat_map.end())
505 set_joy_controls(it->second, jhat.value & SDL_HAT_LEFT);
508 if (changed & SDL_HAT_RIGHT)
510 HatMap::iterator it = joy_hat_map.find(SDL_HAT_RIGHT);
511 if (it != joy_hat_map.end())
512 set_joy_controls(it->second, jhat.value & SDL_HAT_RIGHT);
516 hat_state = jhat.value;
520 JoystickKeyboardController::process_key_event(const SDL_Event& event)
522 KeyMap::iterator key_mapping = keymap.find(event.key.keysym.sym);
524 // if console key was pressed: toggle console
525 if ((key_mapping != keymap.end()) && (key_mapping->second == CONSOLE)) {
526 if (event.type == SDL_KEYDOWN)
527 Console::instance->toggle();
529 if (Console::instance->hasFocus()) {
530 // if console is open: send key there
531 process_console_key_event(event);
532 } else if (Menu::current()) {
533 // if menu mode: send key there
534 process_menu_key_event(event);
535 } else if(key_mapping == keymap.end()) {
536 // default action: update controls
537 //log_debug << "Key " << event.key.keysym.sym << " is unbound" << std::endl;
539 Control control = key_mapping->second;
540 controls[control] = (event.type == SDL_KEYDOWN);
541 if (jump_with_up_kbd && control == UP){
542 controls[JUMP] = (event.type == SDL_KEYDOWN);
549 JoystickKeyboardController::process_console_key_event(const SDL_Event& event)
551 if (event.type != SDL_KEYDOWN) return;
553 switch (event.key.keysym.sym) {
555 Console::instance->enter();
558 Console::instance->backspace();
561 Console::instance->autocomplete();
564 Console::instance->scroll(-1);
567 Console::instance->scroll(+1);
570 Console::instance->move_cursor(-65535);
573 Console::instance->move_cursor(+65535);
576 Console::instance->show_history(-1);
579 Console::instance->show_history(+1);
582 Console::instance->move_cursor(-1);
585 Console::instance->move_cursor(+1);
588 int c = event.key.keysym.unicode;
589 if ((c >= 32) && (c <= 126)) {
590 Console::instance->input((char)c);
597 JoystickKeyboardController::process_menu_key_event(const SDL_Event& event)
599 // wait for key mode?
600 if(wait_for_key >= 0) {
601 if(event.type == SDL_KEYUP)
604 if(event.key.keysym.sym != SDLK_ESCAPE
605 && event.key.keysym.sym != SDLK_PAUSE) {
606 bind_key(event.key.keysym.sym, (Control) wait_for_key);
609 key_options_menu->update();
613 if(wait_for_joystick >= 0) {
614 if(event.key.keysym.sym == SDLK_ESCAPE) {
616 joystick_options_menu->update();
617 wait_for_joystick = -1;
623 /* we use default keys when the menu is open (to avoid problems when
624 * redefining keys to invalid settings
626 switch(event.key.keysym.sym) {
642 control = MENU_SELECT;
646 control = PAUSE_MENU;
653 controls[control] = (event.type == SDL_KEYDOWN);
657 JoystickKeyboardController::unbind_joystick_control(Control control)
659 // remove all previous mappings for that control
660 for(AxisMap::iterator i = joy_axis_map.begin(); i != joy_axis_map.end(); /* no ++i */) {
661 if(i->second == control)
662 joy_axis_map.erase(i++);
667 for(ButtonMap::iterator i = joy_button_map.begin(); i != joy_button_map.end(); /* no ++i */) {
668 if(i->second == control)
669 joy_button_map.erase(i++);
674 for(HatMap::iterator i = joy_hat_map.begin(); i != joy_hat_map.end(); /* no ++i */) {
675 if(i->second == control)
676 joy_hat_map.erase(i++);
683 JoystickKeyboardController::bind_joyaxis(int axis, Control control)
685 // axis isn't the SDL axis number, but axisnumber + 1 with sign
686 // changed depending on if the positive or negative end is to be
687 // used (negative axis 0 becomes -1, positive axis 2 becomes +3,
690 unbind_joystick_control(control);
693 joy_axis_map[axis] = control;
697 JoystickKeyboardController::bind_joyhat(int dir, Control c)
699 unbind_joystick_control(c);
702 joy_hat_map[dir] = c;
706 JoystickKeyboardController::bind_joybutton(int button, Control control)
708 unbind_joystick_control(control);
711 joy_button_map[button] = control;
715 JoystickKeyboardController::bind_key(SDLKey key, Control control)
717 // remove all previous mappings for that control and for that key
718 for(KeyMap::iterator i = keymap.begin();
719 i != keymap.end(); /* no ++i */) {
720 if(i->second == control) {
721 KeyMap::iterator e = i;
729 KeyMap::iterator i = keymap.find(key);
730 if(i != keymap.end())
734 keymap[key]= control;
738 JoystickKeyboardController::print_joystick_mappings()
740 std::cout << "Joystick Mappings" << std::endl;
741 std::cout << "-----------------" << std::endl;
742 for(AxisMap::iterator i = joy_axis_map.begin(); i != joy_axis_map.end(); ++i) {
743 std::cout << "Axis: " << i->first << " -> " << i->second << std::endl;
746 for(ButtonMap::iterator i = joy_button_map.begin(); i != joy_button_map.end(); ++i) {
747 std::cout << "Button: " << i->first << " -> " << i->second << std::endl;
750 for(HatMap::iterator i = joy_hat_map.begin(); i != joy_hat_map.end(); ++i) {
751 std::cout << "Hat: " << i->first << " -> " << i->second << std::endl;
753 std::cout << std::endl;
757 JoystickKeyboardController::reversemap_key(Control c)
759 for(KeyMap::iterator i = keymap.begin(); i != keymap.end(); ++i) {
768 JoystickKeyboardController::reversemap_joyaxis(Control c)
770 for(AxisMap::iterator i = joy_axis_map.begin(); i != joy_axis_map.end(); ++i) {
779 JoystickKeyboardController::reversemap_joybutton(Control c)
781 for(ButtonMap::iterator i = joy_button_map.begin(); i != joy_button_map.end(); ++i) {
790 JoystickKeyboardController::reversemap_joyhat(Control c)
792 for(HatMap::iterator i = joy_hat_map.begin(); i != joy_hat_map.end(); ++i) {
801 JoystickKeyboardController::get_key_options_menu()
803 if(key_options_menu == 0) {
804 key_options_menu = new KeyboardMenu(this);
807 return key_options_menu;
811 JoystickKeyboardController::get_joystick_options_menu()
813 if(joystick_options_menu == 0) {
814 joystick_options_menu = new JoystickMenu(this);
817 return joystick_options_menu;
820 //----------------------------------------------------------------------------
822 JoystickKeyboardController::KeyboardMenu::KeyboardMenu(
823 JoystickKeyboardController* _controller)
824 : controller(_controller)
826 add_label(_("Setup Keyboard"));
828 add_controlfield(Controller::UP, _("Up"));
829 add_controlfield(Controller::DOWN, _("Down"));
830 add_controlfield(Controller::LEFT, _("Left"));
831 add_controlfield(Controller::RIGHT, _("Right"));
832 add_controlfield(Controller::JUMP, _("Jump"));
833 add_controlfield(Controller::ACTION, _("Action"));
834 add_controlfield(Controller::PEEK_LEFT, _("Peek Left"));
835 add_controlfield(Controller::PEEK_RIGHT, _("Peek Right"));
836 add_controlfield(Controller::PEEK_UP, _("Peek Up"));
837 add_controlfield(Controller::PEEK_DOWN, _("Peek Down"));
838 if (g_config->console_enabled) {
839 add_controlfield(Controller::CONSOLE, _("Console"));
841 add_toggle(Controller::CONTROLCOUNT, _("Jump with Up"), controller->jump_with_up_kbd);
847 JoystickKeyboardController::KeyboardMenu::~KeyboardMenu()
851 JoystickKeyboardController::KeyboardMenu::get_key_name(SDLKey key)
857 return _("Up cursor");
859 return _("Down cursor");
861 return _("Left cursor");
863 return _("Right cursor");
869 return _("Right Shift");
871 return _("Left Shift");
873 return _("Right Control");
875 return _("Left Control");
877 return _("Right Alt");
879 return _("Left Alt");
881 return SDL_GetKeyName((SDLKey) key);
886 JoystickKeyboardController::KeyboardMenu::menu_action(MenuItem* item)
888 if(item->id >= 0 && item->id < Controller::CONTROLCOUNT){
889 item->change_input(_("Press Key"));
890 controller->wait_for_key = item->id;
891 } else if( item->id == Controller::CONTROLCOUNT) {
892 controller->jump_with_up_kbd = item->toggled;
897 JoystickKeyboardController::KeyboardMenu::update()
900 get_item_by_id((int) Controller::UP).change_input(get_key_name(
901 controller->reversemap_key(Controller::UP)));
902 get_item_by_id((int) Controller::DOWN).change_input(get_key_name(
903 controller->reversemap_key(Controller::DOWN)));
904 get_item_by_id((int) Controller::LEFT).change_input(get_key_name(
905 controller->reversemap_key(Controller::LEFT)));
906 get_item_by_id((int) Controller::RIGHT).change_input(get_key_name(
907 controller->reversemap_key(Controller::RIGHT)));
908 get_item_by_id((int) Controller::JUMP).change_input(get_key_name(
909 controller->reversemap_key(Controller::JUMP)));
910 get_item_by_id((int) Controller::ACTION).change_input(get_key_name(
911 controller->reversemap_key(Controller::ACTION)));
912 get_item_by_id((int) Controller::PEEK_LEFT).change_input(get_key_name(
913 controller->reversemap_key(Controller::PEEK_LEFT)));
914 get_item_by_id((int) Controller::PEEK_RIGHT).change_input(get_key_name(
915 controller->reversemap_key(Controller::PEEK_RIGHT)));
916 get_item_by_id((int) Controller::PEEK_UP).change_input(get_key_name(
917 controller->reversemap_key(Controller::PEEK_UP)));
918 get_item_by_id((int) Controller::PEEK_DOWN).change_input(get_key_name(
919 controller->reversemap_key(Controller::PEEK_DOWN)));
920 if (g_config->console_enabled) {
921 get_item_by_id((int) Controller::CONSOLE).change_input(get_key_name(
922 controller->reversemap_key(Controller::CONSOLE)));
924 get_item_by_id(Controller::CONTROLCOUNT).toggled = controller->jump_with_up_kbd;
927 //---------------------------------------------------------------------------
929 JoystickKeyboardController::JoystickMenu::JoystickMenu(
930 JoystickKeyboardController* _controller)
931 : controller(_controller)
936 JoystickKeyboardController::JoystickMenu::~JoystickMenu()
940 JoystickKeyboardController::JoystickMenu::recreateMenu()
943 add_label(_("Setup Joystick"));
945 if(controller->joysticks.size() > 0) {
946 add_controlfield(Controller::UP, _("Up"));
947 add_controlfield(Controller::DOWN, _("Down"));
948 add_controlfield(Controller::LEFT, _("Left"));
949 add_controlfield(Controller::RIGHT, _("Right"));
950 add_controlfield(Controller::JUMP, _("Jump"));
951 add_controlfield(Controller::ACTION, _("Action"));
952 add_controlfield(Controller::PAUSE_MENU, _("Pause/Menu"));
953 add_controlfield(Controller::PEEK_LEFT, _("Peek Left"));
954 add_controlfield(Controller::PEEK_RIGHT, _("Peek Right"));
955 add_controlfield(Controller::PEEK_UP, _("Peek Up"));
956 add_controlfield(Controller::PEEK_DOWN, _("Peek Down"));
958 add_toggle(Controller::CONTROLCOUNT, _("Jump with Up"), controller->jump_with_up_joy);
960 add_inactive(-1, _("No Joysticks found"));
963 add_entry(SCAN_JOYSTICKS, _("Scan for Joysticks"));
965 //Show Joysticks currently activated:
966 for(std::vector<SDL_Joystick*>::iterator i = controller->joysticks.begin();
967 i != controller->joysticks.end(); ++i) {
969 add_inactive(-1, SDL_JoystickName(SDL_JoystickIndex(*i)) );
978 JoystickKeyboardController::JoystickMenu::get_button_name(int button)
983 std::ostringstream name;
984 name << "Button " << button;
989 JoystickKeyboardController::JoystickMenu::menu_action(MenuItem* item)
991 if (item->id >= 0 && item->id < Controller::CONTROLCOUNT) {
992 item->change_input(_("Press Button"));
993 controller->wait_for_joystick = item->id;
994 } else if (item->id == Controller::CONTROLCOUNT) {
995 controller->jump_with_up_joy = item->toggled;
996 } else if( item->id == SCAN_JOYSTICKS) {
997 controller->updateAvailableJoysticks();
1003 JoystickKeyboardController::JoystickMenu::update_menu_item(Control id)
1005 int button = controller->reversemap_joybutton(id);
1006 int axis = controller->reversemap_joyaxis(id);
1007 int hat_dir = controller->reversemap_joyhat(id);
1010 get_item_by_id((int)id).change_input(get_button_name(button));
1011 } else if (axis != 0) {
1012 std::ostringstream name;
1023 else if (abs(axis) == 2)
1025 else if (abs(axis) == 2)
1027 else if (abs(axis) == 3)
1032 get_item_by_id((int)id).change_input(name.str());
1033 } else if (hat_dir != -1) {
1055 name = "Unknown hat_dir";
1059 get_item_by_id((int)id).change_input(name);
1061 get_item_by_id((int)id).change_input("None");
1066 JoystickKeyboardController::JoystickMenu::update()
1068 if(controller->joysticks.size() == 0)
1071 update_menu_item(Controller::UP);
1072 update_menu_item(Controller::DOWN);
1073 update_menu_item(Controller::LEFT);
1074 update_menu_item(Controller::RIGHT);
1076 update_menu_item(Controller::JUMP);
1077 update_menu_item(Controller::ACTION);
1078 update_menu_item(Controller::PAUSE_MENU);
1079 update_menu_item(Controller::PEEK_LEFT);
1080 update_menu_item(Controller::PEEK_RIGHT);
1081 update_menu_item(Controller::PEEK_UP);
1082 update_menu_item(Controller::PEEK_DOWN);
1084 get_item_by_id(Controller::CONTROLCOUNT).toggled = controller->jump_with_up_joy;