Merge branch 'rr1-maint'
Conflicts: src/platform/wxwidgets/mainwindow.cpp
This commit is contained in:
commit
7d19748ed2
8 changed files with 690 additions and 193 deletions
|
@ -396,4 +396,73 @@ public:
|
|||
std::runtime_error);
|
||||
};
|
||||
|
||||
class inverse_key
|
||||
{
|
||||
public:
|
||||
/**
|
||||
* Create inverse key.
|
||||
*
|
||||
* Parameter command: Command this is for.
|
||||
* Parameter name: Name of inverse key.
|
||||
*/
|
||||
inverse_key(const std::string& command, const std::string& name) throw(std::bad_alloc);
|
||||
/**
|
||||
* Destructor.
|
||||
*/
|
||||
~inverse_key();
|
||||
/**
|
||||
* Get set of inverse keys.
|
||||
*
|
||||
* Returns: The set of all inverses.
|
||||
*/
|
||||
static std::set<inverse_key*> get_ikeys() throw(std::bad_alloc);
|
||||
/**
|
||||
* Find by command.
|
||||
*
|
||||
* Parameter command: The command.
|
||||
* Returns: The instance.
|
||||
*/
|
||||
static inverse_key* get_for(const std::string& command) throw(std::bad_alloc);
|
||||
/**
|
||||
* Get keyspec.
|
||||
*
|
||||
* Parameter primary: If true, get the primary key, else secondary key.
|
||||
* Returns: The keyspec.
|
||||
*/
|
||||
std::string get(bool primary) throw(std::bad_alloc);
|
||||
/**
|
||||
* Clear key (if primary is cleared, secondary becomes primary).
|
||||
*
|
||||
* Parameter primary: If true, clear the primary, else the secondary.
|
||||
*/
|
||||
void clear(bool primary) throw(std::bad_alloc);
|
||||
/**
|
||||
* Set key.
|
||||
*
|
||||
* Parameter keyspec: The new keyspec.
|
||||
* Parameter primary: If true, set the primary, else the secondary.
|
||||
*/
|
||||
void set(std::string keyspec, bool primary) throw(std::bad_alloc);
|
||||
/**
|
||||
* Notify updated mapping.
|
||||
*/
|
||||
static void notify_update(const std::string& keyspec, const std::string& command);
|
||||
/**
|
||||
* Get name for command.
|
||||
*
|
||||
* Returns: The name.
|
||||
*/
|
||||
std::string getname() throw(std::bad_alloc);
|
||||
private:
|
||||
inverse_key(const inverse_key&);
|
||||
inverse_key& operator=(const inverse_key&);
|
||||
static std::set<inverse_key*>& ikeys();
|
||||
static std::map<std::string, inverse_key*>& forkey();
|
||||
void addkey(const std::string& keyspec);
|
||||
std::string cmd;
|
||||
std::string oname;
|
||||
std::string primary_spec;
|
||||
std::string secondary_spec;
|
||||
};
|
||||
|
||||
#endif
|
||||
|
|
|
@ -30,6 +30,8 @@ void _runuifun_async(void (*fn)(void*), void* arg);
|
|||
void wxeditor_axes_display(wxWindow* parent);
|
||||
void wxeditor_authors_display(wxWindow* parent);
|
||||
void wxeditor_settings_display(wxWindow* parent);
|
||||
void wxeditor_hotkeys_display(wxWindow* parent);
|
||||
std::string wxeditor_keyselect(wxWindow* parent, bool clearable);
|
||||
|
||||
//Auxillary windows.
|
||||
void wxwindow_memorysearch_display();
|
||||
|
|
|
@ -191,7 +191,7 @@ namespace
|
|||
for(size_t i = 0; i < MAX_LOGICAL_BUTTONS; ++i)
|
||||
for(int j = 0; j < 3; ++j)
|
||||
for(unsigned k = 0; k < 8; ++k) {
|
||||
std::string x, y;
|
||||
std::string x, y, expx;
|
||||
char cstr[2] = {0, 0};
|
||||
cstr[0] = 49 + k;
|
||||
switch(j) {
|
||||
|
@ -207,21 +207,32 @@ namespace
|
|||
};
|
||||
x = x + cstr + get_logical_button_name(i);
|
||||
y = cstr + get_logical_button_name(i);
|
||||
expx = std::string("Controller X ") + get_logical_button_name(i);
|
||||
expx[11] = 49 + k;
|
||||
our_commands.insert(new button_action(x, j, k, y));
|
||||
if(j == 0)
|
||||
our_icommands.insert(new inverse_key(x, expx));
|
||||
}
|
||||
for(unsigned k = 0; k < 8; ++k) {
|
||||
std::string x = "controllerXanalog";
|
||||
std::string expx = "Controller X analog function";
|
||||
x[10] = 49 + k;
|
||||
expx[11] = 49 + k;
|
||||
our_commands.insert(new analog_action(x, k));
|
||||
our_icommands.insert(new inverse_key(x, expx));
|
||||
}
|
||||
}
|
||||
~button_action_helper()
|
||||
{
|
||||
for(auto i : our_commands)
|
||||
delete i;
|
||||
for(auto i : our_icommands)
|
||||
delete i;
|
||||
our_commands.clear();
|
||||
our_icommands.clear();
|
||||
}
|
||||
std::set<command*> our_commands;
|
||||
std::set<inverse_key*> our_icommands;
|
||||
} bah;
|
||||
}
|
||||
|
||||
|
|
|
@ -72,6 +72,13 @@ namespace
|
|||
[]() throw(std::bad_alloc, std::runtime_error) {
|
||||
keymapper::dumpbindings();
|
||||
});
|
||||
|
||||
function_ptr_command<> show_inverse("show-inverse", "Show inverse bindings",
|
||||
"Syntax: show-inverse\nShow inversebindings that are currently active.\n",
|
||||
[]() throw(std::bad_alloc, std::runtime_error) {
|
||||
for(auto i : inverse_key::get_ikeys())
|
||||
messages << i->getname() << ":" << i->get(true) << ":" << i->get(false) << std::endl;
|
||||
});
|
||||
}
|
||||
|
||||
std::string fixup_command_polarity(std::string cmd, bool polarity) throw(std::bad_alloc)
|
||||
|
@ -774,7 +781,11 @@ namespace
|
|||
return k;
|
||||
}
|
||||
|
||||
std::map<triple, keybind_data*> keybindings;
|
||||
std::map<triple, keybind_data*>& keybindings()
|
||||
{
|
||||
static std::map<triple, keybind_data*> x;
|
||||
return x;
|
||||
}
|
||||
}
|
||||
|
||||
void keymapper::bind(std::string mod, std::string modmask, std::string keyname, std::string command)
|
||||
|
@ -786,28 +797,30 @@ void keymapper::bind(std::string mod, std::string modmask, std::string keyname,
|
|||
if(!modifier_set::valid(_mod, _modmask))
|
||||
throw std::runtime_error("Invalid modifiers");
|
||||
auto g = keygroup::lookup(keyname);
|
||||
if(!keybindings.count(k)) {
|
||||
keybindings[k] = new keybind_data;
|
||||
keybindings[k]->mod = _mod;
|
||||
keybindings[k]->modmask = _modmask;
|
||||
keybindings[k]->group = g.first;
|
||||
keybindings[k]->subkey = g.second;
|
||||
if(!keybindings().count(k)) {
|
||||
keybindings()[k] = new keybind_data;
|
||||
keybindings()[k]->mod = _mod;
|
||||
keybindings()[k]->modmask = _modmask;
|
||||
keybindings()[k]->group = g.first;
|
||||
keybindings()[k]->subkey = g.second;
|
||||
}
|
||||
keybindings[k]->command = command;
|
||||
keybindings()[k]->command = command;
|
||||
inverse_key::notify_update(mod + "/" + modmask + "|" + keyname, command);
|
||||
}
|
||||
void keymapper::unbind(std::string mod, std::string modmask, std::string keyname) throw(std::bad_alloc,
|
||||
std::runtime_error)
|
||||
{
|
||||
triple k(mod, modmask, keyname);
|
||||
if(!keybindings.count(k))
|
||||
if(!keybindings().count(k))
|
||||
throw std::runtime_error("Key is not bound");
|
||||
delete keybindings[k];
|
||||
keybindings.erase(k);
|
||||
delete keybindings()[k];
|
||||
keybindings().erase(k);
|
||||
inverse_key::notify_update(mod + "/" + modmask + "|" + keyname, "");
|
||||
}
|
||||
|
||||
void keymapper::dumpbindings() throw(std::bad_alloc)
|
||||
{
|
||||
for(auto i : keybindings) {
|
||||
for(auto i : keybindings()) {
|
||||
messages << "bind-key ";
|
||||
if(i.first.a != "" || i.first.b != "")
|
||||
messages << i.first.a << "/" << i.first.b << " ";
|
||||
|
@ -818,7 +831,7 @@ void keymapper::dumpbindings() throw(std::bad_alloc)
|
|||
std::set<std::string> keymapper::get_bindings() throw(std::bad_alloc)
|
||||
{
|
||||
std::set<std::string> r;
|
||||
for(auto i : keybindings)
|
||||
for(auto i : keybindings())
|
||||
r.insert(i.first.a + "/" + i.first.b + "|" + i.first.c);
|
||||
return r;
|
||||
}
|
||||
|
@ -831,9 +844,9 @@ std::string keymapper::get_command_for(const std::string& keyspec) throw(std::ba
|
|||
} catch(std::exception& e) {
|
||||
return "";
|
||||
}
|
||||
if(!keybindings.count(k))
|
||||
if(!keybindings().count(k))
|
||||
return "";
|
||||
return keybindings[k]->command;
|
||||
return keybindings()[k]->command;
|
||||
}
|
||||
|
||||
void keymapper::bind_for(const std::string& keyspec, const std::string& cmd) throw(std::bad_alloc, std::runtime_error)
|
||||
|
@ -845,3 +858,123 @@ void keymapper::bind_for(const std::string& keyspec, const std::string& cmd) thr
|
|||
else
|
||||
unbind(k.a, k.b, k.c);
|
||||
}
|
||||
|
||||
|
||||
inverse_key::inverse_key(const std::string& command, const std::string& name) throw(std::bad_alloc)
|
||||
{
|
||||
cmd = command;
|
||||
oname = name;
|
||||
ikeys().insert(this);
|
||||
forkey()[cmd] = this;
|
||||
//Search the keybindings for matches.
|
||||
auto b = keymapper::get_bindings();
|
||||
for(auto c : b)
|
||||
if(keymapper::get_command_for(c) == cmd)
|
||||
addkey(c);
|
||||
}
|
||||
|
||||
inverse_key::~inverse_key()
|
||||
{
|
||||
ikeys().erase(this);
|
||||
forkey().erase(cmd);
|
||||
}
|
||||
|
||||
std::set<inverse_key*> inverse_key::get_ikeys() throw(std::bad_alloc)
|
||||
{
|
||||
return ikeys();
|
||||
}
|
||||
|
||||
std::string inverse_key::getname() throw(std::bad_alloc)
|
||||
{
|
||||
return oname;
|
||||
}
|
||||
|
||||
inverse_key* inverse_key::get_for(const std::string& command) throw(std::bad_alloc)
|
||||
{
|
||||
return forkey().count(command) ? forkey()[command] : NULL;
|
||||
}
|
||||
|
||||
std::set<inverse_key*>& inverse_key::ikeys()
|
||||
{
|
||||
static std::set<inverse_key*> x;
|
||||
return x;
|
||||
}
|
||||
|
||||
std::map<std::string, inverse_key*>& inverse_key::forkey()
|
||||
{
|
||||
static std::map<std::string, inverse_key*> x;
|
||||
return x;
|
||||
}
|
||||
|
||||
std::string inverse_key::get(bool primary) throw(std::bad_alloc)
|
||||
{
|
||||
return primary ? primary_spec : secondary_spec;
|
||||
}
|
||||
|
||||
void inverse_key::clear(bool primary) throw(std::bad_alloc)
|
||||
{
|
||||
if(primary) {
|
||||
keymapper::bind_for(primary_spec, "");
|
||||
primary_spec = secondary_spec;
|
||||
secondary_spec = "";
|
||||
} else {
|
||||
keymapper::bind_for(secondary_spec, "");
|
||||
secondary_spec = "";
|
||||
}
|
||||
//Search the keybindings for matches.
|
||||
auto b = keymapper::get_bindings();
|
||||
for(auto c : b)
|
||||
if(keymapper::get_command_for(c) == cmd)
|
||||
addkey(c);
|
||||
}
|
||||
|
||||
void inverse_key::set(std::string keyspec, bool primary) throw(std::bad_alloc)
|
||||
{
|
||||
if(keyspec == "") {
|
||||
clear(primary);
|
||||
return;
|
||||
}
|
||||
if(!primary && (primary_spec == "" || primary_spec == keyspec))
|
||||
primary = true;
|
||||
if(primary) {
|
||||
if(primary_spec != "")
|
||||
keymapper::bind_for(primary_spec, "");
|
||||
primary_spec = keyspec;
|
||||
keymapper::bind_for(primary_spec, cmd);
|
||||
} else {
|
||||
if(secondary_spec != "")
|
||||
keymapper::bind_for(secondary_spec, "");
|
||||
secondary_spec = keyspec;
|
||||
keymapper::bind_for(secondary_spec, cmd);
|
||||
}
|
||||
}
|
||||
|
||||
void inverse_key::addkey(const std::string& keyspec)
|
||||
{
|
||||
if(primary_spec == "" || primary_spec == keyspec)
|
||||
primary_spec = keyspec;
|
||||
else if(secondary_spec == "")
|
||||
secondary_spec = keyspec;
|
||||
}
|
||||
|
||||
void inverse_key::notify_update(const std::string& keyspec, const std::string& command)
|
||||
{
|
||||
for(auto k : ikeys()) {
|
||||
bool u = false;
|
||||
if(k->primary_spec == keyspec || k->secondary_spec == keyspec) {
|
||||
if(command == "" || command != k->cmd) {
|
||||
//Unbound.
|
||||
k->primary_spec = "";
|
||||
k->secondary_spec = "";
|
||||
u = true;
|
||||
}
|
||||
} else if(command == k->cmd)
|
||||
k->addkey(keyspec);
|
||||
if(u) {
|
||||
auto b = keymapper::get_bindings();
|
||||
for(auto c : b)
|
||||
if(keymapper::get_command_for(c) == k->cmd)
|
||||
k->addkey(c);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
@ -430,7 +430,7 @@ namespace
|
|||
});
|
||||
|
||||
function_ptr_command<> save_jukebox_prev("cycle-jukebox-backward", "Cycle save jukebox backwards",
|
||||
"Syntax: cycle-jukebox-backwards\nCycle save jukebox backwards\n",
|
||||
"Syntax: cycle-jukebox-backward\nCycle save jukebox backwards\n",
|
||||
[]() throw(std::bad_alloc, std::runtime_error) {
|
||||
if(save_jukebox_pointer == 0)
|
||||
save_jukebox_pointer = save_jukebox.size() - 1;
|
||||
|
@ -443,7 +443,7 @@ namespace
|
|||
});
|
||||
|
||||
function_ptr_command<> save_jukebox_next("cycle-jukebox-forward", "Cycle save jukebox forwards",
|
||||
"Syntax: cycle-jukebox-forwards\nCycle save jukebox forwards\n",
|
||||
"Syntax: cycle-jukebox-forward\nCycle save jukebox forwards\n",
|
||||
[]() throw(std::bad_alloc, std::runtime_error) {
|
||||
if(save_jukebox_pointer == save_jukebox.size() - 1)
|
||||
save_jukebox_pointer = 0;
|
||||
|
@ -645,6 +645,87 @@ namespace
|
|||
});
|
||||
|
||||
|
||||
inverse_key ipause_emulator("pause-emulator", "(Un)pause");
|
||||
inverse_key ijback("cycle-jukebox-backward", "Cycle slot backwards");
|
||||
inverse_key ijforward("cycle-jukebox-forward", "Cycle slot forwards");
|
||||
inverse_key iloadj("load-jukebox", "load selected slot");
|
||||
inverse_key isavej("save-jukebox", "Save selected slot");
|
||||
inverse_key iadvframe("+advance-frame", "Advance frame");
|
||||
inverse_key iadvsubframe("+advance-poll", "Advance subframe");
|
||||
inverse_key iskiplag("advance-skiplag", "Advance to next poll");
|
||||
inverse_key ireset("reset", "System reset");
|
||||
inverse_key iset_rwmode("set-rwmode", "Switch to read/write");
|
||||
inverse_key itoggle_romode("set-romode", "Switch to read-only");
|
||||
inverse_key itoggle_rwmode("toggle-rwmode", "Toggle read-only");
|
||||
inverse_key irepaint("repaint", "Repaint screen");
|
||||
inverse_key itogglepause("toggle-pause-on-end", "Toggle pause-on-end");
|
||||
inverse_key irewind_movie("rewind-movie", "Rewind movie");
|
||||
inverse_key icancel_saves("cancel-saves", "Cancel pending saves");
|
||||
inverse_key iload1("load ${project}1.lsmv", "Load slot 1");
|
||||
inverse_key iload2("load ${project}2.lsmv", "Load slot 2");
|
||||
inverse_key iload3("load ${project}3.lsmv", "Load slot 3");
|
||||
inverse_key iload4("load ${project}4.lsmv", "Load slot 4");
|
||||
inverse_key iload5("load ${project}5.lsmv", "Load slot 5");
|
||||
inverse_key iload6("load ${project}6.lsmv", "Load slot 6");
|
||||
inverse_key iload7("load ${project}7.lsmv", "Load slot 7");
|
||||
inverse_key iload8("load ${project}8.lsmv", "Load slot 8");
|
||||
inverse_key iload9("load ${project}9.lsmv", "Load slot 9");
|
||||
inverse_key iload10("load ${project}10.lsmv", "Load slot 10");
|
||||
inverse_key iload11("load ${project}11.lsmv", "Load slot 11");
|
||||
inverse_key iload12("load ${project}12.lsmv", "Load slot 12");
|
||||
inverse_key iload13("load ${project}13.lsmv", "Load slot 13");
|
||||
inverse_key iload14("load ${project}14.lsmv", "Load slot 14");
|
||||
inverse_key iload15("load ${project}15.lsmv", "Load slot 15");
|
||||
inverse_key iload16("load ${project}16.lsmv", "Load slot 16");
|
||||
inverse_key iload17("load ${project}17.lsmv", "Load slot 17");
|
||||
inverse_key iload18("load ${project}18.lsmv", "Load slot 18");
|
||||
inverse_key iload19("load ${project}19.lsmv", "Load slot 19");
|
||||
inverse_key iload20("load ${project}20.lsmv", "Load slot 20");
|
||||
inverse_key iload21("load ${project}21.lsmv", "Load slot 21");
|
||||
inverse_key iload22("load ${project}22.lsmv", "Load slot 22");
|
||||
inverse_key iload23("load ${project}23.lsmv", "Load slot 23");
|
||||
inverse_key iload24("load ${project}24.lsmv", "Load slot 24");
|
||||
inverse_key iload25("load ${project}25.lsmv", "Load slot 25");
|
||||
inverse_key iload26("load ${project}26.lsmv", "Load slot 26");
|
||||
inverse_key iload27("load ${project}27.lsmv", "Load slot 27");
|
||||
inverse_key iload28("load ${project}28.lsmv", "Load slot 28");
|
||||
inverse_key iload29("load ${project}29.lsmv", "Load slot 29");
|
||||
inverse_key iload30("load ${project}30.lsmv", "Load slot 30");
|
||||
inverse_key iload31("load ${project}31.lsmv", "Load slot 31");
|
||||
inverse_key iload32("load ${project}32.lsmv", "Load slot 32");
|
||||
inverse_key isave1("save-state ${project}1.lsmv", "Save slot 1");
|
||||
inverse_key isave2("save-state ${project}2.lsmv", "Save slot 2");
|
||||
inverse_key isave3("save-state ${project}3.lsmv", "Save slot 3");
|
||||
inverse_key isave4("save-state ${project}4.lsmv", "Save slot 4");
|
||||
inverse_key isave5("save-state ${project}5.lsmv", "Save slot 5");
|
||||
inverse_key isave6("save-state ${project}6.lsmv", "Save slot 6");
|
||||
inverse_key isave7("save-state ${project}7.lsmv", "Save slot 7");
|
||||
inverse_key isave8("save-state ${project}8.lsmv", "Save slot 8");
|
||||
inverse_key isave9("save-state ${project}9.lsmv", "Save slot 9");
|
||||
inverse_key isave10("save-state ${project}10.lsmv", "Save slot 10");
|
||||
inverse_key isave11("save-state ${project}11.lsmv", "Save slot 11");
|
||||
inverse_key isave12("save-state ${project}12.lsmv", "Save slot 12");
|
||||
inverse_key isave13("save-state ${project}13.lsmv", "Save slot 13");
|
||||
inverse_key isave14("save-state ${project}14.lsmv", "Save slot 14");
|
||||
inverse_key isave15("save-state ${project}15.lsmv", "Save slot 15");
|
||||
inverse_key isave16("save-state ${project}16.lsmv", "Save slot 16");
|
||||
inverse_key isave17("save-state ${project}17.lsmv", "Save slot 17");
|
||||
inverse_key isave18("save-state ${project}18.lsmv", "Save slot 18");
|
||||
inverse_key isave19("save-state ${project}19.lsmv", "Save slot 19");
|
||||
inverse_key isave20("save-state ${project}20.lsmv", "Save slot 20");
|
||||
inverse_key isave21("save-state ${project}21.lsmv", "Save slot 21");
|
||||
inverse_key isave22("save-state ${project}22.lsmv", "Save slot 22");
|
||||
inverse_key isave23("save-state ${project}23.lsmv", "Save slot 23");
|
||||
inverse_key isave24("save-state ${project}24.lsmv", "Save slot 24");
|
||||
inverse_key isave25("save-state ${project}25.lsmv", "Save slot 25");
|
||||
inverse_key isave26("save-state ${project}26.lsmv", "Save slot 26");
|
||||
inverse_key isave27("save-state ${project}27.lsmv", "Save slot 27");
|
||||
inverse_key isave28("save-state ${project}28.lsmv", "Save slot 28");
|
||||
inverse_key isave29("save-state ${project}29.lsmv", "Save slot 29");
|
||||
inverse_key isave30("save-state ${project}30.lsmv", "Save slot 30");
|
||||
inverse_key isave31("save-state ${project}31.lsmv", "Save slot 31");
|
||||
inverse_key isave32("save-state ${project}32.lsmv", "Save slot 32");
|
||||
|
||||
bool on_quit_prompt = false;
|
||||
class mywindowcallbacks : public information_dispatch
|
||||
{
|
||||
|
|
|
@ -140,6 +140,9 @@ namespace
|
|||
throw std::runtime_error("Bad sound setting");
|
||||
});
|
||||
|
||||
inverse_key ienable_sound("enable-sound on", "Enable sound");
|
||||
inverse_key idisable_sound("enable-sound off", "Disable sound");
|
||||
|
||||
function_ptr_command<const std::string&> set_sound_device("set-sound-device", "Set sound device",
|
||||
"Syntax: set-sound-device <id>\nSet sound device to <id>.\n",
|
||||
[](const std::string& args) throw(std::bad_alloc, std::runtime_error) {
|
||||
|
|
365
src/platform/wxwidgets/editor-keyselect.cpp
Normal file
365
src/platform/wxwidgets/editor-keyselect.cpp
Normal file
|
@ -0,0 +1,365 @@
|
|||
#include "platform/wxwidgets/platform.hpp"
|
||||
#include "core/keymapper.hpp"
|
||||
|
||||
#include <wx/wx.h>
|
||||
|
||||
namespace
|
||||
{
|
||||
struct keyentry_mod_data
|
||||
{
|
||||
wxCheckBox* pressed;
|
||||
wxCheckBox* unmasked;
|
||||
unsigned tmpflags;
|
||||
};
|
||||
|
||||
class wxdialog_keyentry : public wxDialog
|
||||
{
|
||||
public:
|
||||
wxdialog_keyentry(wxWindow* parent, const std::string& title, bool clearable);
|
||||
void on_change_setting(wxCommandEvent& e);
|
||||
void on_ok(wxCommandEvent& e);
|
||||
void on_cancel(wxCommandEvent& e);
|
||||
void on_clear(wxCommandEvent& e);
|
||||
std::string getkey();
|
||||
private:
|
||||
std::map<std::string, keyentry_mod_data> modifiers;
|
||||
wxComboBox* mainkey;
|
||||
wxButton* ok;
|
||||
wxButton* cancel;
|
||||
wxButton* clear;
|
||||
bool cleared;
|
||||
};
|
||||
|
||||
class wxdialog_hotkeys;
|
||||
|
||||
class hotkey
|
||||
{
|
||||
public:
|
||||
hotkey(wxdialog_hotkeys* h, wxWindow* win, wxSizer* s, inverse_key* ikey, unsigned o);
|
||||
void update(const std::string& primary, const std::string& secondary);
|
||||
inverse_key* get_associated();
|
||||
std::string get_title();
|
||||
private:
|
||||
wxButton* primaryb;
|
||||
wxButton* secondaryb;
|
||||
inverse_key* associated;
|
||||
std::string title;
|
||||
};
|
||||
|
||||
class wxdialog_hotkeys : public wxDialog
|
||||
{
|
||||
public:
|
||||
wxdialog_hotkeys(wxWindow* parent);
|
||||
~wxdialog_hotkeys();
|
||||
void on_close(wxCommandEvent& e);
|
||||
void on_reconfig(wxCommandEvent& e);
|
||||
private:
|
||||
void update();
|
||||
wxScrolledWindow* scroll;
|
||||
wxSizer* scroll_sizer;
|
||||
std::map<unsigned, hotkey*> hotkeys;
|
||||
wxButton* close;
|
||||
};
|
||||
|
||||
wxdialog_keyentry::wxdialog_keyentry(wxWindow* parent, const std::string& title, bool clearable)
|
||||
: wxDialog(parent, wxID_ANY, towxstring(title), wxDefaultPosition, wxSize(-1, -1))
|
||||
{
|
||||
std::vector<wxString> keych;
|
||||
std::set<std::string> mods, keys;
|
||||
|
||||
cleared = false;
|
||||
runemufn([&mods, &keys]() { mods = modifier::get_set(); keys = keygroup::get_keys(); });
|
||||
Centre();
|
||||
wxFlexGridSizer* top_s = new wxFlexGridSizer(2, 1, 0, 0);
|
||||
SetSizer(top_s);
|
||||
|
||||
wxFlexGridSizer* t_s = new wxFlexGridSizer(mods.size() + 1, 3, 0, 0);
|
||||
for(auto i : mods) {
|
||||
t_s->Add(new wxStaticText(this, wxID_ANY, towxstring(i)), 0, wxGROW);
|
||||
keyentry_mod_data m;
|
||||
t_s->Add(m.pressed = new wxCheckBox(this, wxID_ANY, wxT("Pressed")), 0, wxGROW);
|
||||
t_s->Add(m.unmasked = new wxCheckBox(this, wxID_ANY, wxT("Unmasked")), 0, wxGROW);
|
||||
m.pressed->Disable();
|
||||
modifiers[i] = m;
|
||||
m.pressed->Connect(wxEVT_COMMAND_CHECKBOX_CLICKED,
|
||||
wxCommandEventHandler(wxdialog_keyentry::on_change_setting), NULL, this);
|
||||
m.unmasked->Connect(wxEVT_COMMAND_CHECKBOX_CLICKED,
|
||||
wxCommandEventHandler(wxdialog_keyentry::on_change_setting), NULL, this);
|
||||
}
|
||||
for(auto i : keys)
|
||||
keych.push_back(towxstring(i));
|
||||
t_s->Add(new wxStaticText(this, wxID_ANY, wxT("Key")), 0, wxGROW);
|
||||
t_s->Add(mainkey = new wxComboBox(this, wxID_ANY, keych[0], wxDefaultPosition, wxDefaultSize,
|
||||
keych.size(), &keych[0], wxCB_READONLY), 1, wxGROW);
|
||||
mainkey->Connect(wxEVT_COMMAND_COMBOBOX_SELECTED,
|
||||
wxCommandEventHandler(wxdialog_keyentry::on_change_setting), NULL, this);
|
||||
top_s->Add(t_s);
|
||||
|
||||
wxBoxSizer* pbutton_s = new wxBoxSizer(wxHORIZONTAL);
|
||||
if(clearable)
|
||||
pbutton_s->Add(clear = new wxButton(this, wxID_OK, wxT("Clear")), 0, wxGROW);
|
||||
pbutton_s->AddStretchSpacer();
|
||||
pbutton_s->Add(ok = new wxButton(this, wxID_OK, wxT("OK")), 0, wxGROW);
|
||||
pbutton_s->Add(cancel = new wxButton(this, wxID_CANCEL, wxT("Cancel")), 0, wxGROW);
|
||||
ok->Connect(wxEVT_COMMAND_BUTTON_CLICKED,
|
||||
wxCommandEventHandler(wxdialog_keyentry::on_ok), NULL, this);
|
||||
cancel->Connect(wxEVT_COMMAND_BUTTON_CLICKED,
|
||||
wxCommandEventHandler(wxdialog_keyentry::on_cancel), NULL, this);
|
||||
if(clearable)
|
||||
clear->Connect(wxEVT_COMMAND_BUTTON_CLICKED,
|
||||
wxCommandEventHandler(wxdialog_keyentry::on_clear), NULL, this);
|
||||
top_s->Add(pbutton_s, 0, wxGROW);
|
||||
|
||||
t_s->SetSizeHints(this);
|
||||
top_s->SetSizeHints(this);
|
||||
Fit();
|
||||
}
|
||||
|
||||
#define TMPFLAG_UNMASKED 65
|
||||
#define TMPFLAG_UNMASKED_LINK_CHILD 2
|
||||
#define TMPFLAG_UNMASKED_LINK_PARENT 68
|
||||
#define TMPFLAG_PRESSED 8
|
||||
#define TMPFLAG_PRESSED_LINK_CHILD 16
|
||||
#define TMPFLAG_PRESSED_LINK_PARENT 32
|
||||
|
||||
void wxdialog_keyentry::on_change_setting(wxCommandEvent& e)
|
||||
{
|
||||
for(auto& i : modifiers)
|
||||
i.second.tmpflags = 0;
|
||||
for(auto& i : modifiers) {
|
||||
modifier* m = NULL;
|
||||
try {
|
||||
m = &modifier::lookup(i.first);
|
||||
} catch(...) {
|
||||
i.second.pressed->Disable();
|
||||
i.second.unmasked->Disable();
|
||||
continue;
|
||||
}
|
||||
std::string j = m->linked_name();
|
||||
if(i.second.unmasked->GetValue())
|
||||
i.second.tmpflags |= TMPFLAG_UNMASKED;
|
||||
if(j != "") {
|
||||
if(modifiers[j].unmasked->GetValue())
|
||||
i.second.tmpflags |= TMPFLAG_UNMASKED_LINK_PARENT;
|
||||
if(i.second.unmasked->GetValue())
|
||||
modifiers[j].tmpflags |= TMPFLAG_UNMASKED_LINK_CHILD;
|
||||
}
|
||||
if(i.second.pressed->GetValue())
|
||||
i.second.tmpflags |= TMPFLAG_PRESSED;
|
||||
if(j != "") {
|
||||
if(modifiers[j].pressed->GetValue())
|
||||
i.second.tmpflags |= TMPFLAG_PRESSED_LINK_PARENT;
|
||||
if(i.second.pressed->GetValue())
|
||||
modifiers[j].tmpflags |= TMPFLAG_PRESSED_LINK_CHILD;
|
||||
}
|
||||
}
|
||||
for(auto& i : modifiers) {
|
||||
//Unmasked is to be enabled if neither unmasked link flag is set.
|
||||
if(i.second.tmpflags & ((TMPFLAG_UNMASKED_LINK_CHILD | TMPFLAG_UNMASKED_LINK_PARENT) & ~64)) {
|
||||
i.second.unmasked->SetValue(false);
|
||||
i.second.unmasked->Disable();
|
||||
} else
|
||||
i.second.unmasked->Enable();
|
||||
//Pressed is to be enabled if:
|
||||
//- This modifier is unmasked or parent is unmasked.
|
||||
//- Parent nor child is not pressed.
|
||||
if(((i.second.tmpflags & (TMPFLAG_UNMASKED | TMPFLAG_UNMASKED_LINK_PARENT |
|
||||
TMPFLAG_PRESSED_LINK_CHILD | TMPFLAG_PRESSED_LINK_PARENT)) & 112) == 64)
|
||||
i.second.pressed->Enable();
|
||||
else {
|
||||
i.second.pressed->SetValue(false);
|
||||
i.second.pressed->Disable();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void wxdialog_keyentry::on_ok(wxCommandEvent& e)
|
||||
{
|
||||
EndModal(wxID_OK);
|
||||
}
|
||||
|
||||
void wxdialog_keyentry::on_clear(wxCommandEvent& e)
|
||||
{
|
||||
cleared = true;
|
||||
EndModal(wxID_OK);
|
||||
}
|
||||
|
||||
void wxdialog_keyentry::on_cancel(wxCommandEvent& e)
|
||||
{
|
||||
EndModal(wxID_CANCEL);
|
||||
}
|
||||
|
||||
std::string wxdialog_keyentry::getkey()
|
||||
{
|
||||
if(cleared)
|
||||
return "";
|
||||
std::string x;
|
||||
bool f;
|
||||
f = true;
|
||||
for(auto i : modifiers) {
|
||||
if(i.second.pressed->GetValue()) {
|
||||
if(!f)
|
||||
x = x + ",";
|
||||
f = false;
|
||||
x = x + i.first;
|
||||
}
|
||||
}
|
||||
x = x + "/";
|
||||
f = true;
|
||||
for(auto i : modifiers) {
|
||||
if(i.second.unmasked->GetValue()) {
|
||||
if(!f)
|
||||
x = x + ",";
|
||||
f = false;
|
||||
x = x + i.first;
|
||||
}
|
||||
}
|
||||
x = x + "|" + tostdstring(mainkey->GetValue());
|
||||
return x;
|
||||
}
|
||||
|
||||
wxdialog_hotkeys::wxdialog_hotkeys(wxWindow* parent)
|
||||
: wxDialog(parent, wxID_ANY, wxT("Hotkeys"), wxDefaultPosition, wxSize(-1, -1))
|
||||
{
|
||||
scroll = new wxScrolledWindow(this, wxID_ANY, wxDefaultPosition, wxSize(-1, -1));
|
||||
scroll->SetMinSize(wxSize(-1, 500));
|
||||
|
||||
Centre();
|
||||
wxFlexGridSizer* top_s = new wxFlexGridSizer(2, 1, 0, 0);
|
||||
SetSizer(top_s);
|
||||
scroll_sizer = new wxFlexGridSizer(0, 3, 0, 0);
|
||||
scroll->SetSizer(scroll_sizer);
|
||||
|
||||
//Obtain all the inverses.
|
||||
std::set<inverse_key*> inverses;
|
||||
runemufn([&inverses]() {
|
||||
auto x = inverse_key::get_ikeys();
|
||||
for(auto y : x)
|
||||
inverses.insert(y);
|
||||
});
|
||||
unsigned y = 0;
|
||||
for(auto x : inverses) {
|
||||
hotkeys[y] = new hotkey(this, scroll, scroll_sizer, x, y);
|
||||
y++;
|
||||
}
|
||||
update();
|
||||
|
||||
top_s->Add(scroll);
|
||||
scroll->SetScrollRate(0, 20);
|
||||
wxBoxSizer* pbutton_s = new wxBoxSizer(wxHORIZONTAL);
|
||||
pbutton_s->AddStretchSpacer();
|
||||
pbutton_s->Add(close = new wxButton(this, wxID_CANCEL, wxT("Close")), 0, wxGROW);
|
||||
close->Connect(wxEVT_COMMAND_BUTTON_CLICKED,
|
||||
wxCommandEventHandler(wxdialog_hotkeys::on_close), NULL, this);
|
||||
top_s->Add(pbutton_s, 0, wxGROW);
|
||||
|
||||
scroll_sizer->SetSizeHints(this);
|
||||
top_s->SetSizeHints(this);
|
||||
scroll_sizer->Layout();
|
||||
top_s->Layout();
|
||||
Fit();
|
||||
}
|
||||
|
||||
void wxdialog_hotkeys::on_reconfig(wxCommandEvent& e)
|
||||
{
|
||||
int id = e.GetId();
|
||||
if(id <= wxID_HIGHEST)
|
||||
return;
|
||||
unsigned button = (id - wxID_HIGHEST - 1) / 2;
|
||||
bool primflag = (((id - wxID_HIGHEST - 1) % 2) == 0);
|
||||
if(!hotkeys.count(button))
|
||||
return;
|
||||
wxdialog_keyentry* d = new wxdialog_keyentry(this, "Specify key for " + hotkeys[button]->
|
||||
get_title(), true);
|
||||
if(d->ShowModal() == wxID_CANCEL) {
|
||||
d->Destroy();
|
||||
return;
|
||||
}
|
||||
std::string key = d->getkey();
|
||||
d->Destroy();
|
||||
if(key != "")
|
||||
hotkeys[button]->get_associated()->set(key, primflag);
|
||||
else
|
||||
hotkeys[button]->get_associated()->clear(primflag);
|
||||
update();
|
||||
}
|
||||
|
||||
void wxdialog_hotkeys::update()
|
||||
{
|
||||
std::map<inverse_key*, std::pair<std::string, std::string>> data;
|
||||
runemufn([&data]() {
|
||||
auto x = inverse_key::get_ikeys();
|
||||
for(auto y : x)
|
||||
data[y] = std::make_pair(y->get(true), y->get(false));
|
||||
});
|
||||
for(auto i : hotkeys) {
|
||||
inverse_key* j = i.second->get_associated();
|
||||
if(!data.count(j))
|
||||
continue;
|
||||
auto y = data[j];
|
||||
i.second->update(y.first, y.second);
|
||||
}
|
||||
}
|
||||
|
||||
wxdialog_hotkeys::~wxdialog_hotkeys()
|
||||
{
|
||||
for(auto i : hotkeys)
|
||||
delete i.second;
|
||||
}
|
||||
|
||||
void wxdialog_hotkeys::on_close(wxCommandEvent& e)
|
||||
{
|
||||
EndModal(wxID_OK);
|
||||
}
|
||||
|
||||
hotkey::hotkey(wxdialog_hotkeys* h, wxWindow* win, wxSizer* s, inverse_key* ikey, unsigned o)
|
||||
{
|
||||
title = ikey->getname();
|
||||
s->Add(new wxStaticText(win, wxID_ANY, towxstring(title)), 0, wxGROW);
|
||||
s->Add(primaryb = new wxButton(win, wxID_HIGHEST + 1 + 2 * o, wxT("(none)"), wxDefaultPosition,
|
||||
wxSize(200, -1)), 0, wxGROW);
|
||||
s->Add(secondaryb = new wxButton(win, wxID_HIGHEST + 2 + 2 * o, wxT("(none)"), wxDefaultPosition,
|
||||
wxSize(200, -1)), 0, wxGROW);
|
||||
primaryb->Connect(wxEVT_COMMAND_BUTTON_CLICKED,
|
||||
wxCommandEventHandler(wxdialog_hotkeys::on_reconfig), NULL, h);
|
||||
secondaryb->Connect(wxEVT_COMMAND_BUTTON_CLICKED,
|
||||
wxCommandEventHandler(wxdialog_hotkeys::on_reconfig), NULL, h);
|
||||
associated = ikey;
|
||||
}
|
||||
|
||||
inverse_key* hotkey::get_associated()
|
||||
{
|
||||
return associated;
|
||||
}
|
||||
|
||||
std::string hotkey::get_title()
|
||||
{
|
||||
return title;
|
||||
}
|
||||
|
||||
void hotkey::update(const std::string& primary, const std::string& secondary)
|
||||
{
|
||||
primaryb->SetLabel((primary != "") ? towxstring(primary) : towxstring("(none)"));
|
||||
secondaryb->SetLabel((secondary != "") ? towxstring(secondary) : towxstring("(none)"));
|
||||
}
|
||||
}
|
||||
|
||||
std::string wxeditor_keyselect(wxWindow* parent, bool clearable)
|
||||
{
|
||||
wxdialog_keyentry* d = new wxdialog_keyentry(parent, "Specify key", clearable);
|
||||
if(d->ShowModal() == wxID_CANCEL) {
|
||||
d->Destroy();
|
||||
throw canceled_exception();
|
||||
}
|
||||
std::string key = d->getkey();
|
||||
d->Destroy();
|
||||
return key;
|
||||
}
|
||||
|
||||
void wxeditor_hotkeys_display(wxWindow* parent)
|
||||
{
|
||||
modal_pause_holder hld;
|
||||
wxdialog_hotkeys* d = new wxdialog_hotkeys(parent);
|
||||
d->ShowModal();
|
||||
d->Destroy();
|
||||
}
|
|
@ -72,7 +72,8 @@ enum
|
|||
wxID_EDIT_JUKEBOX,
|
||||
wxID_MEMORY_SEARCH,
|
||||
wxID_CANCEL_SAVES,
|
||||
wxID_LOAD_LIBRARY
|
||||
wxID_LOAD_LIBRARY,
|
||||
wxID_EDIT_HOTKEYS
|
||||
};
|
||||
|
||||
|
||||
|
@ -411,171 +412,6 @@ namespace
|
|||
{
|
||||
runuifun([ahmenu]() { ahmenu->reconfigure(); });
|
||||
}
|
||||
|
||||
struct keyentry_mod_data
|
||||
{
|
||||
wxCheckBox* pressed;
|
||||
wxCheckBox* unmasked;
|
||||
unsigned tmpflags;
|
||||
};
|
||||
|
||||
class wxdialog_keyentry : public wxDialog
|
||||
{
|
||||
public:
|
||||
wxdialog_keyentry(wxWindow* parent);
|
||||
void on_change_setting(wxCommandEvent& e);
|
||||
void on_ok(wxCommandEvent& e);
|
||||
void on_cancel(wxCommandEvent& e);
|
||||
std::string getkey();
|
||||
private:
|
||||
std::map<std::string, keyentry_mod_data> modifiers;
|
||||
wxComboBox* mainkey;
|
||||
wxButton* ok;
|
||||
wxButton* cancel;
|
||||
};
|
||||
|
||||
wxdialog_keyentry::wxdialog_keyentry(wxWindow* parent)
|
||||
: wxDialog(parent, wxID_ANY, wxT("Specify key"), wxDefaultPosition, wxSize(-1, -1))
|
||||
{
|
||||
std::vector<wxString> keych;
|
||||
std::set<std::string> mods, keys;
|
||||
|
||||
runemufn([&mods, &keys]() { mods = modifier::get_set(); keys = keygroup::get_keys(); });
|
||||
Centre();
|
||||
wxFlexGridSizer* top_s = new wxFlexGridSizer(2, 1, 0, 0);
|
||||
SetSizer(top_s);
|
||||
|
||||
wxFlexGridSizer* t_s = new wxFlexGridSizer(mods.size() + 1, 3, 0, 0);
|
||||
for(auto i : mods) {
|
||||
t_s->Add(new wxStaticText(this, wxID_ANY, towxstring(i)), 0, wxGROW);
|
||||
keyentry_mod_data m;
|
||||
t_s->Add(m.pressed = new wxCheckBox(this, wxID_ANY, wxT("Pressed")), 0, wxGROW);
|
||||
t_s->Add(m.unmasked = new wxCheckBox(this, wxID_ANY, wxT("Unmasked")), 0, wxGROW);
|
||||
m.pressed->Disable();
|
||||
modifiers[i] = m;
|
||||
m.pressed->Connect(wxEVT_COMMAND_CHECKBOX_CLICKED,
|
||||
wxCommandEventHandler(wxdialog_keyentry::on_change_setting), NULL, this);
|
||||
m.unmasked->Connect(wxEVT_COMMAND_CHECKBOX_CLICKED,
|
||||
wxCommandEventHandler(wxdialog_keyentry::on_change_setting), NULL, this);
|
||||
}
|
||||
for(auto i : keys)
|
||||
keych.push_back(towxstring(i));
|
||||
t_s->Add(new wxStaticText(this, wxID_ANY, wxT("Key")), 0, wxGROW);
|
||||
t_s->Add(mainkey = new wxComboBox(this, wxID_ANY, keych[0], wxDefaultPosition, wxDefaultSize,
|
||||
keych.size(), &keych[0], wxCB_READONLY), 1, wxGROW);
|
||||
mainkey->Connect(wxEVT_COMMAND_COMBOBOX_SELECTED,
|
||||
wxCommandEventHandler(wxdialog_keyentry::on_change_setting), NULL, this);
|
||||
top_s->Add(t_s);
|
||||
|
||||
wxBoxSizer* pbutton_s = new wxBoxSizer(wxHORIZONTAL);
|
||||
pbutton_s->AddStretchSpacer();
|
||||
pbutton_s->Add(ok = new wxButton(this, wxID_OK, wxT("OK")), 0, wxGROW);
|
||||
pbutton_s->Add(cancel = new wxButton(this, wxID_CANCEL, wxT("Cancel")), 0, wxGROW);
|
||||
ok->Connect(wxEVT_COMMAND_BUTTON_CLICKED,
|
||||
wxCommandEventHandler(wxdialog_keyentry::on_ok), NULL, this);
|
||||
cancel->Connect(wxEVT_COMMAND_BUTTON_CLICKED,
|
||||
wxCommandEventHandler(wxdialog_keyentry::on_cancel), NULL, this);
|
||||
top_s->Add(pbutton_s, 0, wxGROW);
|
||||
|
||||
t_s->SetSizeHints(this);
|
||||
top_s->SetSizeHints(this);
|
||||
Fit();
|
||||
}
|
||||
|
||||
#define TMPFLAG_UNMASKED 65
|
||||
#define TMPFLAG_UNMASKED_LINK_CHILD 2
|
||||
#define TMPFLAG_UNMASKED_LINK_PARENT 68
|
||||
#define TMPFLAG_PRESSED 8
|
||||
#define TMPFLAG_PRESSED_LINK_CHILD 16
|
||||
#define TMPFLAG_PRESSED_LINK_PARENT 32
|
||||
|
||||
void wxdialog_keyentry::on_change_setting(wxCommandEvent& e)
|
||||
{
|
||||
for(auto& i : modifiers)
|
||||
i.second.tmpflags = 0;
|
||||
for(auto& i : modifiers) {
|
||||
modifier* m = NULL;
|
||||
try {
|
||||
m = &modifier::lookup(i.first);
|
||||
} catch(...) {
|
||||
i.second.pressed->Disable();
|
||||
i.second.unmasked->Disable();
|
||||
continue;
|
||||
}
|
||||
std::string j = m->linked_name();
|
||||
if(i.second.unmasked->GetValue())
|
||||
i.second.tmpflags |= TMPFLAG_UNMASKED;
|
||||
if(j != "") {
|
||||
if(modifiers[j].unmasked->GetValue())
|
||||
i.second.tmpflags |= TMPFLAG_UNMASKED_LINK_PARENT;
|
||||
if(i.second.unmasked->GetValue())
|
||||
modifiers[j].tmpflags |= TMPFLAG_UNMASKED_LINK_CHILD;
|
||||
}
|
||||
if(i.second.pressed->GetValue())
|
||||
i.second.tmpflags |= TMPFLAG_PRESSED;
|
||||
if(j != "") {
|
||||
if(modifiers[j].pressed->GetValue())
|
||||
i.second.tmpflags |= TMPFLAG_PRESSED_LINK_PARENT;
|
||||
if(i.second.pressed->GetValue())
|
||||
modifiers[j].tmpflags |= TMPFLAG_PRESSED_LINK_CHILD;
|
||||
}
|
||||
}
|
||||
for(auto& i : modifiers) {
|
||||
//Unmasked is to be enabled if neither unmasked link flag is set.
|
||||
if(i.second.tmpflags & ((TMPFLAG_UNMASKED_LINK_CHILD | TMPFLAG_UNMASKED_LINK_PARENT) & ~64)) {
|
||||
i.second.unmasked->SetValue(false);
|
||||
i.second.unmasked->Disable();
|
||||
} else
|
||||
i.second.unmasked->Enable();
|
||||
//Pressed is to be enabled if:
|
||||
//- This modifier is unmasked or parent is unmasked.
|
||||
//- Parent nor child is not pressed.
|
||||
if(((i.second.tmpflags & (TMPFLAG_UNMASKED | TMPFLAG_UNMASKED_LINK_PARENT |
|
||||
TMPFLAG_PRESSED_LINK_CHILD | TMPFLAG_PRESSED_LINK_PARENT)) & 112) == 64)
|
||||
i.second.pressed->Enable();
|
||||
else {
|
||||
i.second.pressed->SetValue(false);
|
||||
i.second.pressed->Disable();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void wxdialog_keyentry::on_ok(wxCommandEvent& e)
|
||||
{
|
||||
EndModal(wxID_OK);
|
||||
}
|
||||
|
||||
void wxdialog_keyentry::on_cancel(wxCommandEvent& e)
|
||||
{
|
||||
EndModal(wxID_CANCEL);
|
||||
}
|
||||
|
||||
std::string wxdialog_keyentry::getkey()
|
||||
{
|
||||
std::string x;
|
||||
bool f;
|
||||
f = true;
|
||||
for(auto i : modifiers) {
|
||||
if(i.second.pressed->GetValue()) {
|
||||
if(!f)
|
||||
x = x + ",";
|
||||
f = false;
|
||||
x = x + i.first;
|
||||
}
|
||||
}
|
||||
x = x + "/";
|
||||
f = true;
|
||||
for(auto i : modifiers) {
|
||||
if(i.second.unmasked->GetValue()) {
|
||||
if(!f)
|
||||
x = x + ",";
|
||||
f = false;
|
||||
x = x + i.first;
|
||||
}
|
||||
}
|
||||
x = x + "|" + tostdstring(mainkey->GetValue());
|
||||
return x;
|
||||
}
|
||||
}
|
||||
|
||||
void boot_emulator(loaded_rom& rom, moviefile& movie)
|
||||
|
@ -829,6 +665,7 @@ wxwin_mainwindow::wxwin_mainwindow()
|
|||
menu_start(wxT("Settings"));
|
||||
menu_entry(wxID_EDIT_AXES, wxT("Configure axes"));
|
||||
menu_entry(wxID_EDIT_SETTINGS, wxT("Configure settings"));
|
||||
menu_entry(wxID_EDIT_HOTKEYS, wxT("Configure hotkeys"));
|
||||
menu_entry(wxID_EDIT_KEYBINDINGS, wxT("Configure keybindings"));
|
||||
menu_entry(wxID_EDIT_ALIAS, wxT("Configure aliases"));
|
||||
menu_entry(wxID_EDIT_JUKEBOX, wxT("Configure jukebox"));
|
||||
|
@ -986,6 +823,9 @@ void wxwin_mainwindow::handle_menu_click_cancelable(wxCommandEvent& e)
|
|||
case wxID_EDIT_SETTINGS:
|
||||
wxeditor_settings_display(this);
|
||||
return;
|
||||
case wxID_EDIT_HOTKEYS:
|
||||
wxeditor_hotkeys_display(this);
|
||||
return;
|
||||
case wxID_EDIT_KEYBINDINGS: {
|
||||
modal_pause_holder hld;
|
||||
std::set<std::string> bind;
|
||||
|
@ -995,15 +835,8 @@ void wxwin_mainwindow::handle_menu_click_cancelable(wxCommandEvent& e)
|
|||
for(auto i : bind)
|
||||
choices.push_back(i);
|
||||
std::string key = pick_among(this, "Select binding", "Select keybinding to edit", choices);
|
||||
if(key == NEW_KEYBINDING) {
|
||||
wxdialog_keyentry* d2 = new wxdialog_keyentry(this);
|
||||
if(d2->ShowModal() == wxID_CANCEL) {
|
||||
d2->Destroy();
|
||||
throw canceled_exception();
|
||||
}
|
||||
key = d2->getkey();
|
||||
d2->Destroy();
|
||||
}
|
||||
if(key == NEW_KEYBINDING)
|
||||
key = wxeditor_keyselect(this, false);
|
||||
std::string old_command_value;
|
||||
runemufn([&old_command_value, key]() { old_command_value = keymapper::get_command_for(key); });
|
||||
std::string newcommand = pick_text(this, "Edit binding", "Enter new command for binding:",
|
||||
|
|
Loading…
Add table
Reference in a new issue