Attachment 'xf86Fpit.c'
Download
Toggle line numbers
1 /*
2 * Copyright 1995, 1999 by Patrick Lecoanet, France. <lecoanet@cena.dgac.fr>
3 * Copyright 2002, Red Hat <alan@redhat.com>
4 *
5 * This driver is a merge of the Elographics driver (from Patrick Lecoanet) and
6 * the driver for Fujitsu Pen Computers from Rob Tsuk and John Apfelbaum.
7 *
8 * Modified for Stylistic 3400 passive pen support by David Clay
9 * Fixed processing of all packets
10 * Detangled and simplified if-statement logic
11 * Fixed hover-mode pointer movement
12 * Added Passive parameter for passive displays
13 * Added switch 3 for "right" mouse button
14 * I might have broken active pen support. I can't test it.
15 * January 2005 <dave at claysrus.com>
16 *
17 * Stylistic 500, 1000, 1200, 2300 Support fixed by John Apfelbaum
18 * June 2001 <johnapf@linuxlsate.com>
19 *
20 * Richard Miller-Smith <Richard.Miller-Smith@philips.com>
21 *
22 * Fixed up for XFree86 4.2, cleaned up the junk, cured crash on pointer
23 * setting.
24 *
25 * Permission to use, copy, modify, distribute, and sell this software and its
26 * documentation for any purpose is hereby granted without fee, provided that
27 * the above copyright notice appear in all copies and that both that
28 * copyright notice and this permission notice appear in supporting
29 * documentation, and that the name of Patrick Lecoanet not be used in
30 * advertising or publicity pertaining to distribution of the software without
31 * specific, written prior permission. The Authors make no
32 * representations about the suitability of this software for any purpose. It
33 * is provided "as is" without express or implied warranty.
34 *
35 * PATRICK LECOANET DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE,
36 * INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS, IN NO
37 * EVENT SHALL PATRICK LECOANET BE LIABLE FOR ANY SPECIAL, INDIRECT OR
38 * CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE,
39 * DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER
40 * TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR
41 * PERFORMANCE OF THIS SOFTWARE.
42 *
43 * RED HAT DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE,
44 * INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS, IN NO
45 * EVENT SHALL RED HAT BE LIABLE FOR ANY SPECIAL, INDIRECT OR
46 * CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE,
47 * DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER
48 * TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR
49 * PERFORMANCE OF THIS SOFTWARE.
50 *
51 */
52 /* $XFree86: xc/programs/Xserver/hw/xfree86/input/fpit/xf86Fpit.c,v 1.6 2004/04/26 22:48:21 dawes Exp $ */
53
54 #ifdef HAVE_CONFIG_H
55 #include "config.h"
56 #endif
57
58 #include <xf86Version.h>
59
60 #include <unistd.h>
61 #include <errno.h>
62 #include <string.h>
63
64 # include <misc.h>
65 # include <xf86.h>
66 # include <xf86_OSproc.h>
67 # include <xf86Xinput.h>
68 # include <exevents.h>
69 # include <randrstr.h>
70
71 # include <xf86Module.h>
72
73 /*
74 ***************************************************************************
75 *
76 * Define scaling constants to fix problem with Fujitsu Stylistic 3400/3500
77 *
78 ***************************************************************************
79 */
80
81 #define SCALE_X 4.0f // for 1024x768 should be 4.0 ; 800x600 5.12
82 #define SCALE_Y 5.4f // for 1024x768 should be 5.4 ; 800x600 6.91
83
84
85 /*
86 ***************************************************************************
87 *
88 * Default constants.
89 *
90 ***************************************************************************
91 */
92 #define FPIT_PORT "/dev/ttyS1"
93
94 #define FPIT_MAX_X 4070
95 #define FPIT_MIN_X 0
96 #define FPIT_MAX_Y 4020
97 #define FPIT_MIN_Y 0
98
99
100 /*
101 ***************************************************************************
102 *
103 * Protocol constants.
104 *
105 ***************************************************************************
106 */
107 #define FPIT_PACKET_SIZE 5
108 #define BUFFER_SIZE (FPIT_PACKET_SIZE*20)
109
110 /*
111 ***************************************************************************
112 *
113 * Screen orientation descriptors.
114 *
115 ***************************************************************************
116 */
117
118 typedef enum {
119 FPIT_INVERT_X = 0x01,
120 FPIT_INVERT_Y = 0x02,
121 FPIT_THEN_SWAP_XY = 0x04
122 } FpitOrientation;
123
124 /*
125 ***************************************************************************
126 *
127 * Device private records.
128 *
129 ***************************************************************************
130 */
131 typedef struct {
132 char *fpitDev; /* device file name */
133 int screen_width;
134 int screen_height;
135 Rotation screen_rotation;
136 int screen_no;
137 int fpitOldX; /* previous X position */
138 int fpitOldY; /* previous Y position */
139 int fpitOldProximity; /* previous proximity */
140 int fpitOldButtons; /* previous buttons state */
141 int fpitMinX; /* min X value */
142 int fpitMinY; /* min Y value */
143 int fpitMaxX; /* max X value */
144 int fpitMaxY; /* max Y value */
145 int fpitIndex; /* number of bytes read */
146 unsigned char fpitData[BUFFER_SIZE]; /* data read on the device */
147 FpitOrientation fpitBaseOrientation; /* read from X config */
148 FpitOrientation fpitTotalOrientation; /* above + RandR */
149 int fpitPassive; /* translate passive buttons */
150 int fpitTrackRandR; /* check for, react to screen rotate/resize */
151 /* XXX when this last option is unset, we provide "compatibly stupid"
152 * behavior. */
153 } FpitPrivateRec, *FpitPrivatePtr;
154
155
156
157
158 /*
159 ***************************************************************************
160 *
161 * xf86FpitConvert --
162 * Convert extended valuators to x and y suitable for core motion
163 * events. Return True if ok and False if the requested conversion
164 * can't be done for the specified valuators.
165 *
166 ***************************************************************************
167 */
168 static Bool xf86FpitConvert(LocalDevicePtr local, int first, int num, int v0, int v1, int v2, int v3, int v4, int v5, int *x, int *y)
169 {
170 FpitPrivatePtr priv = (FpitPrivatePtr) local->private;
171 AxisInfoPtr axes = local->dev->valuator->axes;
172 if (first != 0 || num != 2) {
173 return FALSE;
174 }
175
176 *x = xf86ScaleAxis(v0, 0, priv->screen_width, axes[0].min_value, axes[0].max_value);
177 *y = xf86ScaleAxis(v1, 0, priv->screen_height, axes[1].min_value, axes[1].max_value);
178
179 return TRUE;
180 }
181
182 /*
183 ***************************************************************************
184 *
185 * xf86FpitSetUpAxes --
186 * Based on current screen resolution and, if RandR support is enabled,
187 * current rotation state, set up the XInput axes and orientation info.
188 *
189 ***************************************************************************
190 */
191
192 static void xf86FpitSetUpAxes(DeviceIntPtr dev, FpitPrivatePtr priv)
193 {
194 /*
195 * Device reports motions on 2 axes in absolute coordinates.
196 * Axes min and max values are reported in raw coordinates.
197 * Resolution is computed roughly by the difference between
198 * max and min values scaled from the approximate size of the
199 * screen to fit one meter.
200 */
201 int quarter_turns;
202
203 priv->screen_width = screenInfo.screens[priv->screen_no]->width;
204 priv->screen_height = screenInfo.screens[priv->screen_no]->height;
205
206 priv->fpitTotalOrientation = priv->fpitBaseOrientation;
207 if (!priv->fpitTrackRandR)
208 return;
209
210 /* now apply transforms specified by RandR:
211 * slightly complicated because invertX/Y and swapXY don't commute. */
212 priv->screen_rotation = RRGetRotation(screenInfo.screens[priv->screen_no]);
213 quarter_turns = (
214 (priv->screen_rotation & RR_Rotate_90 ? 1 : 0) +
215 (priv->screen_rotation & RR_Rotate_180 ? 2 : 0) +
216 (priv->screen_rotation & RR_Rotate_270 ? 3 : 0) ) % 4;
217 if (quarter_turns / 2 != 0)
218 priv->fpitTotalOrientation ^= FPIT_INVERT_X | FPIT_INVERT_Y;
219 if (quarter_turns % 2 != 0) {
220 priv->fpitTotalOrientation ^=
221 (priv->fpitTotalOrientation & FPIT_THEN_SWAP_XY ? FPIT_INVERT_X : FPIT_INVERT_Y)
222 | FPIT_THEN_SWAP_XY;
223 }
224
225 if (priv->fpitTotalOrientation & FPIT_THEN_SWAP_XY) {
226 InitValuatorAxisStruct(dev, 1, priv->fpitMinX, priv->fpitMaxX, 9500, 0 /* min_res */ ,
227 9500 /* max_res */ );
228 InitValuatorAxisStruct(dev, 0, priv->fpitMinY, priv->fpitMaxY, 10500, 0 /* min_res */ ,
229 10500 /* max_res */ );
230 } else {
231 InitValuatorAxisStruct(dev, 0, priv->fpitMinX, priv->fpitMaxX, 9500, 0 /* min_res */ ,
232 9500 /* max_res */ );
233 InitValuatorAxisStruct(dev, 1, priv->fpitMinY, priv->fpitMaxY, 10500, 0 /* min_res */ ,
234 10500 /* max_res */ );
235 }
236 }
237 /*
238 ** xf86FpitReadInput
239 ** Reads from the Fpit and posts any new events to the server.
240 */
241 static void xf86FpitReadInput(LocalDevicePtr local)
242 {
243 FpitPrivatePtr priv = (FpitPrivatePtr) local->private;
244 int len, loop;
245 int is_core_pointer = 0;
246 int x, y, buttons, prox;
247 DeviceIntPtr device;
248 int conv_x, conv_y;
249
250 if (priv->fpitTrackRandR && (
251 priv->screen_width != screenInfo.screens[priv->screen_no]->width ||
252 priv->screen_height != screenInfo.screens[priv->screen_no]->height ||
253 priv->screen_rotation != RRGetRotation(screenInfo.screens[priv->screen_no])
254 ))
255 xf86FpitSetUpAxes(local->dev, priv);
256
257 do { /* keep reading blocks until there are no more */
258
259 /* Read data into buffer */
260 len = xf86ReadSerial(local->fd, priv->fpitData+priv->fpitIndex, BUFFER_SIZE-priv->fpitIndex);
261 if (len <= 0) {
262 Error("error reading FPIT device");
263 priv->fpitIndex = 0;
264 return;
265 }
266
267
268 /* Since the Fujitsu only delivers data in an absolute mode, we
269 can look through the data backwards to find the last full and valid
270 position. (This may make cursor movement a bit faster) */
271
272 /* DMC: We want to process ALL packets! This way, all points will come
273 through and drawing curves are smoother. Also we won't miss any
274 button events.
275 */
276
277 priv->fpitIndex += len;
278
279
280 #define PHASING_BIT 0x80
281 #define PROXIMITY_BIT 0x20
282 #define BUTTON_BITS 0x07
283 #define SW1 0x01
284 #define SW2 0x02
285 #define SW3 0x04
286
287 /* process each packet in this block */
288 /* Format of 5 bytes data packet for Fpit Tablets
289 Byte 1
290 bit 7 (0x80) Phasing bit always 1
291 bit 6 (0x40) Switch status change
292 bit 5 (0x20) Proximity
293 bit 4 (0x10) Always 0
294 bit 3 (0x08) Test data
295 bits 2-0 (0x07) Buttons:
296 bit 2 (0x04) Sw3 (2nd side sw)
297 bit 1 (0x02) Sw2 (1st side sw)
298 bit 0 (0x01) Sw1 (Pen tip sw)
299
300 Byte 2
301 bit 7 (0x80) Always 0
302 bits 6-0 (0x7f) X6 - X0
303
304 Byte 3
305 bit 7 (0x80) Always 0
306 bits 6-0 (0x7f) X13 - X7
307
308 Byte 4
309 bit 7 (0x80) Always 0
310 bits 6-0 (0x7f) Y6 - Y0
311
312 Byte 5
313 bit 7 (0x80) Always 0
314 bits 6-0 (0x7f) Y13 - Y7
315 */
316 for (loop=0;loop+FPIT_PACKET_SIZE<=priv->fpitIndex;loop++) {
317 if (!(priv->fpitData[loop] & PHASING_BIT)) continue; /* we don't have a start bit yet */
318
319 x = (int) (priv->fpitData[loop + 1] & 0x7f) + ((int) (priv->fpitData[loop + 2] & 0x7f) << 7);
320 y = (int) (priv->fpitData[loop + 3] & 0x7f) + ((int) (priv->fpitData[loop + 4] & 0x7f) << 7);
321 x = (int) (x/SCALE_X);
322 y = (int) (y/SCALE_Y);
323 /* Adjust to orientation */
324 if (priv->fpitTotalOrientation & FPIT_INVERT_X)
325 x = priv->fpitMaxX - x + priv->fpitMinX;
326 if (priv->fpitTotalOrientation & FPIT_INVERT_Y)
327 y = priv->fpitMaxY - y + priv->fpitMinY;
328 if (priv->fpitTotalOrientation & FPIT_THEN_SWAP_XY) {
329 int z = x; x = y; y = z;
330 }
331
332 prox = (priv->fpitData[loop] & PROXIMITY_BIT) ? 0 : 1;
333 buttons = (priv->fpitData[loop] & BUTTON_BITS);
334 device = local->dev;
335 #if GET_ABI_MAJOR(ABI_XINPUT_VERSION) == 0
336 is_core_pointer = xf86IsCorePointer(device);
337 #endif
338
339 xf86FpitConvert(local, 0, 2, x, y, 0, 0, 0, 0, &conv_x, &conv_y);
340 xf86XInputSetScreen(local, priv->screen_no, conv_x, conv_y);
341
342 /* coordinates are ready we can send events */
343
344 if (prox!=priv->fpitOldProximity) /* proximity changed */
345 if (!is_core_pointer) xf86PostProximityEvent(device, prox, 0, 2, x, y);
346
347 if (priv->fpitOldX != x || priv->fpitOldY != y) /* position changed */
348 xf86PostMotionEvent(device, 1, 0, 2, x, y);
349
350 if (priv->fpitPassive) {
351 /*
352 For passive pen (Stylistic 3400, et al.):
353 sw1 = 1 if pen is moving
354 sw2 = 1 if pen was lifted from the pad / isn't in contact
355 sw3 = 1 if right mouse-button icon was chosen
356 */
357 /* convert the pen button bits to actual mouse buttons */
358 if (buttons & SW2) buttons=0; /* the pen was lifted, so no buttons are pressed */
359 else if (buttons & SW3) buttons=SW3; /* the "right mouse" button was pressed, so send down event */
360 else if (prox) buttons=SW1; /* the "left mouse" button was pressed and we are not hovering, so send down event */
361 else buttons=0; /* We are in hover mode, so not left-clicking. */
362 }
363 /* the active pen's buttons map directly to the mouse buttons. Right-click may happen even in hover mode. */
364
365 /* DBG(2, ErrorF("%02d/%02d Prox=%d SW:%x Buttons:%x->%x (%d, %d)\n",
366 loop,priv->fpitIndex,prox,priv->fpitData[loop]&BUTTON_BITS,priv->fpitOldButtons,buttons,x,y));*/
367
368 if (priv->fpitOldButtons != buttons) {
369 int delta;
370 delta = buttons ^ priv->fpitOldButtons; /* set delta to the bits that have changed */
371 while (delta) {
372 int id;
373 id = ffs(delta);
374 delta &= ~(1 << (id - 1));
375 xf86PostButtonEvent(device, 1, id, (buttons & (1 << (id - 1))), 0, 2, x, y);
376 /* DBG(1, ErrorF("Button %d %s\n",id,(buttons & (1 << (id - 1)))?"DOWN":"UP"));*/
377 }
378 priv->fpitOldButtons = buttons;
379 }
380 priv->fpitOldX = x;
381 priv->fpitOldY = y;
382 priv->fpitOldProximity = prox;
383
384 loop+=FPIT_PACKET_SIZE-1; /* advance to the next packet */
385 } /* for each packet */
386
387 /* remove from the data buffer all that we have processed */
388 if (loop<priv->fpitIndex) memmove(priv->fpitData, priv->fpitData+loop,priv->fpitIndex-loop);
389 priv->fpitIndex-=loop;
390
391 /* DMC: My system did not read the pen-up event until another event was
392 posted, the result was the button sticking down even though
393 I had lifted the pen. So I am checking the device for more data
394 and then retrieving it. This fixed it for me. I don't know if this is just my system. */
395
396 } while (xf86WaitForInput(local->fd,0)>0); /* go back and check for more data (we don't want to block for I/O!) */
397
398 return;
399 }
400
401 static void xf86FpitPtrCtrl(DeviceIntPtr device, PtrCtrl *ctrl)
402 {
403 /* I have no clue what this does, except that registering it stops the
404 X server segfaulting in ProcGetPointerMapping()
405 Ho Hum.
406 */
407 }
408
409
410 /*
411 ***************************************************************************
412 *
413 * xf86FpitControl --
414 *
415 ***************************************************************************
416 */
417 static Bool xf86FpitControl(DeviceIntPtr dev, int mode)
418 {
419 LocalDevicePtr local = (LocalDevicePtr) dev->public.devicePrivate;
420 FpitPrivatePtr priv = (FpitPrivatePtr) (local->private);
421 unsigned char map[] = {
422 0, 1, 2, 3 /* DMC: changed this so we can use all three buttons */
423 };
424
425
426 switch (mode) {
427 case DEVICE_INIT:
428 {
429
430 if (priv->screen_no >= screenInfo.numScreens || priv->screen_no < 0) {
431 priv->screen_no = 0;
432 }
433 /*
434 * Device reports button press for up to 3 buttons.
435 */
436 if (InitButtonClassDeviceStruct(dev, 3, map) == FALSE) {
437 ErrorF("Unable to allocate Fpit touchscreen ButtonClassDeviceStruct\n");
438 return !Success;
439 }
440
441 if (InitFocusClassDeviceStruct(dev) == FALSE) {
442 ErrorF("Unable to allocate Fpit touchscreen FocusClassDeviceStruct\n");
443 return !Success;
444 }
445
446 if(InitPtrFeedbackClassDeviceStruct(dev, xf86FpitPtrCtrl) == FALSE) {
447 ErrorF("Unable to allocate PtrFeedBackClassDeviceStruct\n");
448 }
449
450 if (InitValuatorClassDeviceStruct(dev, 2, xf86GetMotionEvents, local->history_size, Absolute) == FALSE) {
451 ErrorF("Unable to allocate Fpit touchscreen ValuatorClassDeviceStruct\n");
452 return !Success;
453 }
454 xf86FpitSetUpAxes(dev, priv);
455
456 if (InitFocusClassDeviceStruct(dev) == FALSE) {
457 ErrorF("Unable to allocate Fpit touchscreen FocusClassDeviceStruct\n");
458 }
459 /*
460 * Allocate the motion events buffer.
461 */
462 xf86MotionHistoryAllocate(local);
463 /*
464 * This once has caused the server to crash after doing an xalloc & strcpy ??
465 */
466 return Success;
467 }
468
469 case DEVICE_ON:
470 if (local->fd < 0) {
471 local->fd = xf86OpenSerial(local->options);
472 if (local->fd < 0) {
473 Error("Unable to open Fpit touchscreen device");
474 return !Success;
475 }
476
477 xf86AddEnabledDevice(local);
478 dev->public.on = TRUE;
479 }
480 return Success;
481
482 /*
483 * Deactivate the device. After this, the device will not emit
484 * events until a subsequent DEVICE_ON. Thus, we can momentarily
485 * close the port.
486 */
487 case DEVICE_OFF:
488 dev->public.on = FALSE;
489 if (local->fd >= 0) {
490 xf86RemoveEnabledDevice(local);
491 }
492 xf86CloseSerial(local->fd);
493 local->fd = -1;
494 return Success;
495 /*
496 * Final close before server exit. This is used during server shutdown.
497 * Close the port and free all the resources.
498 */
499 case DEVICE_CLOSE:
500 dev->public.on = FALSE;
501 if (local->fd >= 0) {
502 RemoveEnabledDevice(local->fd);
503 }
504 xf86CloseSerial(local->fd);
505 local->fd = -1;
506 return Success;
507 default:
508 ErrorF("unsupported mode=%d\n", mode);
509 return !Success;
510 }
511 }
512
513 /*
514 ***************************************************************************
515 *
516 * xf86FpitAllocate --
517 *
518 ***************************************************************************
519 */
520 static LocalDevicePtr xf86FpitAllocate(InputDriverPtr drv)
521 {
522 LocalDevicePtr local;
523 FpitPrivatePtr priv;
524 priv = xalloc(sizeof(FpitPrivateRec));
525 if (!priv)
526 return NULL;
527 local = xf86AllocateInput(drv, 0);
528 if (!local) {
529 xfree(priv);
530 return NULL;
531 }
532
533 priv->fpitDev = strdup(FPIT_PORT);
534 priv->screen_no = 0;
535 priv->screen_width = -1;
536 priv->screen_height = -1;
537 priv->screen_rotation = RR_Rotate_0;
538 priv->fpitMinX = FPIT_MIN_X;
539 priv->fpitMaxX = FPIT_MAX_X;
540 priv->fpitMinY = FPIT_MIN_Y;
541 priv->fpitMaxY = FPIT_MAX_Y;
542 priv->fpitOldX = priv->fpitOldY = -1;
543 priv->fpitOldButtons = 0;
544 priv->fpitOldProximity = 0;
545 priv->fpitIndex = 0;
546 priv->fpitPassive = 0;
547 local->name = XI_TOUCHSCREEN;
548 local->flags = 0 /* XI86_NO_OPEN_ON_INIT */ ;
549 local->device_control = xf86FpitControl;
550 local->read_input = xf86FpitReadInput;
551 local->control_proc = NULL;
552 local->close_proc = NULL;
553 local->switch_mode = NULL;
554 local->conversion_proc = xf86FpitConvert;
555 local->reverse_conversion_proc = NULL;
556 local->fd = -1;
557 local->atom = 0;
558 local->dev = NULL;
559 local->private = priv;
560 local->type_name = "Fujitsu Stylistic";
561 local->history_size = 0;
562 return local;
563 }
564
565 static void xf86FpitUninit(InputDriverPtr drv, LocalDevicePtr local, int flags)
566 {
567 FpitPrivatePtr priv = (FpitPrivatePtr) local->private;
568 xf86FpitControl(local->dev, DEVICE_OFF);
569 xfree(priv->fpitDev);
570 xfree(priv);
571 xfree(local->name);
572 xfree(local);
573 xf86DeleteInput(local, 0);
574 }
575
576 static const char *default_options[] = {
577 "BaudRate", "19200", "StopBits", "0", "DataBits", "8", "Parity", "None", "Vmin", "10", "Vtime", "1", "FlowControl", "None", NULL
578 };
579
580 static InputInfoPtr xf86FpitInit(InputDriverPtr drv, IDevPtr dev, int flags)
581 {
582 LocalDevicePtr local = NULL;
583 FpitPrivatePtr priv = NULL;
584 char *str;
585
586 local = xf86FpitAllocate(drv);
587 if (!local)
588 return NULL;
589
590 priv = local->private;
591 local->conf_idev = dev;
592 xf86CollectInputOptions(local, default_options, NULL);
593 /* Process the common options. */
594 xf86ProcessCommonOptions(local, local->options);
595 str = xf86FindOptionValue(local->options, "Device");
596 if (!str) {
597 xf86Msg(X_ERROR, "%s: No Device specified in FPIT module config.\n", dev->identifier);
598 if (priv) {
599 if (priv->fpitDev) {
600 xfree(priv->fpitDev);
601 }
602 xfree(priv);
603 }
604 return local;
605 }
606 priv->fpitDev = strdup(str);
607 local->name = xf86SetStrOption(local->options, "DeviceName", XI_TOUCHSCREEN);
608 xf86Msg(X_CONFIG, "FPIT device name: %s\n", local->name);
609 priv->screen_no = xf86SetIntOption(local->options, "ScreenNo", 0);
610 xf86Msg(X_CONFIG, "Fpit associated screen: %d\n", priv->screen_no);
611 priv->fpitMaxX = xf86SetIntOption(local->options, "MaximumXPosition", FPIT_MAX_X);
612 xf86Msg(X_CONFIG, "FPIT maximum x position: %d\n", priv->fpitMaxX);
613 priv->fpitMinX = xf86SetIntOption(local->options, "MinimumXPosition", FPIT_MIN_X);
614 xf86Msg(X_CONFIG, "FPIT minimum x position: %d\n", priv->fpitMinX);
615 priv->fpitMaxY = xf86SetIntOption(local->options, "MaximumYPosition", FPIT_MAX_Y);
616 xf86Msg(X_CONFIG, "FPIT maximum y position: %d\n", priv->fpitMaxY);
617 priv->fpitMinY = xf86SetIntOption(local->options, "MinimumYPosition", FPIT_MIN_Y);
618 xf86Msg(X_CONFIG, "FPIT minimum y position: %d\n", priv->fpitMinY);
619
620 priv->fpitBaseOrientation = 0;
621 if (xf86SetBoolOption(local->options, "InvertX", 0))
622 priv->fpitBaseOrientation |= FPIT_INVERT_X;
623 if (xf86SetBoolOption(local->options, "InvertY", 0))
624 priv->fpitBaseOrientation |= FPIT_INVERT_Y;
625 if (xf86SetBoolOption(local->options, "SwapXY", 0))
626 priv->fpitBaseOrientation |= FPIT_THEN_SWAP_XY;
627 priv->fpitPassive = xf86SetBoolOption(local->options, "Passive", 0);
628 priv->fpitTrackRandR = xf86SetBoolOption(local->options, "TrackRandR", 0);
629 /* XXX "Rotate" option provides compatibly stupid behavior. JEB. */
630 str = xf86SetStrOption(local->options, "Rotate", 0);
631 if (!xf86NameCmp(str, "CW"))
632 priv->fpitBaseOrientation |= FPIT_INVERT_X | FPIT_INVERT_Y | FPIT_THEN_SWAP_XY;
633 else if (!xf86NameCmp(str, "CCW"))
634 priv->fpitBaseOrientation |= FPIT_THEN_SWAP_XY;
635 xf86Msg(X_CONFIG, "FPIT invert X axis: %s\n", priv->fpitBaseOrientation & FPIT_INVERT_X ? "Yes" : "No");
636 xf86Msg(X_CONFIG, "FPIT invert Y axis: %s\n", priv->fpitBaseOrientation & FPIT_INVERT_Y ? "Yes" : "No");
637 xf86Msg(X_CONFIG, "FPIT swap X and Y axis: %s\n", priv->fpitBaseOrientation & FPIT_THEN_SWAP_XY ? "Yes" : "No");
638 xf86Msg(X_CONFIG, "FPIT Passive button mode: %s\n", priv->fpitPassive ? "Yes" : "No");
639 xf86Msg(X_CONFIG, "FPIT RandR tracking: %s\n", priv->fpitTrackRandR ? "Yes" : "No");
640 /* mark the device configured */
641 local->flags |= XI86_CONFIGURED;
642 return local;
643 }
644
645
646 _X_EXPORT InputDriverRec FPIT = {
647 1, /* driver version */
648 "fpit", /* driver name */
649 NULL, /* identify */
650 xf86FpitInit, /* pre-init */
651 xf86FpitUninit, /* un-init */
652 NULL, /* module */
653 0 /* ref count */
654 };
655
656 #ifdef XFree86LOADER
657 static pointer Plug(pointer module, pointer options, int *errmaj, int *errmin)
658 {
659 xf86AddInputDriver(&FPIT, module, 0);
660 return module;
661 }
662
663 static void Unplug(pointer p)
664 {
665 }
666
667 static XF86ModuleVersionInfo version_rec = {
668 "fpit",
669 MODULEVENDORSTRING,
670 MODINFOSTRING1,
671 MODINFOSTRING2,
672 XORG_VERSION_CURRENT,
673 PACKAGE_VERSION_MAJOR, PACKAGE_VERSION_MINOR, PACKAGE_VERSION_PATCHLEVEL,
674 ABI_CLASS_XINPUT,
675 ABI_XINPUT_VERSION,
676 MOD_CLASS_XINPUT,
677 {0, 0, 0, 0}
678 };
679
680 /*
681 * This is the entry point in the module. The name
682 * is setup after the pattern <module_name>ModuleData.
683 * Do not change it.
684 */
685 _X_EXPORT XF86ModuleData fpitModuleData = {
686 &version_rec, Plug, Unplug
687 };
688 #endif
689
Attached Files
To refer to attachments on a page, use attachment:filename, as shown below in the list of files. Do NOT use the URL of the [get] link, since this is subject to change and can break easily.You are not allowed to attach a file to this page.