ManaPlus
setup_input.cpp
Go to the documentation of this file.
1 /*
2  * The ManaPlus Client
3  * Copyright (C) 2007 Joshua Langley <[email protected]>
4  * Copyright (C) 2009 The Mana World Development Team
5  * Copyright (C) 2009-2010 The Mana Developers
6  * Copyright (C) 2011-2018 The ManaPlus Developers
7  *
8  * This file is part of The ManaPlus Client.
9  *
10  * This program is free software; you can redistribute it and/or modify
11  * it under the terms of the GNU General Public License as published by
12  * the Free Software Foundation; either version 2 of the License, or
13  * any later version.
14  *
15  * This program is distributed in the hope that it will be useful,
16  * but WITHOUT ANY WARRANTY; without even the implied warranty of
17  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
18  * GNU General Public License for more details.
19  *
20  * You should have received a copy of the GNU General Public License
21  * along with this program. If not, see <http://www.gnu.org/licenses/>.
22  */
23 
25 
26 #include "configuration.h"
27 
28 #include "const/gui/pages.h"
29 
31 #include "input/inputmanager.h"
32 #include "input/keyboardconfig.h"
33 
34 #include "input/pages/craft.h"
35 #include "input/pages/emotes.h"
36 #include "input/pages/move.h"
37 #include "input/pages/outfits.h"
38 #include "input/pages/shortcuts.h"
39 
40 #include "gui/gui.h"
41 #include "gui/setupinputpages.h"
42 
43 #include "gui/windows/okdialog.h"
44 
45 #include "gui/widgets/button.h"
49 #include "gui/widgets/listbox.h"
50 #include "gui/widgets/scrollarea.h"
51 #include "gui/widgets/tabstrip.h"
52 
54 
55 #include "utils/delete2.h"
56 #include "utils/gettext.h"
57 
58 #include "debug.h"
59 
60 Setup_Input::Setup_Input(const Widget2 *const widget) :
61  SetupTab(widget),
62  mKeyListModel(new KeyListModel),
63  mKeyList(CREATEWIDGETR(ListBox, this, mKeyListModel, "")),
64  // TRANSLATORS: button in input settings tab
65  mAssignKeyButton(new Button(this, _("Assign"), "assign", this)),
66  // TRANSLATORS: button in input settings tab
67  mUnassignKeyButton(new Button(this, _("Unassign"), "unassign", this)),
68  // TRANSLATORS: button in input settings tab
69  mDefaultButton(new Button(this, _("Default"), "default", this)),
70  // TRANSLATORS: button in input settings tab
71  mResetKeysButton(new Button(this, _("Reset all keys"), "resetkeys", this)),
72  mTabs(new TabStrip(this, config.getIntValue("fontSize") + 10, 0)),
73  mScrollArea(new ScrollArea(this, mKeyList,
74  Opaque_true, "setup_input_background.xml")),
75  mKeySetting(false),
76  mActionDataSize(new int [SETUP_PAGES])
77 {
79  // TRANSLATORS: setting tab name
80  setName(_("Input"));
81 
83 
84  for (int f = 0; f < SETUP_PAGES; f ++)
85  {
86  int cnt = 0;
87  while (!setupActionData[f][cnt].name.empty())
88  cnt ++;
89  mActionDataSize[f] = cnt;
90  }
91 
93  refreshKeys();
94  if (gui != nullptr)
97 
105 
106  mTabs->addActionListener(this);
107  mTabs->setActionEventId("tabs_");
108  int k = 0;
109  while (pages[k] != nullptr)
110  {
111  mTabs->addButton(gettext(pages[k]), pages[k], false);
112  k ++;
113  }
114 
115  fixTranslations();
116 
117  // Do the layout
118  LayoutHelper h(this);
119  ContainerPlacer place = h.getPlacer(0, 0);
120 
121  place(0, 0, mTabs, 5, 1);
122  place(0, 1, mScrollArea, 5, 5).setPadding(2);
123  place(0, 6, mResetKeysButton, 1, 1);
124  place(2, 6, mAssignKeyButton, 1, 1);
125  place(3, 6, mUnassignKeyButton, 1, 1);
126  place(4, 6, mDefaultButton, 1, 1);
127 
128  int width = 600;
129  if (config.getIntValue("screenwidth") >= 730)
130  width += 100;
131 
132  setDimension(Rect(0, 0, width, 350));
133 }
134 
136 {
137  delete2(mKeyList);
142  delete [] mActionDataSize;
143  mActionDataSize = nullptr;
145 }
146 
148 {
149  keyUnresolved();
150  InputActionT key1, key2;
151 
152  if (inputManager.hasConflicts(key1, key2))
153  {
154  const std::string str1 = keyToString(key1);
155  const std::string str2 = keyToString(key2);
156 
158  // TRANSLATORS: input settings error header
159  _("Key Conflict(s) Detected."),
160  // TRANSLATORS: input settings error
161  strprintf(_("Conflict \"%s\" and \"%s\" keys. "
162  "Resolve them, or gameplay may result in strange behaviour."),
163  gettext(str1.c_str()), gettext(str2.c_str())),
164  // TRANSLATORS: ok dialog button
165  _("OK"),
167  Modal_true,
169  nullptr,
170  260);
171  }
172  keyboard.setEnabled(true);
174 }
175 
177 {
178  keyUnresolved();
180  keyboard.setEnabled(true);
181  refreshKeys();
182 }
183 
185 {
186  const std::string &id = event.getId();
187  const int selectedData = mKeyListModel->getSelectedData();
188 
189  if (event.getSource() == mKeyList)
190  {
191  if (!mKeySetting)
192  {
193  const int i(mKeyList->getSelected());
194  if (i >= 0 && i < mActionDataSize[selectedData])
195  {
196  if (setupActionData[selectedData][i].actionId
198  {
201  }
202  else
203  {
206  }
207  }
208  }
209  }
210  else if (id == "assign")
211  {
212  mKeySetting = true;
214  keyboard.setEnabled(false);
215  const int i(mKeyList->getSelected());
216  if (i >= 0 && i < mActionDataSize[selectedData])
217  {
218  const SetupActionData &key = setupActionData[selectedData][i];
219  const InputActionT ik = key.actionId;
221  mKeyListModel->setElementAt(i, std::string(
222  gettext(key.name.c_str())).append(": ?"));
223  }
224  }
225  else if (id == "unassign")
226  {
227  const int i(mKeyList->getSelected());
228  if (i >= 0 && i < mActionDataSize[selectedData])
229  {
230  const SetupActionData &key = setupActionData[selectedData][i];
231  const InputActionT ik = key.actionId;
236  }
238  }
239  else if (id == "resetkeys")
240  {
243  refreshKeys();
244  }
245  else if (id == "default")
246  {
247  const int i(mKeyList->getSelected());
248  if (i >= 0 && i < mActionDataSize[selectedData])
249  {
250  const SetupActionData &key = setupActionData[selectedData][i];
251  const InputActionT ik = key.actionId;
253  refreshKeys();
254  }
255  }
256  else if (strStartWith(id, "tabs_"))
257  {
258  int k = 0;
259  std::string str("tabs_");
260  while (pages[k] != nullptr)
261  {
262  if (str + pages[k] == id)
263  break;
264  k ++;
265  }
266  if ((pages[k] != nullptr) && str + pages[k] == id)
267  {
270  refreshKeys();
271  mKeyList->setSelected(0);
272  }
273  }
274 }
275 
276 void Setup_Input::refreshAssignedKey(const int index)
277 {
278  const int selectedData = mKeyListModel->getSelectedData();
279  const SetupActionData &key = setupActionData[selectedData][index];
280  if (key.actionId == InputAction::NO_VALUE)
281  {
282  const std::string str(" \342\200\225\342\200\225\342\200\225"
283  "\342\200\225\342\200\225 ");
285  str + gettext(key.name.c_str()) + str);
286  }
287  else
288  {
289  std::string str = gettext(key.name.c_str());
290  unsigned int sz = 20;
291  if (mainGraphics->mWidth > 800)
292  sz = 30;
293  while (str.size() < sz)
294  str.append(" ");
295  mKeyListModel->setElementAt(index, strprintf("%s: %s", str.c_str(),
296  inputManager.getKeyStringLong(key.actionId).c_str()));
297  }
298 }
299 
301 {
302  mKeySetting = false;
303  const int i = keyToSetupData(index);
304  if (i >= 0)
307 }
308 
310 {
311  const int selectedData = mKeyListModel->getSelectedData();
312  for (int i = 0; i < mActionDataSize[selectedData]; i++)
313  {
314  const SetupActionData &key = setupActionData[selectedData][i];
315  if (key.actionId == index)
316  return i;
317  }
318  return -1;
319 }
320 
321 std::string Setup_Input::keyToString(const InputActionT index) const
322 {
323  for (int f = 0; f < SETUP_PAGES; f ++)
324  {
325  for (int i = 0; i < mActionDataSize[f]; i++)
326  {
327  const SetupActionData &key = setupActionData[f][i];
328  if (key.actionId == index)
329  return key.name;
330  }
331  }
332  // TRANSLATORS: unknown key name
333  return _("unknown");
334 }
335 
337 {
338  const int selectedData = mKeyListModel->getSelectedData();
339  for (int i = 0; i < mActionDataSize[selectedData]; i++)
341 }
342 
344 {
345  if (mKeySetting)
346  {
349  }
350 }
351 
353  const InputActionT actionStart,
354  const InputActionT actionEnd,
355  const std::string &text)
356 {
357  int k = 0;
358 
359  while (!actionDatas[k].name.empty())
360  {
361  SetupActionData &data = actionDatas[k];
362 
363  const InputActionT actionId = data.actionId;
364  if (actionId >= actionStart && actionId <= actionEnd)
365  {
366  data.name = strprintf(gettext(text.c_str()),
367  actionId - actionStart + 1);
368  }
369  k ++;
370  }
371 }
372 
374 {
378  "Item Shortcut %d");
379 
383  "Emote Shortcut %d");
384 
388  "Craft shortcut %d");
389 
393  "Outfit Shortcut %d");
394 
398  "Move to point Shortcut %d");
399 }
bool strStartWith(const std::string &str1, const std::string &str2)
#define _(s)
Definition: gettext.h:34
void action(const ActionEvent &event)
ListBox * mKeyList
Definition: setup_input.h:93
void setSelected(const int selected)
Definition: listbox.cpp:398
Font * getHelpFont() const
Definition: gui.h:165
SetupActionData setupActionDataShortcuts[]
Definition: shortcuts.cpp:31
void unassignKey()
static void fixTranslation(SetupActionData *const actionDatas, const InputActionT actionStart, const InputActionT actionEnd, const std::string &text)
Gui * gui
Definition: gui.cpp:110
int getSelectedData() const
Definition: keylistmodel.h:79
void refreshAssignedKey(const int index)
SetupActionData setupActionDataEmotes[]
Definition: emotes.cpp:31
virtual void addButton(const std::string &text, const std::string &tag, const bool pressed)
Definition: widgetgroup.cpp:41
void setNewKeyIndex(const InputActionT value)
Definition: inputmanager.h:103
void setSelectedData(const int i)
Definition: keylistmodel.h:76
Setup_Input(const Widget2 *const widget)
Definition: setup_input.cpp:60
void addActionListener(ActionListener *const actionListener)
Definition: widget.cpp:251
static void fixTranslations()
Button * mAssignKeyButton
Definition: setup_input.h:95
int * mActionDataSize
Definition: setup_input.h:102
Definition: rect.h:72
void setSetupInput(Setup_Input *const setupInput)
Definition: inputmanager.h:109
int mWidth
Definition: graphics.h:483
Definition: button.h:94
Configuration config
SetupActionData *const setupActionData[]
KeyListModel * mKeyListModel
Definition: setup_input.h:92
void setDimension(const Rect &dimension)
Definition: widget.cpp:168
void setElementAt(const int i, const std::string &caption)
Definition: keylistmodel.h:67
std::string getKeyStringLong(const InputActionT index) const
SetupActionData setupActionDataMove[]
Definition: move.cpp:31
int getIntValue(const std::string &key) const
const int SETUP_PAGES
Definition: pages.h:28
void setActionEventId(const std::string &actionEventId)
Definition: widget.h:595
std::string name
#define delete2(var)
Definition: delete2.h:24
void newKeyCallback(const InputActionT index)
void setSize(const int size)
Definition: keylistmodel.h:70
bool mKeySetting
Definition: setup_input.h:101
#define new
Definition: debug_new.h:147
void refreshKeys()
std::string strprintf(const char *const format,...)
Definition: stringutils.cpp:99
const InputActionT actionId
uint32_t data
Widget * getSource() const
Definition: event.h:103
Button * mUnassignKeyButton
Definition: setup_input.h:96
Button * mResetKeysButton
Definition: setup_input.h:98
int getSelected() const
Definition: listbox.h:167
InputAction ::T InputActionT
Definition: inputaction.h:714
static void update()
Graphics * mainGraphics
Definition: graphics.cpp:108
const bool ShowCenter_true
Definition: showcenter.h:29
void store() const
ScrollArea * mScrollArea
Definition: setup_input.h:100
ContainerPlacer getPlacer(const int x, const int y)
void setEnabled(const bool enabled)
Definition: widget.h:351
InputActionT getNewKeyIndex() const
Definition: inputmanager.h:116
SetupActionData setupActionDataOutfits[]
Definition: outfits.cpp:31
#define CREATEWIDGET(type,...)
Definition: createwidget.h:28
void setFont(Font *const font)
Definition: widget.cpp:348
Button * mDefaultButton
Definition: setup_input.h:97
void setName(const std::string &name)
Definition: setuptab.h:67
const bool Opaque_true
Definition: opaque.h:29
void makeDefault(const InputActionT i)
const char *const pages[SETUP_PAGES+1]
SetupActionData setupActionDataCraft[]
Definition: craft.cpp:28
KeyboardConfig keyboard
TabStrip * mTabs
Definition: setup_input.h:99
int keyToSetupData(const InputActionT index) const
InputManager inputManager
#define CREATEWIDGETR(type,...)
Definition: createwidget.h:35
void keyUnresolved()
bool hasConflicts(InputActionT &key1, InputActionT &key2) const
void setEnabled(const bool flag)
std::string keyToString(const InputActionT index) const
void setHorizontalScrollPolicy(const ScrollPolicy hPolicy)