Merge lp:~attente/compiz/plugin-actions into lp:compiz/0.9.11

Proposed by William Hua
Status: Merged
Approved by: Christopher Townsend
Approved revision: 3823
Merged at revision: 3817
Proposed branch: lp:~attente/compiz/plugin-actions
Merge into: lp:compiz/0.9.11
Diff against target: 832 lines (+309/-144)
8 files modified
include/core/abiversion.h (+1/-1)
include/core/action.h (+27/-12)
include/core/plugin.h (+24/-0)
src/action.cpp (+53/-10)
src/event.cpp (+183/-116)
src/plugin.cpp (+6/-0)
src/plugin/tests/test-plugin.cpp (+0/-5)
src/privatescreen.h (+15/-0)
To merge this branch: bzr merge lp:~attente/compiz/plugin-actions
Reviewer Review Type Date Requested Status
PS Jenkins bot (community) continuous-integration Approve
Christopher Townsend Approve
Marco Trevisan (Treviño) Approve
Review via email: mp+200307@code.launchpad.net

Commit message

Add an interface for plugins to provide non-option key actions that can be triggered.

Description of the change

Add an interface for plugins to provide non-option key actions that can be triggered.

To post a comment you must log in.
Revision history for this message
PS Jenkins bot (ps-jenkins) wrote :
review: Needs Fixing (continuous-integration)
Revision history for this message
Christopher Townsend (townsend) wrote :

Gmock already has a class named CompAction that is interfering with your newly created CompAction class. This is causing build failures when building the compiz_plugin_test.

Please rename your new class to something like CompizAction to avoid this.

Thanks!

review: Needs Fixing
Revision history for this message
Christopher Townsend (townsend) wrote :

Also, I don't quite understand what this change is for and how to test it. What am I expecting it to do?

Revision history for this message
William Hua (attente) wrote :

Thanks, Christopher, I'll fix the CompAction problem, as well as another bug I'm currently encountering with the branch.

Right now, (afaict) the only way for a key CompAction to be triggered is if it's set as the value of a CompOption returned by a Compiz plugin's getOptions () method. So this branch should allow plugins to return a list of key actions which are not necessarily plugin options, and those actions will be appropriately triggered by the event handling code.

I needed this because I've been trying to implement the GNOME key grabber in Unity, which will allow us to stop using passive key grabs in gnome-settings-daemon which conflict with Compiz. I have an initial implementation (there's still a couple of issues I'm trying to fix): https://launchpad.net/~attente/+archive/gnome-key-grabber.

Revision history for this message
Christopher Townsend (townsend) wrote :

Ok, thanks for the explanation. I have heard here and there about these changes but I'm not well versed on it. So it seems it really can't be tested until all the pieces are in place.

Once you update the branch, we'll review the code and make sure it builds, runs, etc.

lp:~attente/compiz/plugin-actions updated
3820. By William Hua

Fix test errors.

Revision history for this message
PS Jenkins bot (ps-jenkins) wrote :
review: Needs Fixing (continuous-integration)
lp:~attente/compiz/plugin-actions updated
3821. By William Hua

Merge trunk.

Revision history for this message
PS Jenkins bot (ps-jenkins) wrote :
review: Approve (continuous-integration)
Revision history for this message
Marco Trevisan (Treviño) (3v1n0) wrote :

40 + class Class {
41 + public:
42 + virtual ~Class() {}
43 + virtual Vector & getActions () = 0;
44 + };

No better name? Also, wouldn't make sense to return a const& instead?

Revision history for this message
William Hua (attente) wrote :

I just realized, adding those const qualifiers to the CompAction public API may break Compiz consumers... is this something we're ok with doing? Anyone who uses those CompAction member functions will be safe, however we would break anyone who tried to re-implement those functions in a subclass...

lp:~attente/compiz/plugin-actions updated
3822. By William Hua

Rename CompAction::Class -> CompAction::Container

Revision history for this message
William Hua (attente) wrote :

Hi Marco, I tried to const-correct that, but it seems not possible to make getActions return a const Vector &. The reason is because the initiate and terminate callbacks of CompAction require a non-const pointer to the CompAction object, and there are places in Unity which call non-const member functions on that pointer.

Revision history for this message
PS Jenkins bot (ps-jenkins) wrote :
review: Approve (continuous-integration)
Revision history for this message
Marco Trevisan (Treviño) (3v1n0) wrote :

Ok, that's fine then.

review: Approve
Revision history for this message
Christopher Townsend (townsend) wrote :

Hi William,

This is indeed an ABI break. We'll need to update the ABI version in Compiz to reflect this. To do this:

1. Open include/core/abiversion.h
2. Replace the value of CORE_ABIVERSION to today's date in form of yyyymmdd.

