[PATCH] Added screen edge trigger delay setting.
Danny Baumann
dannybaumann at web.de
Thu Jul 12 04:35:30 PDT 2007
Plugins can prevent edge delay by setting the metadata hint <ignore_edge_delay>.
---
include/compiz.h | 42 +++++++++++-----
metadata/core.xml.in | 7 +++
src/display.c | 5 ++-
src/event.c | 130 +++++++++++++++++++++++++++++++++++++++++++------
src/metadata.c | 12 ++++-
5 files changed, 164 insertions(+), 32 deletions(-)
diff --git a/include/compiz.h b/include/compiz.h
index cefb7d7..f5d6e95 100644
--- a/include/compiz.h
+++ b/include/compiz.h
@@ -26,7 +26,7 @@
#ifndef _COMPIZ_H
#define _COMPIZ_H
-#define ABIVERSION 20070706
+#define ABIVERSION 20070712
#include <stdio.h>
#include <sys/time.h>
@@ -290,18 +290,19 @@ typedef enum {
} CompBindingType;
typedef enum {
- CompActionStateInitKey = 1 << 0,
- CompActionStateTermKey = 1 << 1,
- CompActionStateInitButton = 1 << 2,
- CompActionStateTermButton = 1 << 3,
- CompActionStateInitBell = 1 << 4,
- CompActionStateInitEdge = 1 << 5,
- CompActionStateTermEdge = 1 << 6,
- CompActionStateInitEdgeDnd = 1 << 7,
- CompActionStateTermEdgeDnd = 1 << 8,
- CompActionStateCommit = 1 << 9,
- CompActionStateCancel = 1 << 10,
- CompActionStateAutoGrab = 1 << 11
+ CompActionStateInitKey = 1 << 0,
+ CompActionStateTermKey = 1 << 1,
+ CompActionStateInitButton = 1 << 2,
+ CompActionStateTermButton = 1 << 3,
+ CompActionStateInitBell = 1 << 4,
+ CompActionStateInitEdge = 1 << 5,
+ CompActionStateTermEdge = 1 << 6,
+ CompActionStateInitEdgeDnd = 1 << 7,
+ CompActionStateTermEdgeDnd = 1 << 8,
+ CompActionStateCommit = 1 << 9,
+ CompActionStateCancel = 1 << 10,
+ CompActionStateAutoGrab = 1 << 11,
+ CompActionStateIgnoreEdgeDelay = 1 << 12
} CompActionState;
typedef enum {
@@ -587,7 +588,8 @@ typedef int CompFileWatchHandle;
#define COMP_DISPLAY_OPTION_TERMINAL 56
#define COMP_DISPLAY_OPTION_RUN_TERMINAL 57
#define COMP_DISPLAY_OPTION_PING_DELAY 58
-#define COMP_DISPLAY_OPTION_NUM 59
+#define COMP_DISPLAY_OPTION_EDGE_DELAY 59
+#define COMP_DISPLAY_OPTION_NUM 60
typedef CompOption *(*GetDisplayOptionsProc) (CompDisplay *display,
int *count);
@@ -904,6 +906,8 @@ struct _CompDisplay {
CompTimeoutHandle autoRaiseHandle;
Window autoRaiseWindow;
+ CompTimeoutHandle edgeDelayHandle;
+
CompOptionValue plugin;
Bool dirtyPluginList;
@@ -1107,6 +1111,16 @@ findCursorAtDisplay (CompDisplay *display);
/* event.c */
+typedef struct _CompDelayedEdgeSettings
+{
+ CompDisplay *d;
+
+ unsigned int edge;
+ unsigned int state;
+
+ CompOption option[7];
+} CompDelayedEdgeSettings;
+
void
handleEvent (CompDisplay *display,
XEvent *event);
diff --git a/metadata/core.xml.in b/metadata/core.xml.in
index 8424ab1..64d418a 100644
--- a/metadata/core.xml.in
+++ b/metadata/core.xml.in
@@ -44,6 +44,13 @@
<min>0</min>
<max>10000</max>
</option>
+ <option name="edge_delay" type="int">
+ <_short>Edge Trigger Delay</_short>
+ <_long>Duration the pointer must reset in a screen edge before an edge action is taken.</_long>
+ <default>0</default>
+ <min>0</min>
+ <max>10000</max>
+ </option>
<option name="close_window" type="action">
<_short>Close Window</_short>
<_long>Close active window</_long>
diff --git a/src/display.c b/src/display.c
index 69e7de3..2c7ed60 100644
--- a/src/display.c
+++ b/src/display.c
@@ -726,7 +726,8 @@ const CompMetadataOptionInfo coreDisplayOptionInfo[COMP_DISPLAY_OPTION_NUM] = {
{ "ignore_hints_when_maximized", "bool", 0, 0, 0 },
{ "command_terminal", "string", 0, 0, 0 },
{ "run_command_terminal", "action", 0, runCommandTerminal, 0 },
- { "ping_delay", "int", "<min>1000</min>", 0, 0 }
+ { "ping_delay", "int", "<min>1000</min>", 0, 0 },
+ { "edge_delay", "int", "<min>0</min>", 0, 0 }
};
CompOption *
@@ -1981,6 +1982,8 @@ addDisplay (char *name)
d->logMessage = logMessage;
+ d->edgeDelayHandle = 0;
+
d->display = dpy = XOpenDisplay (name);
if (!d->display)
{
diff --git a/src/event.c b/src/event.c
index ab530c2..7d13ad8 100644
--- a/src/event.c
+++ b/src/event.c
@@ -595,6 +595,7 @@ isEdgeAction (CompOption *option,
static Bool
isEdgeEnterAction (CompOption *option,
CompActionState state,
+ CompActionState ignoreState,
unsigned int edge,
CompAction **action)
{
@@ -607,6 +608,15 @@ isEdgeEnterAction (CompOption *option,
if (!option->value.action.initiate)
return FALSE;
+ if (ignoreState)
+ {
+ if ((option->value.action.state & CompActionStateIgnoreEdgeDelay) !=
+ (ignoreState & CompActionStateIgnoreEdgeDelay))
+ {
+ return FALSE;
+ }
+ }
+
*action = &option->value.action;
return TRUE;
@@ -634,6 +644,7 @@ triggerEdgeEnterBindings (CompDisplay *d,
CompOption *option,
int nOption,
CompActionState state,
+ CompActionState ignoreState,
unsigned int edge,
CompOption *argument,
int nArgument)
@@ -642,7 +653,7 @@ triggerEdgeEnterBindings (CompDisplay *d,
while (nOption--)
{
- if (isEdgeEnterAction (option, state, edge, &action))
+ if (isEdgeEnterAction (option, state, ignoreState, edge, &action))
{
if ((*action->initiate) (d, action, state, argument, nArgument))
return TRUE;
@@ -680,6 +691,62 @@ triggerEdgeLeaveBindings (CompDisplay *d,
}
static Bool
+triggerAllEdgeEnterBindings (CompDisplay *d,
+ CompActionState state,
+ CompActionState ignoreState,
+ unsigned int edge,
+ CompOption *argument,
+ int nArgument)
+{
+ CompOption *option;
+ int nOption;
+ CompPlugin *p;
+
+ for (p = getPlugins(); p; p = p->next)
+ {
+ if (p->vTable->getDisplayOptions)
+ {
+ option = (*p->vTable->getDisplayOptions) (p, d, &nOption);
+ if (triggerEdgeEnterBindings (d,
+ option, nOption,
+ state, ignoreState, edge,
+ argument, nArgument))
+ {
+ return TRUE;
+ }
+ }
+ }
+
+ option = compGetDisplayOptions (d, &nOption);
+ if (triggerEdgeEnterBindings(d,
+ option, nOption,
+ state, ignoreState, edge,
+ argument, nArgument))
+ {
+ return TRUE;
+ }
+
+ return FALSE;
+}
+
+static Bool
+delayedEdgeTimeout (void *closure)
+{
+ CompDelayedEdgeSettings *settings = (CompDelayedEdgeSettings *) closure;
+ CompDisplay *d = settings->d;
+
+ triggerAllEdgeEnterBindings (d,
+ settings->state,
+ ~CompActionStateIgnoreEdgeDelay,
+ settings->edge,
+ settings->option, 7);
+
+ free (settings);
+
+ return FALSE;
+}
+
+static Bool
handleActionEvent (CompDisplay *d,
XEvent *event)
{
@@ -846,6 +913,16 @@ handleActionEvent (CompDisplay *d,
if (!s)
return FALSE;
+ if (d->edgeDelayHandle)
+ {
+ void *closure;
+
+ closure = compRemoveTimeout (d->edgeDelayHandle);
+ if (closure)
+ free (closure);
+ d->edgeDelayHandle = 0;
+ }
+
if (edgeWindow && edgeWindow != event->xcrossing.window)
{
state = CompActionStateTermEdge;
@@ -903,10 +980,25 @@ handleActionEvent (CompDisplay *d,
if (edge)
{
+ int delay;
+ CompDelayedEdgeSettings *delayedSettings = NULL;
+
+ delay = d->opt[COMP_DISPLAY_OPTION_EDGE_DELAY].value.i;
state = CompActionStateInitEdge;
edgeWindow = event->xcrossing.window;
+ if (delay > 0)
+ {
+ delayedSettings = malloc (sizeof (CompDelayedEdgeSettings));
+ if (delayedSettings)
+ {
+ delayedSettings->d = d;
+ delayedSettings->edge = edge;
+ delayedSettings->state = state;
+ }
+ }
+
o[0].value.i = event->xcrossing.window;
o[1].value.i = d->activeWindow;
o[2].value.i = event->xcrossing.state;
@@ -918,21 +1010,27 @@ handleActionEvent (CompDisplay *d,
o[6].name = "time";
o[6].value.i = event->xcrossing.time;
- for (p = getPlugins (); p; p = p->next)
+ if (delayedSettings)
{
- if (p->vTable->getDisplayOptions)
- {
- option = (*p->vTable->getDisplayOptions) (p, d, &nOption);
- if (triggerEdgeEnterBindings (d, option, nOption, state,
- edge, o, 7))
- return TRUE;
- }
- }
+ CompActionState ignoreState;
- option = compGetDisplayOptions (d, &nOption);
- if (triggerEdgeEnterBindings (d, option, nOption, state,
- edge, o, 7))
- return TRUE;
+ for (i = 0; i < 7; i++)
+ delayedSettings->option[i] = o[i];
+
+ d->edgeDelayHandle = compAddTimeout (delay,
+ delayedEdgeTimeout,
+ delayedSettings);
+
+ ignoreState = CompActionStateIgnoreEdgeDelay;
+ if (triggerAllEdgeEnterBindings (d, state, ignoreState,
+ edge, o, 7))
+ return TRUE;
+ }
+ else
+ {
+ if (triggerAllEdgeEnterBindings (d, state, 0, edge, o, 7))
+ return TRUE;
+ }
}
} break;
case ClientMessage:
@@ -1041,14 +1139,14 @@ handleActionEvent (CompDisplay *d,
{
option = (*p->vTable->getDisplayOptions) (p, d, &nOption);
if (triggerEdgeEnterBindings (d, option, nOption, state,
- edge, o, 6))
+ 0, edge, o, 6))
return TRUE;
}
}
option = compGetDisplayOptions (d, &nOption);
if (triggerEdgeEnterBindings (d, option, nOption, state,
- edge, o, 6))
+ 0, edge, o, 6))
return TRUE;
}
diff --git a/src/metadata.c b/src/metadata.c
index 337c91c..51e7211 100644
--- a/src/metadata.c
+++ b/src/metadata.c
@@ -851,7 +851,7 @@ initActionState (CompMetadata *metadata,
};
int i;
CompXPath xPath;
- char *grab;
+ char *grab, *ignoreEdgeDelay;
*state = CompActionStateAutoGrab;
@@ -864,6 +864,16 @@ initActionState (CompMetadata *metadata,
free (grab);
}
+ ignoreEdgeDelay = stringFromMetadataPathElement (metadata, path,
+ "ignore_edge_delay");
+ if (ignoreEdgeDelay)
+ {
+ if (strcmp (ignoreEdgeDelay, "true") == 0)
+ *state |= CompActionStateIgnoreEdgeDelay;
+
+ free (ignoreEdgeDelay);
+ }
+
if (!initXPathFromMetadataPathElement (&xPath, metadata, BAD_CAST path,
BAD_CAST "allowed"))
return;
--
1.5.2.2
--=-6B8vdMXn+vBOTdKrS7o1
Content-Disposition: attachment; filename=0002-Also-use-edge-delay-setting-for-DnD-actions.patch
Content-Type: application/mbox; name=0002-Also-use-edge-delay-setting-for-DnD-actions.patch
Content-Transfer-Encoding: 7bit
More information about the compiz
mailing list