Lua: Fix type confusion between signed and unsigned
[lsnes.git] / include / library / keyboard-mapper.hpp
blob7cb71586f1197ae0a45ec05ad7475f3619e9e887
1 #ifndef _library__keyboard_mapper__hpp__included__
2 #define _library__keyboard_mapper__hpp__included__
4 #include <set>
5 #include <list>
6 #include <stdexcept>
7 #include <string>
8 #include "keyboard.hpp"
10 namespace command
12 class group;
15 namespace keyboard
17 class invbind;
18 class ctrlrkey;
20 std::pair<key*, unsigned> keymapper_lookup_subkey(keyboard& kbd, const std::string& name,
21 bool axis) throw(std::bad_alloc, std::runtime_error);
23 /**
24 * Key specifier
26 struct keyspec
28 /**
29 * Create a new key specifier (invalid).
31 keyspec() throw(std::bad_alloc);
32 /**
33 * Create a new key specifier from keyspec.
35 * Parameter keyspec: The key specifier.
37 keyspec(const std::string& keyspec) throw(std::bad_alloc, std::runtime_error);
38 /**
39 * Get the key specifier as a keyspec.
41 operator std::string() throw(std::bad_alloc);
42 /**
43 * Is valid?
45 operator bool() throw();
46 /**
47 * Is not valid?
49 bool operator!() throw();
50 /**
51 * Clear the keyspec.
53 void clear() throw();
54 /**
55 * Compare for equality.
57 bool operator==(const keyspec& keyspec);
58 /**
59 * Compare for not-equality.
61 bool operator!=(const keyspec& keyspec);
62 /**
63 * The modifier.
65 std::string mod;
66 /**
67 * The mask.
69 std::string mask;
70 /**
71 * The key itself.
73 std::string key;
76 class invbind_set;
77 class invbind_info;
79 class invbind_info;
81 /**
82 * Inverse bind set.
84 class invbind_set
86 public:
87 /**
88 * Set add/drop listener.
90 class listener
92 public:
93 /**
94 * Dtor.
96 virtual ~listener();
97 /**
98 * New item in set.
100 virtual void create(invbind_set& s, const std::string& name, invbind_info& ibinfo) = 0;
102 * Deleted item from set.
104 virtual void destroy(invbind_set& s, const std::string& name) = 0;
106 * Destroyed the entiere set.
108 virtual void kill(invbind_set& s) = 0;
111 * Create a set.
113 invbind_set();
115 * Destructor.
117 ~invbind_set();
119 * Register a inverse bind.
121 void do_register(const std::string& name, invbind_info& info);
123 * Unregister a inverse bind.
125 void do_unregister(const std::string& name, invbind_info& info);
127 * Add a callback on new invese bind.
129 void add_callback(listener& listener) throw(std::bad_alloc);
131 * Drop a callback on new inverse bind.
133 void drop_callback(listener& listener);
137 * Keyboard mapper. Maps keyboard keys into commands.
139 class mapper : public event_listener
141 public:
143 * Create new keyboard mapper.
145 mapper(keyboard& kbd, command::group& domain) throw(std::bad_alloc);
147 * Destroy a keyboard mapper.
149 ~mapper() throw();
151 * Binds a key, erroring out if binding would conflict with existing one.
153 * parameter mod: Modifier set to require to be pressed.
154 * parameter modmask: Modifier set to take into account.
155 * parameter keyname: Key to bind the action to.
156 * parameter command: The command to bind.
157 * throws std::bad_alloc: Not enough memory.
158 * throws std::runtime_error: The binding would conflict with existing one or invalid modifier/key.
160 void bind(std::string mod, std::string modmask, std::string keyname, std::string command)
161 throw(std::bad_alloc, std::runtime_error);
163 * Unbinds a key, erroring out if binding does not exist.
165 * parameter mod: Modifier set to require to be pressed.
166 * parameter modmask: Modifier set to take into account.
167 * parameter keyname: Key to bind the action to.
168 * throws std::bad_alloc: Not enough memory.
169 * throws std::runtime_error: The binding does not exist.
171 void unbind(std::string mod, std::string modmask, std::string keyname) throw(std::bad_alloc,
172 std::runtime_error);
174 * Get keys bound.
176 * Returns: The set of keyspecs that are bound.
178 std::list<keyspec> get_bindings() throw(std::bad_alloc);
180 * Get command for key.
182 std::string get(const keyspec& keyspec) throw(std::bad_alloc);
184 * Bind command for key.
186 * Parameter keyspec: The key specifier to bind to.
187 * Parameter cmd: The command to bind. If "", the key is unbound.
189 void set(const keyspec& keyspec, const std::string& cmd) throw(std::bad_alloc, std::runtime_error);
191 * Get set of inverse binds.
193 * Returns: The set of all inverses.
195 std::set<invbind*> get_inverses() throw(std::bad_alloc);
197 * Find inverse bind by command.
199 * Parameter command: The command.
200 * Returns: The inverse bind, or NULL if none.
202 invbind* get_inverse(const std::string& command) throw(std::bad_alloc);
204 * Get set of controller keys.
206 * Returns: The set of all controller keys.
208 std::set<ctrlrkey*> get_controller_keys() throw(std::bad_alloc);
210 * Get specific controller key.
212 ctrlrkey* get_controllerkey(const std::string& command) throw(std::bad_alloc);
214 * Get list of controller keys for specific keyboard key.
216 std::list<ctrlrkey*> get_controllerkeys_kbdkey(key* kbdkey) throw(std::bad_alloc);
218 * Register inverse bind.
220 void do_register(const std::string& name, invbind& bind) throw(std::bad_alloc);
222 * Unregister inverse bind.
224 void do_unregister(const std::string& name, invbind& bind) throw(std::bad_alloc);
226 * Register controller key.
228 void do_register(const std::string& name, ctrlrkey& ckey) throw(std::bad_alloc);
230 * Unregister inverse bind.
232 void do_unregister(const std::string& name, ctrlrkey& ckey) throw(std::bad_alloc);
234 * Get keyboard.
236 keyboard& get_keyboard() throw();
238 * Get command group to run commands in..
240 command::group& get_command_group() throw();
242 * Fixup command based on polarity.
244 * Parameter cmd: The raw command.
245 * Parameter polarity: Polarity (true is rising edge, false is falling edge).
246 * Returns: The fixed command, or "" if nothing should be run.
248 static std::string fixup_command_polarity(std::string cmd, bool polarity) throw(std::bad_alloc);
250 * Add a set of inverse binds.
252 void add_invbind_set(invbind_set& set);
254 * Drop a set of inverse binds.
256 void drop_invbind_set(invbind_set& set);
258 * Key triplet.
260 struct triplet
262 triplet(modifier_set mod, modifier_set mask, key& kkey, unsigned subkey);
263 triplet(key& kkey, unsigned subkey);
264 triplet(keyboard& k, const keyspec& spec);
265 bool operator<(const struct triplet& a) const;
266 bool operator==(const struct triplet& a) const;
267 bool operator<=(const struct triplet& a) const { return !(a > *this); }
268 bool operator!=(const struct triplet& a) const { return !(a == *this); }
269 bool operator>=(const struct triplet& a) const { return !(a < *this); }
270 bool operator>(const struct triplet& a) const { return (a < *this); }
271 keyspec as_keyspec() const throw(std::bad_alloc);
272 bool index;
273 modifier_set mod;
274 modifier_set mask;
275 key* _key;
276 unsigned subkey;
278 private:
279 class listener : public invbind_set::listener
281 public:
282 listener(mapper& _grp);
283 ~listener();
284 void create(invbind_set& s, const std::string& name, invbind_info& ibinfo);
285 void destroy(invbind_set& s, const std::string& name);
286 void kill(invbind_set& s);
287 private:
288 mapper& grp;
289 } _listener;
290 void change_command(const keyspec& spec, const std::string& old, const std::string& newc);
291 void on_key_event(modifier_set& mods, key& key, event& event);
292 void on_key_event_subkey(modifier_set& mods, key& key, unsigned skey, bool polarity);
293 mapper(const mapper&);
294 mapper& operator=(const mapper&);
295 std::set<key*> listening;
296 keyboard& kbd;
297 command::group& domain;
302 * Inverse bind info.
304 class invbind_info
306 public:
308 * Create inverse bind.
310 * Parameter set: The set to be in.
311 * Parameter _command: Command this is for.
312 * Parameter _name: Name of inverse key.
314 invbind_info(invbind_set& set, const std::string& _command, const std::string& _name)
315 throw(std::bad_alloc);
317 * Destructor.
319 ~invbind_info() throw();
321 * Make inverse bind out of this.
323 invbind* make(mapper& m);
325 * Notify set dying.
327 void set_died();
328 private:
329 invbind_set* in_set;
330 std::string command;
331 std::string name;
335 * Inverse bind. Can map up to 2 keys to some command (and follows forward binds).
337 class invbind
339 public:
341 * Create inverse bind.
343 * Parameter mapper: The keyboard mapper to follow.
344 * Parameter command: Command this is for.
345 * Parameter name: Name of inverse key.
347 invbind(mapper& kmapper, const std::string& command, const std::string& name, bool dynamic = false)
348 throw(std::bad_alloc);
350 * Destructor.
352 ~invbind() throw();
354 * Get keyspec.
356 * Parameter index: Index of the keyspec to get.
357 * Returns: The keyspec.
359 keyspec get(unsigned index) throw(std::bad_alloc);
361 * Clear key (subsequent keys fill the gap).
363 * Parameter index: Index of key to clear.
365 void clear(unsigned index) throw(std::bad_alloc);
367 * Add key to set.
369 * Parameter keyspec: The new keyspec.
371 void append(const keyspec& keyspec) throw(std::bad_alloc);
373 * Get name for command.
375 * Returns: The name.
377 std::string getname() throw(std::bad_alloc);
379 * Notify mapper dying.
381 void mapper_died();
382 private:
383 friend class mapper;
384 invbind(const invbind&);
385 invbind& operator=(const invbind&);
386 void addkey(const keyspec& keyspec);
387 mapper* _mapper;
388 std::string cmd;
389 std::string oname;
390 std::vector<keyspec> specs;
391 bool is_dynamic;
395 * A controller key.
397 * Can overlap with any other bind.
399 class ctrlrkey : public event_listener
401 public:
403 * Create a new controller key.
405 * Parameter mapper: The keyboard mapper to follow.
406 * Parameter command: Command to run.
407 * Parameter name: Name of controller key.
408 * Parameter axis: If true, create a axis-type key.
410 ctrlrkey(mapper& kmapper, const std::string& command, const std::string& name,
411 bool axis = false) throw(std::bad_alloc);
413 * Destructor.
415 ~ctrlrkey() throw();
417 * Get the trigger key.
419 std::pair<key*, unsigned> get(unsigned index) throw();
421 * Get the trigger key.
423 std::string get_string(unsigned index) throw(std::bad_alloc);
425 * Set the trigger key (appends).
427 void append(key* key, unsigned subkey) throw();
429 * Set the trigger key (appends).
431 void append(const std::string& key) throw(std::bad_alloc, std::runtime_error);
433 * Remove the trigger key.
435 void remove(key* key, unsigned subkey) throw();
437 * Get the command.
439 const std::string& get_command() const throw() { return cmd; }
441 * Get the name.
443 const std::string& get_name() const throw() { return oname; }
445 * Is axis-type?
447 bool is_axis() const throw() { return axis; }
448 private:
449 void on_key_event(modifier_set& mods, key& key, event& event);
450 mapper& _mapper;
451 std::string cmd;
452 std::string oname;
453 std::vector<std::pair<key*, unsigned>> keys;
454 bool axis;
458 #endif