Distance values reported by the puck tool on protocol 4 tablets (e.g.
the Graphire4) have an inverted scale compared to other devices and
tools. That is to say, the values are at their maximum while the puck
is resting on the tablet and minimum just prior to going out of prox.
The way that xf86-input-wacom handles this is with explicit protocol
version checks, which limits our ability to fix this issue going
forward (when libinput/Wayland begin to rule the desktop).

This patch changes how the driver calculates wcmMaxCursorDist so that
it is able to gracefully handle the day we fix this kernel bug.
Instead of storing the minimum/maximum value ever seen on the tablet
(switching between codepaths based on protocol 5/4) we store the value
that is seen whenever the user clicks a button. It is reasonably safe
to assume that this occurs with the puck on the tablet and thus will
be the correct value. Even if the user happens to click with the puck
raised above the surface, a subsuqent click *on* the surface will
reset the value.

Signed-off-by: Jason Gerecke <jason.gere...@wacom.com>
---
 src/wcmCommon.c | 64 +++++++++++++++++++++++----------------------------------
 1 file changed, 26 insertions(+), 38 deletions(-)

diff --git a/src/wcmCommon.c b/src/wcmCommon.c
index e36ac97..9408f42 100644
--- a/src/wcmCommon.c
+++ b/src/wcmCommon.c
@@ -1240,15 +1240,6 @@ static void commonDispatchDevice(InputInfoPtr pInfo,
                }
                filtered.pressure = applyPressureCurve(priv,&filtered);
        }
-       else if (IsCursor(priv) && !priv->oldCursorHwProx)
-       {
-               /* initial current max distance for Intuos series */
-               if ((TabletHasFeature(common, WCM_ROTATION)) ||
-                               (TabletHasFeature(common, WCM_DUALINPUT)))
-                       common->wcmMaxCursorDist = common->wcmMaxDist;
-               else
-                       common->wcmMaxCursorDist = 0;
-       }
 
        /* Store cursor hardware prox for next use */
        if (IsCursor(priv))
@@ -1285,20 +1276,15 @@ static void commonDispatchDevice(InputInfoPtr pInfo,
        /* force out-prox when distance is outside wcmCursorProxoutDist for 
pucks */
        if (IsCursor(priv))
        {
-               if (common->wcmProtocolLevel == WCM_PROTOCOL_5)
-               {
-                       /* protocol 5 distance starts from the MaxDist
-                        * when getting in the prox.
-                        */
-                       if (common->wcmMaxCursorDist > filtered.distance)
-                               common->wcmMaxCursorDist = filtered.distance;
-               }
-               else
-               {
-                       /* protocol 4 distance is 0 when getting in the prox */
-                       if (common->wcmMaxCursorDist < filtered.distance)
-                               common->wcmMaxCursorDist = filtered.distance;
-               }
+               /* Assume the the user clicks the puck buttons while
+                * it is resting on the tablet. This works for both
+                * tablets that have a normal distance scale (protocol
+                * 5) as well as those with an inverted scale (protocol
+                * 4 for many many kernel versions).
+                */
+               if (filtered.buttons)
+                       common->wcmMaxCursorDist = filtered.distance;
+
                DBG(10, common, "Distance over"
                                " the tablet: %d, ProxoutDist: %d current"
                                " min/max %d hard prox: %d\n",
@@ -1307,21 +1293,23 @@ static void commonDispatchDevice(InputInfoPtr pInfo,
                                common->wcmMaxCursorDist,
                                ds->proximity);
 
-               if (priv->oldState.proximity)
-               {
-                       if (abs(filtered.distance - common->wcmMaxCursorDist)
-                                       > common->wcmCursorProxoutDist)
-                               filtered.proximity = 0;
-               }
-               /* once it is out. Don't let it in until a hard in */
-               /* or it gets inside wcmCursorProxoutDist */
-               else
-               {
-                       if (abs(filtered.distance - common->wcmMaxCursorDist) >
-                                       common->wcmCursorProxoutDist && 
ds->proximity)
-                               return;
-                       if (!ds->proximity)
-                               return;
+               if (common->wcmMaxCursorDist) {
+                       if (priv->oldState.proximity)
+                       {
+                               if (abs(filtered.distance - 
common->wcmMaxCursorDist)
+                                               > common->wcmCursorProxoutDist)
+                                       filtered.proximity = 0;
+                       }
+                       /* once it is out. Don't let it in until a hard in */
+                       /* or it gets inside wcmCursorProxoutDist */
+                       else
+                       {
+                               if (abs(filtered.distance - 
common->wcmMaxCursorDist) >
+                                               common->wcmCursorProxoutDist && 
ds->proximity)
+                                       return;
+                               if (!ds->proximity)
+                                       return;
+                       }
                }
        }
        wcmSendEvents(pInfo, &filtered);
-- 
2.4.6


------------------------------------------------------------------------------
_______________________________________________
Linuxwacom-devel mailing list
Linuxwacom-devel@lists.sourceforge.net
https://lists.sourceforge.net/lists/listinfo/linuxwacom-devel

Reply via email to