Merge branch 'feature/menu-cleanup'
[supertux.git] / src / supertux / menu / joystick_menu.cpp
1 //  SuperTux
2 //  Copyright (C) 2006 Matthias Braun <matze@braunis.de>,
3 //                2007 Ingo Ruhnke <grumbel@gmx.de>
4 //
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.
9 //
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.
14 //
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/>.
17
18 #include "supertux/menu/joystick_menu.hpp"
19
20 #include <sstream>
21
22 #include "control/joystick_manager.hpp"
23 #include "util/gettext.hpp"
24
25 namespace {
26
27 enum {
28   MNID_JUMP_WITH_UP = Controller::CONTROLCOUNT,
29   MNID_SCAN_JOYSTICKS,
30   MNID_AUTO_JOYSTICK_CFG
31 };
32
33 } // namespace
34
35 JoystickMenu::JoystickMenu(InputManager* input_manager) :
36   m_input_manager(input_manager),
37   m_joysticks_available(false)
38 {
39   recreate_menu();
40 }
41
42 JoystickMenu::~JoystickMenu()
43 {}
44
45 void
46 JoystickMenu::recreate_menu()
47 {
48   clear();
49   add_label(_("Setup Joystick"));
50   add_hl();
51
52   add_toggle(MNID_AUTO_JOYSTICK_CFG, _("Manual Joystick Configuration"),
53              !m_input_manager->use_game_controller());
54
55   if (m_input_manager->use_game_controller())
56   {
57     m_joysticks_available = false;
58   }
59   else
60   {
61     if (m_input_manager->joystick_manager->joysticks.size() > 0)
62     {
63       m_joysticks_available = true;
64
65       add_controlfield(Controller::UP,          _("Up"));
66       add_controlfield(Controller::DOWN,        _("Down"));
67       add_controlfield(Controller::LEFT,        _("Left"));
68       add_controlfield(Controller::RIGHT,       _("Right"));
69       add_controlfield(Controller::JUMP,        _("Jump"));
70       add_controlfield(Controller::ACTION,      _("Action"));
71       add_controlfield(Controller::PAUSE_MENU,  _("Pause/Menu"));
72       add_controlfield(Controller::PEEK_LEFT,   _("Peek Left"));
73       add_controlfield(Controller::PEEK_RIGHT,  _("Peek Right"));
74       add_controlfield(Controller::PEEK_UP,     _("Peek Up"));
75       add_controlfield(Controller::PEEK_DOWN,   _("Peek Down"));
76
77       add_toggle(MNID_JUMP_WITH_UP, _("Jump with Up"), m_input_manager->joystick_manager->jump_with_up_joy);
78     }
79     else
80     {
81       m_joysticks_available = false;
82
83       add_inactive(-1, _("No Joysticks found"));
84       add_entry(MNID_SCAN_JOYSTICKS, _("Scan for Joysticks"));
85     }
86   }
87
88   add_hl();
89   add_back(_("Back"));
90   refresh();
91 }
92
93 std::string
94 JoystickMenu::get_button_name(int button)
95 {
96   if(button < 0)
97   {
98     return _("None");
99   }
100   else
101   {
102     std::ostringstream name;
103     name << "Button " << button;
104     return name.str();
105   }
106 }
107
108 void
109 JoystickMenu::menu_action(MenuItem* item)
110 {
111   if (0 <= item->id && item->id < Controller::CONTROLCOUNT)
112   {
113     item->change_input(_("Press Button"));
114     m_input_manager->joystick_manager->wait_for_joystick = item->id;
115   }
116   else if (item->id == MNID_JUMP_WITH_UP)
117   {
118     m_input_manager->joystick_manager->jump_with_up_joy = item->toggled;
119   }
120   else if (item->id == MNID_AUTO_JOYSTICK_CFG)
121   {
122     m_input_manager->use_game_controller(!item->toggled);
123     m_input_manager->reset();
124     recreate_menu();
125   }
126   else if(item->id == MNID_SCAN_JOYSTICKS)
127   {
128     m_input_manager->reset();
129     recreate_menu();
130   }
131 }
132
133 void
134 JoystickMenu::refresh_menu_item(Controller::Control id)
135 {
136   int button  = m_input_manager->joystick_manager->reversemap_joybutton(id);
137   int axis    = m_input_manager->joystick_manager->reversemap_joyaxis(id);
138   int hat_dir = m_input_manager->joystick_manager->reversemap_joyhat(id);
139
140   if (button != -1)
141   {
142     get_item_by_id(static_cast<int>(id)).change_input(get_button_name(button));
143   }
144   else if (axis != 0)
145   {
146     std::ostringstream name;
147
148     name << "Axis ";
149
150     if (axis < 0)
151       name << "-";
152     else
153       name << "+";
154
155     if (abs(axis) == 1)
156       name << "X";
157     else if (abs(axis) == 2)
158       name << "Y";
159     else if (abs(axis) == 2)
160       name << "X2";
161     else if (abs(axis) == 3)
162       name << "Y2";
163     else
164       name << abs(axis);
165
166     get_item_by_id(static_cast<int>(id)).change_input(name.str());
167   }
168   else if (hat_dir != -1)
169   {
170     std::string name;
171
172     switch (hat_dir)
173     {
174       case SDL_HAT_UP:
175         name = "Hat Up";
176         break;
177
178       case SDL_HAT_DOWN:
179         name = "Hat Down";
180         break;
181
182       case SDL_HAT_LEFT:
183         name = "Hat Left";
184         break;
185
186       case SDL_HAT_RIGHT:
187         name = "Hat Right";
188         break;
189
190       default:
191         name = "Unknown hat_dir";
192         break;
193     }
194
195     get_item_by_id(static_cast<int>(id)).change_input(name);
196   }
197   else
198   {
199     get_item_by_id(static_cast<int>(id)).change_input("None");
200   }
201 }
202
203 void
204 JoystickMenu::refresh()
205 {
206   if (m_joysticks_available)
207   {
208     refresh_menu_item(Controller::UP);
209     refresh_menu_item(Controller::DOWN);
210     refresh_menu_item(Controller::LEFT);
211     refresh_menu_item(Controller::RIGHT);
212
213     refresh_menu_item(Controller::JUMP);
214     refresh_menu_item(Controller::ACTION);
215     refresh_menu_item(Controller::PAUSE_MENU);
216     refresh_menu_item(Controller::PEEK_LEFT);
217     refresh_menu_item(Controller::PEEK_RIGHT);
218     refresh_menu_item(Controller::PEEK_UP);
219     refresh_menu_item(Controller::PEEK_DOWN);
220   }
221 }
222
223 /* EOF */