diff options
author | Mark Tiefenbruck <mark@fluxbox.org> | 2008-10-04 05:59:14 (GMT) |
---|---|---|
committer | Mark Tiefenbruck <mark@fluxbox.org> | 2008-10-04 05:59:14 (GMT) |
commit | 22f3df9aa81efc071cb13d43a372ead97548eebc (patch) | |
tree | 7aebd6ceca68ab4b7a723ac4d2370239c59afde1 /src | |
parent | c91926cf71dcaaea2cf6e56e74b1de50ff17f6f5 (diff) | |
download | fluxbox_pavel-22f3df9aa81efc071cb13d43a372ead97548eebc.zip fluxbox_pavel-22f3df9aa81efc071cb13d43a372ead97548eebc.tar.bz2 |
break keychains after an invalid key is pressed (which unfortunately will be swallowed)
Diffstat (limited to 'src')
-rw-r--r-- | src/Keys.cc | 15 | ||||
-rw-r--r-- | src/Keys.hh | 5 | ||||
-rw-r--r-- | src/Screen.cc | 5 |
3 files changed, 13 insertions, 12 deletions
diff --git a/src/Keys.cc b/src/Keys.cc index 05f1747..658820e 100644 --- a/src/Keys.cc +++ b/src/Keys.cc | |||
@@ -170,7 +170,9 @@ Keys::t_key::~t_key() { | |||
170 | 170 | ||
171 | 171 | ||
172 | 172 | ||
173 | Keys::Keys(): m_reloader(new FbTk::AutoReloadHelper()), next_key(0) { | 173 | Keys::Keys(): |
174 | m_reloader(new FbTk::AutoReloadHelper()), | ||
175 | next_key(0), saved_keymode(0) { | ||
174 | m_reloader->setReloadCmd(FbTk::RefCount<FbTk::Command<void> >(new FbTk::SimpleCommand<Keys>(*this, &Keys::reload))); | 176 | m_reloader->setReloadCmd(FbTk::RefCount<FbTk::Command<void> >(new FbTk::SimpleCommand<Keys>(*this, &Keys::reload))); |
175 | } | 177 | } |
176 | 178 | ||
@@ -187,6 +189,7 @@ void Keys::deleteTree() { | |||
187 | delete map_it->second; | 189 | delete map_it->second; |
188 | m_map.clear(); | 190 | m_map.clear(); |
189 | next_key = 0; | 191 | next_key = 0; |
192 | saved_keymode = 0; | ||
190 | } | 193 | } |
191 | 194 | ||
192 | // keys are only grabbed in global context | 195 | // keys are only grabbed in global context |
@@ -504,22 +507,16 @@ bool Keys::doAction(int type, unsigned int mods, unsigned int key, | |||
504 | if (!temp_key && isdouble) | 507 | if (!temp_key && isdouble) |
505 | temp_key = next_key->find(type, mods, key, context, false); | 508 | temp_key = next_key->find(type, mods, key, context, false); |
506 | 509 | ||
507 | // need to save this for emacs-style keybindings | ||
508 | static t_key *saved_keymode = 0; | ||
509 | |||
510 | // grab "None Escape" to exit keychain in the middle | ||
511 | unsigned int esc = FbTk::KeyUtil::getKey("Escape"); | ||
512 | |||
513 | if (temp_key && !temp_key->keylist.empty()) { // emacs-style | 510 | if (temp_key && !temp_key->keylist.empty()) { // emacs-style |
514 | if (!saved_keymode) | 511 | if (!saved_keymode) |
515 | saved_keymode = m_keylist; | 512 | saved_keymode = m_keylist; |
516 | next_key = temp_key; | 513 | next_key = temp_key; |
517 | setKeyMode(next_key); | 514 | setKeyMode(next_key); |
518 | grabKey(esc,0); | ||
519 | return true; | 515 | return true; |
520 | } | 516 | } |
521 | if (!temp_key || *temp_key->m_command == 0) { | 517 | if (!temp_key || *temp_key->m_command == 0) { |
522 | if (type == KeyPress && key == esc && mods == 0) { | 518 | if (type == KeyPress && |
519 | !FbTk::KeyUtil::instance().keycodeToModmask(key)) { | ||
523 | // if we're in the middle of an emacs-style keychain, exit it | 520 | // if we're in the middle of an emacs-style keychain, exit it |
524 | next_key = 0; | 521 | next_key = 0; |
525 | if (saved_keymode) { | 522 | if (saved_keymode) { |
diff --git a/src/Keys.hh b/src/Keys.hh index 03a15dd..9502643 100644 --- a/src/Keys.hh +++ b/src/Keys.hh | |||
@@ -83,6 +83,9 @@ public: | |||
83 | */ | 83 | */ |
84 | void reconfigure(); | 84 | void reconfigure(); |
85 | void keyMode(const std::string& keyMode); | 85 | void keyMode(const std::string& keyMode); |
86 | |||
87 | bool inKeychain() const { return saved_keymode != 0; } | ||
88 | |||
86 | private: | 89 | private: |
87 | class t_key; // helper class to build a 'keytree' | 90 | class t_key; // helper class to build a 'keytree' |
88 | typedef std::map<std::string, t_key *> keyspace_t; | 91 | typedef std::map<std::string, t_key *> keyspace_t; |
@@ -109,7 +112,7 @@ private: | |||
109 | keyspace_t m_map; | 112 | keyspace_t m_map; |
110 | 113 | ||
111 | // former doAction static var, we need to access it from deleteTree | 114 | // former doAction static var, we need to access it from deleteTree |
112 | t_key *next_key; | 115 | t_key *next_key, *saved_keymode; |
113 | 116 | ||
114 | WindowMap m_window_map; | 117 | WindowMap m_window_map; |
115 | HandlerMap m_handler_map; | 118 | HandlerMap m_handler_map; |
diff --git a/src/Screen.cc b/src/Screen.cc index 892afda..49b631d 100644 --- a/src/Screen.cc +++ b/src/Screen.cc | |||
@@ -856,6 +856,7 @@ void BScreen::keyPressEvent(XKeyEvent &ke) { | |||
856 | if (Fluxbox::instance()->keys()->doAction(ke.type, ke.state, ke.keycode, | 856 | if (Fluxbox::instance()->keys()->doAction(ke.type, ke.state, ke.keycode, |
857 | Keys::GLOBAL|Keys::ON_DESKTOP)) | 857 | Keys::GLOBAL|Keys::ON_DESKTOP)) |
858 | // re-grab keyboard, so we don't pass KeyRelease to clients | 858 | // re-grab keyboard, so we don't pass KeyRelease to clients |
859 | // also for catching invalid keys in the middle of keychains | ||
859 | FbTk::EventManager::instance()->grabKeyboard(rootWindow().window()); | 860 | FbTk::EventManager::instance()->grabKeyboard(rootWindow().window()); |
860 | 861 | ||
861 | } | 862 | } |
@@ -871,8 +872,8 @@ void BScreen::keyReleaseEvent(XKeyEvent &ke) { | |||
871 | m_cycling = false; | 872 | m_cycling = false; |
872 | focusControl().stopCyclingFocus(); | 873 | focusControl().stopCyclingFocus(); |
873 | } | 874 | } |
874 | 875 | if (!Fluxbox::instance()->keys()->inKeychain()) | |
875 | FbTk::EventManager::instance()->ungrabKeyboard(); | 876 | FbTk::EventManager::instance()->ungrabKeyboard(); |
876 | } | 877 | } |
877 | 878 | ||
878 | void BScreen::buttonPressEvent(XButtonEvent &be) { | 879 | void BScreen::buttonPressEvent(XButtonEvent &be) { |