diff --git a/driver/xf86-input-ws/man/ws.man b/driver/xf86-input-ws/man/ws.man index 09c23c15e..8551e2513 100644 --- a/driver/xf86-input-ws/man/ws.man +++ b/driver/xf86-input-ws/man/ws.man @@ -1,4 +1,4 @@ -.\" $OpenBSD: ws.man,v 1.12 2011/11/28 23:49:59 shadchin Exp $ +.\" $OpenBSD: ws.man,v 1.13 2012/06/12 17:12:50 shadchin Exp $ .\" .\" Copyright (c) 2005,2009,2011 Matthieu Herrb .\" @@ -53,6 +53,16 @@ Please refer to __xconfigfile__(__filemansuffix__) for general configuration details and for options that can be used with all input drivers. This section only covers configuration details specific to this driver. .TP 4 +.BI "Option \*qButtonMapping\*q \*q" string \*q +Sets the button mapping for this device. The mapping is a space-separated list +of button mappings that correspond in order to the physical buttons on the +device (i.e. the first number is the mapping for button 1, etc.). The default +mapping is "1 2 3 ... 32". A mapping of 0 deactivates the button. Multiple +buttons can have the same mapping. +For example, a left-handed mouse with deactivated scroll-wheel would use a +mapping of "3 2 1 0 0". Invalid mappings are ignored and the default mapping +is used. Buttons not specified in the user's mapping use the default mapping. +.TP 4 .BI "Option \*qButtons\*q \*q" integer \*q Specifies the number of mouse buttons. In cases where the number of buttons cannot be auto-detected, the diff --git a/driver/xf86-input-ws/src/ws.c b/driver/xf86-input-ws/src/ws.c index fded40f38..5e94a4bba 100644 --- a/driver/xf86-input-ws/src/ws.c +++ b/driver/xf86-input-ws/src/ws.c @@ -13,7 +13,7 @@ * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ -/* $OpenBSD: ws.c,v 1.53 2012/06/12 17:10:03 shadchin Exp $ */ +/* $OpenBSD: ws.c,v 1.54 2012/06/12 17:12:50 shadchin Exp $ */ #ifdef HAVE_CONFIG_H #include "config.h" @@ -120,7 +120,7 @@ wsPreInit(InputDriverPtr drv, InputInfoPtr pInfo, int flags) WSDevicePtr priv; MessageType buttons_from = X_CONFIG; char *s; - int rc = BadValue; + int i, phy_btn = 1, rc = BadValue; priv = (WSDevicePtr)calloc(1, sizeof(WSDeviceRec)); if (priv == NULL) { @@ -145,6 +145,31 @@ wsPreInit(InputDriverPtr drv, InputInfoPtr pInfo, int flags) buttons_from = X_DEFAULT; } + /* Check for user-defined button mapping */ + s = xf86SetStrOption(pInfo->options, "ButtonMapping", NULL); + if (s) { + char *map = s, *end; + int btn; + + do { + btn = strtol(map, &end, 10); + + if (end == map || btn < 0 || btn > NBUTTONS) { + xf86IDrvMsg(pInfo, X_ERROR, + "Invalid button mapping. Using defaults\n"); + phy_btn = 1; /* ensure defaults start at 1 */ + break; + } + + priv->btnmap[phy_btn++] = btn; + map = end; + } while (end && *end != '\0' && phy_btn <= NBUTTONS); + free(s); + } + + for (i = phy_btn; i <= NBUTTONS; i++) + priv->btnmap[i] = i; + wsWheelHandleButtonMap(pInfo, &(priv->Z), "ZAxisMapping", "4 5"); wsWheelHandleButtonMap(pInfo, &(priv->W), "WAxisMapping", "6 7"); @@ -295,8 +320,7 @@ wsDeviceInit(DeviceIntPtr pWS) { InputInfoPtr pInfo = (InputInfoPtr)pWS->public.devicePrivate; WSDevicePtr priv = (WSDevicePtr)pInfo->private; - unsigned char map[NBUTTONS + 1]; - int i, xmin, xmax, ymin, ymax; + int xmin, xmax, ymin, ymax; Atom btn_labels[NBUTTONS] = {0}; Atom axes_labels[NAXES] = {0}; @@ -305,12 +329,8 @@ wsDeviceInit(DeviceIntPtr pWS) btn_labels[0] = XIGetKnownProperty(BTN_LABEL_PROP_BTN_LEFT); btn_labels[1] = XIGetKnownProperty(BTN_LABEL_PROP_BTN_MIDDLE); btn_labels[2] = XIGetKnownProperty(BTN_LABEL_PROP_BTN_RIGHT); - for (i = 0; i < NBUTTONS; i++) - map[i + 1] = i + 1; - if (!InitButtonClassDeviceStruct(pWS, - min(priv->buttons, NBUTTONS), - btn_labels, - map)) + if (!InitButtonClassDeviceStruct(pWS, min(priv->buttons, NBUTTONS), + btn_labels, priv->btnmap)) return !Success; if (priv->type == WSMOUSE_TYPE_TPANEL) { diff --git a/driver/xf86-input-ws/src/ws.h b/driver/xf86-input-ws/src/ws.h index fd84b633d..83029547b 100644 --- a/driver/xf86-input-ws/src/ws.h +++ b/driver/xf86-input-ws/src/ws.h @@ -43,7 +43,6 @@ typedef struct { typedef struct WSDevice { char *devName; /* device name */ int type; /* ws device type */ - unsigned int buttons; /* # of buttons */ unsigned int lastButtons; /* last state of buttons */ int old_ax, old_ay; int min_x, max_x, min_y, max_y; /* coord space */ @@ -56,13 +55,17 @@ typedef struct WSDevice { WheelAxis W; struct wsmouse_calibcoords coords; /* mirror of the kernel values */ + /* # of buttons and config-file specified button mapping */ + unsigned int buttons; + unsigned char btnmap[NBUTTONS + 1]; + /* Middle mouse button emulation */ struct { BOOL enabled; - BOOL pending; /* timer waiting? */ - int buttonstate; /* phys. button state */ - int state; /* state machine (see emumb.c) */ - Time expires; /* time of expiry */ + BOOL pending; /* timer waiting? */ + int buttonstate; /* phys. button state */ + int state; /* state machine (see emumb.c) */ + Time expires; /* time of expiry */ Time timeout; } emulateMB;