Other than that, this looks good. Once you get the ABI version change in, we'll top approve.

Thanks!

lp:~attente/compiz/plugin-actions updated
3823. By William Hua

Bump ABI version.

Revision history for this message
William Hua (attente) wrote :

Great, thanks guys! If we need any last minute changes, just let me know!

Revision history for this message
Christopher Townsend (townsend) wrote :

Ok, looks good to me as well.

review: Approve
Revision history for this message
PS Jenkins bot (ps-jenkins) wrote :
review: Approve (continuous-integration)

Preview Diff

[H/L] Next/Prev Comment, [J/K] Next/Prev File, [N/P] Next/Prev Hunk
=== modified file 'include/core/abiversion.h'
--- include/core/abiversion.h 2013-11-05 18:51:36 +0000
+++ include/core/abiversion.h 2014-01-23 16:45:20 +0000
@@ -5,6 +5,6 @@
5# error Conflicting definitions of CORE_ABIVERSION5# error Conflicting definitions of CORE_ABIVERSION
6#endif6#endif
77
8#define CORE_ABIVERSION 201311058#define CORE_ABIVERSION 20140123
99
10#endif // COMPIZ_ABIVERSION_H10#endif // COMPIZ_ABIVERSION_H
1111
=== modified file 'include/core/action.h'
--- include/core/action.h 2012-10-11 10:12:05 +0000
+++ include/core/action.h 2014-01-23 16:45:20 +0000
@@ -32,8 +32,6 @@
3232
33#include <boost/function.hpp>33#include <boost/function.hpp>
3434
35#include <X11/Xlib-xcb.h>
36
37namespace compiz35namespace compiz
38{36{
39namespace actions37namespace actions
@@ -109,6 +107,9 @@
109 bool fromString (const CompString &str);107 bool fromString (const CompString &str);
110 CompString toString () const;108 CompString toString () const;
111109
110 bool operator== (const KeyBinding &k) const;
111 bool operator!= (const KeyBinding &k) const;
112
112 private:113 private:
113 unsigned int mModifiers;114 unsigned int mModifiers;
114 int mKeycode;115 int mKeycode;
@@ -126,6 +127,9 @@
126 bool fromString (const CompString &str);127 bool fromString (const CompString &str);
127 CompString toString () const;128 CompString toString () const;
128129
130 bool operator== (const ButtonBinding &b) const;
131 bool operator!= (const ButtonBinding &b) const;
132
129 private:133 private:
130 unsigned int mModifiers;134 unsigned int mModifiers;
131 int mButton;135 int mButton;
@@ -133,32 +137,41 @@
133137
134 typedef unsigned int State;138 typedef unsigned int State;
135 typedef unsigned int BindingType;139 typedef unsigned int BindingType;
140 typedef std::vector<CompAction> Vector;
136 typedef boost::function <bool (CompAction *, State, CompOption::Vector &)> CallBack;141 typedef boost::function <bool (CompAction *, State, CompOption::Vector &)> CallBack;
137142
143 class Container {
144 public:
145 virtual ~Container() {}
146 virtual Vector & getActions () = 0;
147 };
148
138 public:149 public:
139 CompAction ();150 CompAction ();
140 CompAction (const CompAction &);151 CompAction (const CompAction &);
141 ~CompAction ();152 ~CompAction ();
142153
143 CallBack initiate ();154 CallBack initiate () const;
144 CallBack terminate ();155 CallBack terminate () const;
145156
146 void setInitiate (const CallBack &initiate);157 void setInitiate (const CallBack &initiate);
147 void setTerminate (const CallBack &terminate);158 void setTerminate (const CallBack &terminate);
148159
149 State state ();160 State state () const;
150 BindingType type ();161 BindingType type () const;
151162
152 KeyBinding & key ();163 KeyBinding & key ();
164 const KeyBinding & key () const;
153 void setKey (const KeyBinding &key);165 void setKey (const KeyBinding &key);
154166
155 ButtonBinding & button ();167 ButtonBinding & button ();
168 const ButtonBinding & button () const;
156 void setButton (const ButtonBinding &button);169 void setButton (const ButtonBinding &button);
157170
158 unsigned int edgeMask ();171 unsigned int edgeMask () const;
159 void setEdgeMask (unsigned int edge);172 void setEdgeMask (unsigned int edge);
160173
161 bool bell ();174 bool bell () const;
162 void setBell (bool bell);175 void setBell (bool bell);
163176
164 void setState (State state);177 void setState (State state);
@@ -172,13 +185,13 @@
172 bool buttonFromString (const CompString &str);185 bool buttonFromString (const CompString &str);
173 bool edgeMaskFromString (const CompString &str);186 bool edgeMaskFromString (const CompString &str);
174187
175 CompString keyToString ();188 CompString keyToString () const;
176 CompString buttonToString ();189 CompString buttonToString () const;
177 CompString edgeMaskToString ();190 CompString edgeMaskToString () const;
178191
179 static CompString edgeToString (unsigned int edge);192 static CompString edgeToString (unsigned int edge);
180193
181 bool active ();194 bool active () const;
182195
183 /* CompAction should be a pure virtual class so196 /* CompAction should be a pure virtual class so
184 * that we can pass the interface required to for setActionActiveState197 * that we can pass the interface required to for setActionActiveState
@@ -191,4 +204,6 @@
191 PrivateAction *priv;204 PrivateAction *priv;
192};205};
193206
207CompAction::Vector & noActions ();
208
194#endif209#endif
195210
=== modified file 'include/core/plugin.h'
--- include/core/plugin.h 2013-04-17 06:58:36 +0000
+++ include/core/plugin.h 2014-01-23 16:45:20 +0000
@@ -27,6 +27,7 @@
27#define _COMPIZ_PLUGIN_H27#define _COMPIZ_PLUGIN_H
2828
29#include <core/string.h>29#include <core/string.h>
30#include <core/action.h>
30#include <core/option.h>31#include <core/option.h>
31#include <core/privateunion.h>32#include <core/privateunion.h>
32#include <core/pluginclasshandler.h>33#include <core/pluginclasshandler.h>
@@ -146,6 +147,8 @@
146147
147 virtual bool setOption (const CompString &name,148 virtual bool setOption (const CompString &name,
148 CompOption::Value &value);149 CompOption::Value &value);
150
151 virtual CompAction::Vector & getActions ();
149 private:152 private:
150 CompString mName;153 CompString mName;
151 VTable **mSelf;154 VTable **mSelf;
@@ -167,6 +170,7 @@
167 CompOption::Vector & getOptions ();170 CompOption::Vector & getOptions ();
168 bool setOption (const CompString &name,171 bool setOption (const CompString &name,
169 CompOption::Value &value);172 CompOption::Value &value);
173 CompAction::Vector & getActions ();
170174
171 private:175 private:
172176
@@ -190,6 +194,7 @@
190 void finiScreen (CompScreen *s);194 void finiScreen (CompScreen *s);
191 CompOption::Vector & getOptions ();195 CompOption::Vector & getOptions ();
192 bool setOption (const CompString &name, CompOption::Value &value);196 bool setOption (const CompString &name, CompOption::Value &value);
197 CompAction::Vector & getActions ();
193198
194 private:199 private:
195200
@@ -364,6 +369,15 @@
364 return oc->setOption (name, value);369 return oc->setOption (name, value);
365}370}
366371
372template <typename T, typename T2, int ABI>
373CompAction::Vector & CompPlugin::VTableForScreenAndWindow<T, T2, ABI>::getActions ()
374{
375 CompAction::Container *ac = dynamic_cast<CompAction::Container *> (T::get (screen));
376 if (!ac)
377 return noActions ();
378 return ac->getActions ();
379}
380
367/**381/**
368 * Mark the plugin class handlers as ready to be initialized382 * Mark the plugin class handlers as ready to be initialized
369 */383 */
@@ -435,6 +449,16 @@
435 return oc->setOption (name, value);449 return oc->setOption (name, value);
436}450}
437451
452template <typename T, int ABI>
453CompAction::Vector &
454CompPlugin::VTableForScreen<T, ABI>::getActions ()
455{
456 CompAction::Container *ac = dynamic_cast<CompAction::Container *> (T::get (screen));
457 if (!ac)
458 return noActions ();
459 return ac->getActions ();
460}
461
438typedef CompPlugin::VTable *(*PluginGetInfoProc) (void);462typedef CompPlugin::VTable *(*PluginGetInfoProc) (void);
439463
440#endif464#endif
441465
=== modified file 'src/action.cpp'
--- src/action.cpp 2013-11-25 20:54:05 +0000
+++ src/action.cpp 2014-01-23 16:45:20 +0000
@@ -242,6 +242,18 @@
242 return binding;242 return binding;
243}243}
244244
245bool
246CompAction::KeyBinding::operator== (const KeyBinding &k) const
247{
248 return mKeycode == k.mKeycode && mModifiers == k.mModifiers;
249}
250
251bool
252CompAction::KeyBinding::operator!= (const KeyBinding &k) const
253{
254 return !(*this == k);
255}
256
245CompAction::ButtonBinding::ButtonBinding () :257CompAction::ButtonBinding::ButtonBinding () :
246 mModifiers (0),258 mModifiers (0),
247 mButton (0)259 mButton (0)
@@ -314,6 +326,18 @@
314 return binding;326 return binding;
315}327}
316328
329bool
330CompAction::ButtonBinding::operator== (const ButtonBinding &b) const
331{
332 return mButton == b.mButton && mModifiers == b.mModifiers;
333}
334
335bool
336CompAction::ButtonBinding::operator!= (const ButtonBinding &b) const
337{
338 return !(*this == b);
339}
340
317CompAction::CompAction () :341CompAction::CompAction () :
318 priv (new PrivateAction ())342 priv (new PrivateAction ())
319{343{
@@ -330,13 +354,13 @@
330}354}
331355
332CompAction::CallBack356CompAction::CallBack
333CompAction::initiate ()357CompAction::initiate () const
334{358{
335 return priv->initiate;359 return priv->initiate;
336}360}
337361
338CompAction::CallBack362CompAction::CallBack
339CompAction::terminate ()363CompAction::terminate () const
340{364{
341 return priv->terminate;365 return priv->terminate;
342}366}
@@ -354,13 +378,13 @@
354}378}
355379
356CompAction::State380CompAction::State
357CompAction::state ()381CompAction::state () const
358{382{
359 return priv->state;383 return priv->state;
360}384}
361385
362CompAction::BindingType386CompAction::BindingType
363CompAction::type ()387CompAction::type () const
364{388{
365 return priv->type;389 return priv->type;
366}390}
@@ -371,6 +395,12 @@
371 return priv->key;395 return priv->key;
372}396}
373397
398const CompAction::KeyBinding &
399CompAction::key () const
400{
401 return priv->key;
402}
403
374void404void
375CompAction::setKey (const CompAction::KeyBinding &key)405CompAction::setKey (const CompAction::KeyBinding &key)
376{406{
@@ -388,6 +418,12 @@
388 return priv->button;418 return priv->button;
389}419}
390420
421const CompAction::ButtonBinding &
422CompAction::button () const
423{
424 return priv->button;
425}
426
391void427void
392CompAction::setButton (const CompAction::ButtonBinding &button)428CompAction::setButton (const CompAction::ButtonBinding &button)
393{429{
@@ -405,7 +441,7 @@
405}441}
406442
407unsigned int443unsigned int
408CompAction::edgeMask ()444CompAction::edgeMask () const
409{445{
410 return priv->edgeMask;446 return priv->edgeMask;
411}447}
@@ -426,7 +462,7 @@
426}462}
427463
428bool464bool
429CompAction::bell ()465CompAction::bell () const
430{466{
431 return priv->bell;467 return priv->bell;
432}468}
@@ -558,7 +594,7 @@
558}594}
559595
560CompString596CompString
561CompAction::keyToString ()597CompAction::keyToString () const
562{598{
563 CompString binding = priv->key.toString ();599 CompString binding = priv->key.toString ();
564600
@@ -569,7 +605,7 @@
569}605}
570606
571CompString607CompString
572CompAction::buttonToString ()608CompAction::buttonToString () const
573{609{
574 CompString edge;610 CompString edge;
575611
@@ -584,7 +620,7 @@
584}620}
585621
586CompString622CompString
587CompAction::edgeMaskToString ()623CompAction::edgeMaskToString () const
588{624{
589 CompString edge;625 CompString edge;
590626
@@ -609,7 +645,7 @@
609}645}
610646
611bool647bool
612CompAction::active ()648CompAction::active () const
613{649{
614 return priv->active;650 return priv->active;
615}651}
@@ -654,3 +690,10 @@
654{690{
655 memcpy (&priv, &a.priv, sizeof (CompPrivate));691 memcpy (&priv, &a.priv, sizeof (CompPrivate));
656}692}
693
694CompAction::Vector &
695noActions ()
696{
697 static CompAction::Vector v;
698 return v;
699}
657700
=== modified file 'src/event.cpp'
--- src/event.cpp 2013-11-22 15:11:24 +0000
+++ src/event.cpp 2014-01-23 16:45:20 +0000
@@ -98,6 +98,23 @@
98 Mod3Mask | Mod4Mask | Mod5Mask | CompNoMask)98 Mod3Mask | Mod4Mask | Mod5Mask | CompNoMask)
9999
100static bool100static bool
101isCallBackBinding (CompAction &action,
102 CompAction::BindingType type,
103 CompAction::State state)
104{
105 if (!(action.type () & type))
106 return false;
107
108 if (!(action.state () & state))
109 return false;
110
111 if (!action.active ())
112 return false;
113
114 return true;
115}
116
117static bool
101isCallBackBinding (CompOption &option,118isCallBackBinding (CompOption &option,
102 CompAction::BindingType type,119 CompAction::BindingType type,
103 CompAction::State state)120 CompAction::State state)
@@ -105,16 +122,7 @@
105 if (!option.isAction ())122 if (!option.isAction ())
106 return false;123 return false;
107124
108 if (!(option.value ().action ().type () & type))125 return isCallBackBinding (option.value ().action (), type, state);
109 return false;
110
111 if (!(option.value ().action ().state () & state))
112 return false;
113
114 if (!option.value ().action ().active ())
115 return false;
116
117 return true;
118}126}
119127
120static bool128static bool
@@ -135,6 +143,14 @@
135}143}
136144
137static bool145static bool
146isBound (CompAction &action,
147 CompAction::BindingType type,
148 CompAction::State state)
149{
150 return isCallBackBinding (action, type, state);
151}
152
153static bool
138isBound (CompOption &option,154isBound (CompOption &option,
139 CompAction::BindingType type,155 CompAction::BindingType type,
140 CompAction::State state,156 CompAction::State state,
@@ -379,19 +395,53 @@
379}395}
380396
381bool397bool
398PrivateScreen::shouldTriggerKeyPressAction (CompAction *action,
399 XKeyEvent *event)
400{
401 unsigned int modMask = REAL_MOD_MASK & ~modHandler->ignoredModMask ();
402 unsigned int bindMods = modHandler->virtualToRealModMask (action->key ().modifiers ());
403 int bindCode = action->key ().keycode ();
404 unsigned int bindCodeMod = bindCode ? modHandler->keycodeToModifiers (bindCode) : 0;
405 unsigned int eventMods = event->state & modMask;
406
407 if (bindCode == (int) event->keycode)
408 return (bindMods & modMask) == eventMods;
409 else if (!xkbEvent.get() && bindCode == 0)
410 return bindMods == eventMods;
411 else if (bindCodeMod != 0)
412 {
413 for (int mod = 0; mod < 8; mod++)
414 {
415 int mask = 1 << mod;
416
417 if ((bindMods & mask) == 0)
418 continue;
419
420 for (int k = mod * modHandler->modMap ()->max_keypermod;
421 k < (mod + 1) * modHandler->modMap ()->max_keypermod;
422 k++)
423 {
424 if (modHandler->modMap ()->modifiermap[k] == event->keycode)
425 {
426 if ((((bindMods & ~mask) | bindCodeMod) & modMask) == eventMods)
427 return true;
428
429 break;
430 }
431 }
432 }
433 }
434
435 return false;
436}
437
438bool
382PrivateScreen::triggerKeyPressBindings (CompOption::Vector &options,439PrivateScreen::triggerKeyPressBindings (CompOption::Vector &options,
440 CompAction::Vector &actions,
383 XKeyEvent *event,441 XKeyEvent *event,
384 CompOption::Vector &arguments)442 CompOption::Vector &arguments)
385{443{
386 CompAction::State state = 0;444 CompAction::State state = 0;
387 CompAction *action;
388 unsigned int modMask = REAL_MOD_MASK & ~modHandler->ignoredModMask ();
389 unsigned int modifierForBindCode;
390 unsigned int bindMods;
391 int bindCode;
392 int mask;
393 int mod;
394 int k;
395445
396 if (event->keycode == escapeKeyCode)446 if (event->keycode == escapeKeyCode)
397 state = CompAction::StateCancel;447 state = CompAction::StateCancel;
@@ -410,6 +460,12 @@
410 }460 }
411 }461 }
412462
463 foreach (CompAction &a, actions)
464 {
465 if (!a.terminate ().empty ())
466 a.terminate () (&a, state, noOptions ());
467 }
468
413 if (state == CompAction::StateCancel)469 if (state == CompAction::StateCancel)
414 return false;470 return false;
415 }471 }
@@ -417,103 +473,114 @@
417 state = CompAction::StateInitKey;473 state = CompAction::StateInitKey;
418 foreach (CompOption &option, options)474 foreach (CompOption &option, options)
419 {475 {
420 if (isBound (option, CompAction::BindingTypeKey, state, &action))476 CompAction *action;
421 {477
422 bindCode = action->key ().keycode ();478 if (isBound (option, CompAction::BindingTypeKey, state, &action) &&
423 bindMods = modHandler->virtualToRealModMask (action->key ().modifiers ());479 shouldTriggerKeyPressAction (action, event) &&
424480 eventManager.triggerPress (action, state, arguments))
425 if (bindCode == 0)481 return true;
426 modifierForBindCode = 0;482 }
427 else483
428 modifierForBindCode = modHandler->keycodeToModifiers (bindCode);484 foreach (CompAction &action, actions)
429485 {
430 bool match = false;486 if (isBound (action, CompAction::BindingTypeKey, state) &&
431 if (bindCode == (int) event->keycode)487 shouldTriggerKeyPressAction (&action, event) &&
432 match = ((bindMods & modMask) == (event->state & modMask));488 eventManager.triggerPress (&action, state, arguments))
433 else if (!xkbEvent.get() && bindCode == 0)489 return true;
434 match = (bindMods == (event->state & modMask));
435 else if (modifierForBindCode != 0)
436 {
437 for (mod = 0; mod < 8; mod++)
438 {
439 mask = 1 << mod;
440
441 if ((bindMods & mask) == 0)
442 continue;
443
444 for (k = mod * modHandler->modMap ()->max_keypermod;
445 k < (mod + 1) * modHandler->modMap ()->max_keypermod;
446 k++)
447 {
448 if (modHandler->modMap ()->modifiermap[k] == event->keycode)
449 {
450 match = ((((bindMods & ~mask) | modifierForBindCode) & modMask) == (event->state & modMask));
451 break;
452 }
453 }
454
455 if (match)
456 break;
457 }
458 }
459
460 if (match && eventManager.triggerPress (action, state, arguments))
461 return true;
462 }
463 }490 }
464491
465 return false;492 return false;
466}493}
467494
468bool495bool
496PrivateScreen::shouldTriggerKeyReleaseAction (CompAction *action,
497 XKeyEvent *event)
498{
499 unsigned int modMask = REAL_MOD_MASK & ~modHandler->ignoredModMask ();
500 unsigned int bindMods = modHandler->virtualToRealModMask (action->key ().modifiers ());
501
502 if ((bindMods & modMask) == 0)
503 return (unsigned int) action->key ().keycode () == event->keycode;
504
505 unsigned int mods = modHandler->keycodeToModifiers (event->keycode);
506 return !xkbEvent.get() && ((mods & modMask & bindMods) != bindMods);
507}
508
509bool
469PrivateScreen::triggerKeyReleaseBindings (CompOption::Vector &options,510PrivateScreen::triggerKeyReleaseBindings (CompOption::Vector &options,
511 CompAction::Vector &actions,
470 XKeyEvent *event,512 XKeyEvent *event,
471 CompOption::Vector &arguments)513 CompOption::Vector &arguments)
472{514{
473 CompAction::State state = CompAction::StateTermKey;515 CompAction::State state = CompAction::StateTermKey;
474 CompAction *action;
475 unsigned int ignored = modHandler->ignoredModMask ();
476 unsigned int modMask = REAL_MOD_MASK & ~ignored;
477 unsigned int bindMods;
478 unsigned int mods;
479516
480 mods = modHandler->keycodeToModifiers (event->keycode);517 if (!xkbEvent.get() && !modHandler->keycodeToModifiers (event->keycode))
481 if (!xkbEvent.get() && !mods)
482 return false;518 return false;
483519
484 bool handled = false;520 bool handled = false;
485521
486 foreach (CompOption &option, options)522 foreach (CompOption &option, options)
487 {523 {
488 if (isBound (option, CompAction::BindingTypeKey, state, &action))524 CompAction *action;
489 {525
490 bindMods = modHandler->virtualToRealModMask (action->key ().modifiers ());526 if (isBound (option, CompAction::BindingTypeKey, state, &action) &&
491527 shouldTriggerKeyReleaseAction (action, event))
492 bool match = false;528 handled |= eventManager.triggerRelease (action, state, arguments);
493 if ((bindMods & modMask) == 0)529 }
494 match = ((unsigned int) action->key ().keycode () ==530
495 (unsigned int) event->keycode);531 foreach (CompAction &action, actions)
496 else if (!xkbEvent.get() && ((mods & modMask & bindMods) != bindMods))532 {
497 match = true;533 if (isBound (action, CompAction::BindingTypeKey, state) &&
498534 shouldTriggerKeyReleaseAction (&action, event))
499 handled |= match && eventManager.triggerRelease (action, state, arguments);535 handled |= eventManager.triggerRelease (&action, state, arguments);
500 }
501 }536 }
502537
503 return handled;538 return handled;
504}539}
505540
506bool541bool
542PrivateScreen::shouldTriggerModifierPressAction (CompAction *action,
543 XkbStateNotifyEvent *event)
544{
545 if (action->key ().keycode ())
546 return false;
547
548 unsigned int modMask = REAL_MOD_MASK & ~modHandler->ignoredModMask ();
549 unsigned int bindMods = modHandler->virtualToRealModMask (action->key ().modifiers ());
550 unsigned int eventMods = event->mods & modMask;
551
552 return eventMods == bindMods;
553}
554
555bool
556PrivateScreen::shouldTriggerModifierReleaseAction (CompAction *action,
557 XkbStateNotifyEvent *event)
558{
559 unsigned int modMask = REAL_MOD_MASK & ~modHandler->ignoredModMask ();
560 unsigned int bindMods = modHandler->virtualToRealModMask (action->key ().modifiers ());
561
562 if (event->mods && ((event->mods & modMask) != bindMods))
563 return true;
564
565 unsigned int eventCodeMod = modHandler->keycodeToModifiers (event->keycode);
566
567 if (!event->mods && (eventCodeMod == bindMods))
568 return true;
569
570 int bindCode = action->key ().keycode ();
571 unsigned int bindCodeMod = bindCode ? modHandler->keycodeToModifiers (bindCode) : 0;
572
573 return bindCodeMod && event->keycode == bindCode &&
574 ((bindMods | bindCodeMod) == ((event->mods & modMask) | eventCodeMod));
575}
576
577bool
507PrivateScreen::triggerStateNotifyBindings (CompOption::Vector &options,578PrivateScreen::triggerStateNotifyBindings (CompOption::Vector &options,
579 CompAction::Vector &actions,
508 XkbStateNotifyEvent *event,580 XkbStateNotifyEvent *event,
509 CompOption::Vector &arguments)581 CompOption::Vector &arguments)
510{582{
511 CompAction::State state;583 CompAction::State state;
512 CompAction *action;
513 unsigned int ignored = modHandler->ignoredModMask ();
514 unsigned int modMask = REAL_MOD_MASK & ~ignored;
515 unsigned int bindMods;
516 int bindCode;
517584
518 if (event->event_type == KeyPress)585 if (event->event_type == KeyPress)
519 {586 {
@@ -521,20 +588,20 @@
521588
522 foreach (CompOption &option, options)589 foreach (CompOption &option, options)
523 {590 {
524 if (isBound (option, CompAction::BindingTypeKey, state, &action))591 CompAction *action;
525 {592
526 if (action->key ().keycode () == 0)593 if (isBound (option, CompAction::BindingTypeKey, state, &action) &&
527 {594 shouldTriggerModifierPressAction (action, event) &&
528 bindMods =595 eventManager.triggerPress (action, state, arguments))
529 modHandler->virtualToRealModMask (action->key ().modifiers ());596 return true;
530597 }
531 if ((event->mods & modMask) == bindMods)598
532 {599 foreach (CompAction &action, actions)
533 if (eventManager.triggerPress (action, state, arguments))600 {
534 return true;601 if (isBound (action, CompAction::BindingTypeKey, state) &&
535 }602 shouldTriggerModifierPressAction (&action, event) &&
536 }603 eventManager.triggerPress (&action, state, arguments))
537 }604 return true;
538 }605 }
539 }606 }
540 else if (event->event_type == KeyRelease)607 else if (event->event_type == KeyRelease)
@@ -544,21 +611,18 @@
544611
545 foreach (CompOption &option, options)612 foreach (CompOption &option, options)
546 {613 {
547 if (isBound (option, CompAction::BindingTypeKey, state, &action))614 CompAction *action;
548 {
549 bindCode = action->key ().keycode ();
550 bindMods = modHandler->virtualToRealModMask (action->key ().modifiers ());
551 unsigned int modifierForBindCode = bindCode ? modHandler->keycodeToModifiers (bindCode) : 0;
552 unsigned int modifierForEventCode = modHandler->keycodeToModifiers (event->keycode);
553615
554 if ((event->mods && ((event->mods & modMask) != bindMods)) ||616 if (isBound (option, CompAction::BindingTypeKey, state, &action) &&
555 (!event->mods && (modifierForEventCode == bindMods)) ||617 shouldTriggerModifierReleaseAction (action, event))
556 (modifierForBindCode && event->keycode == bindCode &&
557 ((bindMods | modifierForBindCode) == ((event->mods & modMask) | modifierForEventCode))))
558 {
559 handled |= eventManager.triggerRelease (action, state, arguments);618 handled |= eventManager.triggerRelease (action, state, arguments);
560 }619 }
561 }620
621 foreach (CompAction &action, actions)
622 {
623 if (isBound (action, CompAction::BindingTypeKey, state) &&
624 shouldTriggerModifierReleaseAction (&action, event))
625 handled |= eventManager.triggerRelease (&action, state, arguments);
562 }626 }
563627
564 if (handled)628 if (handled)
@@ -880,7 +944,8 @@
880 foreach (CompPlugin *p, CompPlugin::getPlugins ())944 foreach (CompPlugin *p, CompPlugin::getPlugins ())
881 {945 {
882 CompOption::Vector &options = p->vTable->getOptions ();946 CompOption::Vector &options = p->vTable->getOptions ();
883 if (triggerKeyPressBindings (options, &event->xkey, o))947 CompAction::Vector &actions = p->vTable->getActions ();
948 if (triggerKeyPressBindings (options, actions, &event->xkey, o))
884 return true;949 return true;
885 }950 }
886 break;951 break;
@@ -904,7 +969,8 @@
904 foreach (CompPlugin *p, CompPlugin::getPlugins ())969 foreach (CompPlugin *p, CompPlugin::getPlugins ())
905 {970 {
906 CompOption::Vector &options = p->vTable->getOptions ();971 CompOption::Vector &options = p->vTable->getOptions ();
907 handled |= triggerKeyReleaseBindings (options, &event->xkey, o);972 CompAction::Vector &actions = p->vTable->getActions ();
973 handled |= triggerKeyReleaseBindings (options, actions, &event->xkey, o);
908 }974 }
909975
910 if (handled)976 if (handled)
@@ -1110,7 +1176,8 @@
1110 foreach (CompPlugin *p, CompPlugin::getPlugins ())1176 foreach (CompPlugin *p, CompPlugin::getPlugins ())
1111 {1177 {
1112 CompOption::Vector &options = p->vTable->getOptions ();1178 CompOption::Vector &options = p->vTable->getOptions ();
1113 handled |= triggerStateNotifyBindings (options, stateEvent, arg);1179 CompAction::Vector &actions = p->vTable->getActions ();
1180 handled |= triggerStateNotifyBindings (options, actions, stateEvent, arg);
1114 }1181 }
11151182
1116 if (handled)1183 if (handled)
11171184
=== modified file 'src/plugin.cpp'
--- src/plugin.cpp 2013-06-28 01:10:57 +0000
+++ src/plugin.cpp 2014-01-23 16:45:20 +0000
@@ -638,3 +638,9 @@
638{638{
639 return false;639 return false;
640}640}
641
642CompAction::Vector &
643CompPlugin::VTable::getActions ()
644{
645 return noActions ();
646}
641647
=== modified file 'src/plugin/tests/test-plugin.cpp'
--- src/plugin/tests/test-plugin.cpp 2013-06-28 01:10:57 +0000
+++ src/plugin/tests/test-plugin.cpp 2014-01-23 16:45:20 +0000
@@ -13,11 +13,6 @@
13#include <gtest_shared_tmpenv.h>13#include <gtest_shared_tmpenv.h>
14#include <gtest_shared_autodestroy.h>14#include <gtest_shared_autodestroy.h>
1515
16/* This is a link-seam so that we don't have to include screen.h */
17class CompAction
18{
19};
20
21class CompMatch16class CompMatch
22{17{
23};18};
2419
=== modified file 'src/privatescreen.h'
--- src/privatescreen.h 2013-10-31 15:59:14 +0000
+++ src/privatescreen.h 2014-01-23 16:45:20 +0000
@@ -624,15 +624,30 @@
624 XButtonEvent *event,624 XButtonEvent *event,
625 CompOption::Vector &arguments);625 CompOption::Vector &arguments);
626626
627 bool shouldTriggerKeyPressAction (CompAction *action,
628 XKeyEvent *event);
629
630 bool shouldTriggerKeyReleaseAction (CompAction *action,
631 XKeyEvent *event);
632
633 bool shouldTriggerModifierPressAction (CompAction *action,
634 XkbStateNotifyEvent *event);
635
636 bool shouldTriggerModifierReleaseAction (CompAction *action,
637 XkbStateNotifyEvent *event);
638
627 bool triggerKeyPressBindings (CompOption::Vector &options,639 bool triggerKeyPressBindings (CompOption::Vector &options,
640 CompAction::Vector &actions,
628 XKeyEvent *event,641 XKeyEvent *event,
629 CompOption::Vector &arguments);642 CompOption::Vector &arguments);
630643
631 bool triggerKeyReleaseBindings (CompOption::Vector &options,644 bool triggerKeyReleaseBindings (CompOption::Vector &options,
645 CompAction::Vector &actions,
632 XKeyEvent *event,646 XKeyEvent *event,
633 CompOption::Vector &arguments);647 CompOption::Vector &arguments);
634648
635 bool triggerStateNotifyBindings (CompOption::Vector &options,649 bool triggerStateNotifyBindings (CompOption::Vector &options,
650 CompAction::Vector &actions,
636 XkbStateNotifyEvent *event,651 XkbStateNotifyEvent *event,
637 CompOption::Vector &arguments);652 CompOption::Vector &arguments);
638653

Subscribers

People subscribed via source and target branches