static void* lircEventThread( CoreThread *thread, void *driver_data ) { LircData *data = (LircData*) driver_data; int readlen; char buf[128]; DFBInputEvent evt; memset( &evt, 0, sizeof(DFBInputEvent) ); while ((readlen = read( data->fd, buf, 128 )) > 0 || errno == EINTR) { dfb_thread_testcancel( thread ); if (readlen < 1) continue; evt.key_symbol = lirc_parse_line( buf ); if (evt.key_symbol != DIKS_NULL) { evt.type = DIET_KEYPRESS; evt.flags = DIEF_KEYSYMBOL; dfb_input_dispatch( data->device, &evt ); evt.type = DIET_KEYRELEASE; evt.flags = DIEF_KEYSYMBOL; dfb_input_dispatch( data->device, &evt ); } } if (readlen <= 0 && errno != EINTR) PERRORMSG ("lirc thread died\n"); return NULL; }
static void flush_xy( PS2MouseData *data ) { DFBInputEvent evt; if (data->dx) { evt.type = DIET_AXISMOTION; evt.flags = DIEF_AXISREL; evt.axis = DIAI_X; evt.axisrel = data->dx; /* Signal immediately following event. */ if (data->dy) evt.flags |= DIEF_FOLLOW; dfb_input_dispatch( data->device, &evt ); data->dx = 0; } if (data->dy) { evt.type = DIET_AXISMOTION; evt.flags = DIEF_AXISREL; evt.axis = DIAI_Y; evt.axisrel = data->dy; dfb_input_dispatch( data->device, &evt ); data->dy = 0; } }
/* * Input thread reading from device. * Generates events on incoming data. */ static void* dreamboxremoteEventThread( DirectThread *thread, void *driver_data ) { DreamboxremoteData *data = (DreamboxremoteData*) driver_data; int readlen; u16 rccode; DFBInputEvent evt; while ((readlen = read( data->fd, &rccode, 2 )) == 2) { direct_thread_testcancel( thread ); /* translate rccode to DirectFB keycode */ evt.key_symbol = dreamboxremote_parse_rccode( rccode ); if (evt.key_symbol != DIKS_NULL) { /* set event type and dispatch*/ evt.type = DIET_KEYPRESS; evt.flags = DIEF_KEYSYMBOL; dfb_input_dispatch( data->device, &evt ); /* set event type and dispatch*/ evt.type = DIET_KEYRELEASE; evt.flags = DIEF_KEYSYMBOL; dfb_input_dispatch( data->device, &evt ); } } if (readlen <= 0 && errno != EINTR) D_PERROR ("dreamboxremote thread died\n"); return NULL; }
/* * Input thread reading from device. * Generates events on incoming data. */ static void* sonypiEventThread( DirectThread *thread, void *driver_data ) { SonypiData *data = (SonypiData*) driver_data; int readlen; u8 buffer[16]; /* loop until error occurs except EINTR */ while ((readlen = read( data->fd, buffer, 16 )) > 0 || errno == EINTR) { int i; DFBInputEvent evt; direct_thread_testcancel( thread ); /* process each byte */ for (i=0; i<readlen; i++) { /* check for jogdial events */ switch (buffer[i]) { case SONYPI_EVENT_JOGDIAL_DOWN: case SONYPI_EVENT_JOGDIAL_UP: case SONYPI_EVENT_JOGDIAL_DOWN_PRESSED: case SONYPI_EVENT_JOGDIAL_UP_PRESSED: evt.type = DIET_AXISMOTION; evt.axis = DIAI_Z; evt.flags = DIEF_AXISREL; if (buffer[i] == SONYPI_EVENT_JOGDIAL_DOWN || buffer[i] == SONYPI_EVENT_JOGDIAL_DOWN_PRESSED) evt.axisrel = 1; else evt.axisrel = -1; dfb_input_dispatch( data->device, &evt ); break; case SONYPI_EVENT_JOGDIAL_PRESSED: case SONYPI_EVENT_JOGDIAL_RELEASED: if (buffer[i] == SONYPI_EVENT_JOGDIAL_PRESSED) evt.type = DIET_BUTTONPRESS; else evt.type = DIET_BUTTONRELEASE; evt.flags = DIEF_NONE; /* button is always valid */ evt.button = DIBI_MIDDLE; dfb_input_dispatch( data->device, &evt ); break; default: ; } } } if (readlen < 0) D_PERROR ("sonypi thread died\n"); return NULL; }
/* * Input thread reading from device. * Generates events on incoming data. */ static void* osxEventThread( DirectThread *thread, void *driver_data ) { OSXInputData *data = (OSXInputData*) driver_data; DFBOSX *dfb_osx = data->dfb_osx; while (!data->stop) { DFBInputEvent evt; EventRecord event; fusion_skirmish_prevail( &dfb_osx->lock ); /* Check for events */ while ( WaitNextEvent( everyEvent, &event, 0, nil) ) { fusion_skirmish_dismiss( &dfb_osx->lock ); switch (event.what) { case keyDown: case keyUp: case autoKey: if (event.what == keyUp) evt.type = DIET_KEYRELEASE; else evt.type = DIET_KEYPRESS; if (translate_key( event.message & (charCodeMask | keyCodeMask), &evt )) { dfb_input_dispatch( data->device, &evt ); } break; case mouseDown: evt.type = DIET_BUTTONPRESS; evt.button = DIBI_LEFT; dfb_input_dispatch( data->device, &evt ); break; case mouseUp: evt.type = DIET_BUTTONRELEASE; evt.button = DIBI_LEFT; dfb_input_dispatch( data->device, &evt ); break; default: printf("%d\n",event.what); break; } fusion_skirmish_prevail( &dfb_osx->lock ); } fusion_skirmish_dismiss( &dfb_osx->lock ); usleep(10000); direct_thread_testcancel( thread ); } return NULL; }
/* The main routine for PenMount */ static void *PenMountEventThread(DirectThread *thread, void *driver_data){ PeMData *data = (PeMData *) driver_data; /* Read data */ while (1) { DFBInputEvent evt; static int pressed = 0; if (!PeMGetEvent (data)) continue; direct_thread_testcancel (thread); /* Dispatch axis */ evt.type = DIET_AXISMOTION; evt.flags = DIEF_AXISABS; evt.axis = DIAI_X; evt.axisabs = data->x; dfb_input_dispatch (data->device, &evt); evt.type = DIET_AXISMOTION; evt.flags = DIEF_AXISABS; evt.axis = DIAI_Y; evt.axisabs = data->y; dfb_input_dispatch (data->device, &evt); /* Dispatch touch event */ switch (data->action) { case PEM_PANEL_TOUCH: if (!pressed) evt.type = DIET_BUTTONPRESS; pressed = 1; break; case PEM_PANEL_UNTOUCH: if (pressed) evt.type = DIET_BUTTONRELEASE; pressed = 0; break; } evt.flags = DIEF_NONE; evt.button = DIBI_LEFT; dfb_input_dispatch (data->device, &evt); direct_thread_testcancel (thread); } return NULL; }
static inline void mouse_motion_realize( SerialMouseData *data ) { if (data->x_motion.axisrel) { data->x_motion.flags = DIEF_AXISREL; dfb_input_dispatch( data->device, &data->x_motion ); data->x_motion.axisrel = 0; } if (data->y_motion.axisrel) { data->y_motion.flags = DIEF_AXISREL; dfb_input_dispatch( data->device, &data->y_motion ); data->y_motion.axisrel = 0; } }
static void motion_realize( OSXInputData *data ) { if (motionX.type != DIET_UNKNOWN) { dfb_input_dispatch( data->device, &motionX ); motionX.type = DIET_UNKNOWN; } if (motionY.type != DIET_UNKNOWN) { dfb_input_dispatch( data->device, &motionY ); motionY.type = DIET_UNKNOWN; } }
static void* keyboardEventThread( DirectThread *thread, void *driver_data ) { int readlen; unsigned char buf[64]; KeyboardData *data = (KeyboardData*) driver_data; /* Read keyboard data */ while ((readlen = read (data->vt_fd, buf, 64)) >= 0 || errno == EINTR) { int i; direct_thread_testcancel( thread ); for (i = 0; i < readlen; i++) { DFBInputEvent evt; evt.type = ((buf[i] & 0x80) ? DIET_KEYRELEASE : DIET_KEYPRESS); evt.flags = DIEF_KEYCODE; evt.key_code = buf[i] & 0x7f; dfb_input_dispatch( data->device, &evt ); keyboard_set_lights( data, evt.locks ); } if (readlen <= 0) usleep( 200000 ); } if (readlen <= 0 && errno != EINTR) D_PERROR ("keyboard thread died\n"); return NULL; }
static void joystick_handle_event( JoystickData *data, struct js_event jse ) { DFBInputEvent event; switch (jse.type) { case JS_EVENT_BUTTON: event.type = (jse.value ? DIET_BUTTONPRESS : DIET_BUTTONRELEASE); event.flags = DIEF_NONE; /* button is always valid */ event.button = jse.number; break; case JS_EVENT_AXIS: event.type = DIET_AXISMOTION; event.flags = DIEF_AXISABS; event.axis = jse.number; event.axisabs = jse.value; break; case JS_EVENT_INIT: case JS_EVENT_INIT | JS_EVENT_BUTTON: case JS_EVENT_INIT | JS_EVENT_AXIS: D_ONCE( "Joystick sends JS_EVENT_INIT events, " \ "make sure it has been calibrated using 'jscal -c'\n"); return; break; default: D_PERROR ("unknown joystick event type\n"); return; } dfb_input_dispatch( data->device, &event ); }
/* * Input thread reading from device. * Generates events on incoming data. */ static void* linux_input_EventThread( CoreThread *thread, void *driver_data ) { LinuxInputData *data = (LinuxInputData*) driver_data; int readlen; struct input_event levt; DFBInputEvent devt; while ((readlen = read( data->fd, &levt, sizeof(levt) )) == sizeof(levt) || (readlen < 0 && errno == EINTR)) { dfb_thread_testcancel( thread ); if (readlen <= 0) continue; if (translate_event( &levt, &devt)) dfb_input_dispatch( data->device, &devt ); } if (readlen <= 0) PERRORMSG ("linux_input thread died\n"); return NULL; }
static void motion_realize( X11InputData *data ) { if (motionX.type != DIET_UNKNOWN) { if (motionY.type != DIET_UNKNOWN) motionX.flags |= DIEF_FOLLOW; dfb_input_dispatch( data->device, &motionX ); motionX.type = DIET_UNKNOWN; } if (motionY.type != DIET_UNKNOWN) { dfb_input_dispatch( data->device, &motionY ); motionY.type = DIET_UNKNOWN; } }
static void motion_realize( SDLInputData *data ) { if (motionX.type != DIET_UNKNOWN) { if (motionY.type != DIET_UNKNOWN) { /* let DirectFB know two events are coming */ motionX.flags |= DIEF_FOLLOW; } dfb_input_dispatch( data->device, &motionX ); motionX.type = DIET_UNKNOWN; } if (motionY.type != DIET_UNKNOWN) { dfb_input_dispatch( data->device, &motionY ); motionY.type = DIET_UNKNOWN; } }
/* The main routine for elo */ static void *eloTouchEventThread(DirectThread *thread, void *driver_data) { eloData *data = (eloData *) driver_data; /* Read data */ while (1) { DFBInputEvent evt; if(eloGetEvent(data) == -1) continue; direct_thread_testcancel(thread); /* Dispatch axis */ evt.type = DIET_AXISMOTION; evt.flags = DIEF_AXISABS; evt.axis = DIAI_X; evt.axisabs = data->x; dfb_input_dispatch(data->device, &evt); evt.type = DIET_AXISMOTION; evt.flags = DIEF_AXISABS; evt.axis = DIAI_Y; evt.axisabs = data->y; dfb_input_dispatch(data->device, &evt); /* Dispatch touch event */ if(data->action & ELO_M_UNTOUCH) evt.type = DIET_BUTTONRELEASE; else evt.type = DIET_BUTTONPRESS; evt.flags = DIEF_NONE; evt.button = DIBI_LEFT; dfb_input_dispatch(data->device, &evt); direct_thread_testcancel(thread); } return NULL; }
static void motion_realize( X11InputData *data ) { if (motionX.type != DIET_UNKNOWN) { if (motionY.type != DIET_UNKNOWN) motionX.flags |= DIEF_FOLLOW; motionX.max = data->x11->showing_w - 1; // FIXME dfb_input_dispatch( data->device, &motionX ); motionX.type = DIET_UNKNOWN; } if (motionY.type != DIET_UNKNOWN) { motionY.max = data->x11->showing_h - 1; // FIXME dfb_input_dispatch( data->device, &motionY ); motionY.type = DIET_UNKNOWN; } }
static void InputHub_EventDispatch( void *ctx, DFBInputDeviceID device_id, const DFBInputEvent *event ) { InputHubDeviceNode *node; D_DEBUG_AT( Input_Hub, "%s( ID %u, %s )\n", __FUNCTION__, device_id, dfb_input_event_type_name(event->type) ); node = direct_hash_lookup( m_nodes, device_id ); if (node) { if (node->device) { DFBInputEvent event_copy = *event; D_DEBUG_AT( Input_Hub, " -> found device %p (ID %u)\n", node->device, dfb_input_device_id(node->device) ); dfb_input_dispatch( node->device, &event_copy ); } else D_WARN( "inactive device (ID %u)", device_id ); } else D_WARN( "unknown device (ID %u)", device_id ); }
// le thread qui sert à recevoir des données en continue : static void *ZytronicEventThread(DirectThread *thread, void *driver_data) { ZytData *data = (ZytData *) driver_data; int lastAction = ZYT_ACTION_RELEASE; struct timeval unT; unsigned int lastT,newT; unsigned short nbClignot=0; lastT = 0; DFBInputEvent evt; /* Read data */ while (1) { if (!ZytReadTouchMessage (data)){ // si jamais il y a eut mauvaise lecture (pas normal) continue; // on ignore le mesage mal lu } // en mode sans drag&drop, si l'action actuelle est la même que la précédente, on l'ignore: if (zytConf.mode==NO_DRAG_DROP && lastAction == data->action){ nbClignot=0; // et on dit que ça clignote pas (car c'est un appui long, pas un clignotement) continue; // permet de ne garder que le premier appui, et le relachement : } gettimeofday(&unT,NULL); newT = unT.tv_sec*1000000 + unT.tv_usec; if(zytConf.debug==DEBUG){ D_INFO("newT=%u\n",newT); D_INFO("lastT=%u\n",lastT); D_INFO("lastT+attente=%u\n",lastT+zytConf.attenteMultiClic); } // si on "appui" trop vite, sans faire un appui continu, on réenregistre la dernière action,... : if(data->action==ZYT_ACTION_TOUCH && nbClignot < zytConf.nbClignToPress && \ (lastT + zytConf.attenteMultiClic) > newT) { nbClignot++;// ..on compte combien de fois de suite on essai d'appuyer (pour voir si c'est la fin // d'un clignotement justement parce qu'on a rapprocher le doigt suffisemment) .. gettimeofday(&unT,NULL); lastT = unT.tv_sec*1000000 + unT.tv_usec; continue; // ..et on ignore cet appui (permet d'éviter le phénomène de clignotement..) } nbClignot=0; // on remet le compteur à zéro, puisque c'est ici un appui réel direct_thread_testcancel (thread); // si cette ligne fait bien ce que je pense (regarder si on n'a pas // demandé la fin du thread en cours) pourquoi est-elle là, et pas avant le "if" ? Car si le controlleur // n'envoi plus aucune information pendant un moment, le driver ne peut pas détecter de "cancel" // pendant ce laps de temps .. ? *** // Dispatch axis evt.type = DIET_AXISMOTION; evt.flags = DIEF_AXISABS; evt.axis = DIAI_X; evt.axisabs = data->x; dfb_input_dispatch (data->device, &evt); evt.type = DIET_AXISMOTION; evt.flags = DIEF_AXISABS; evt.axis = DIAI_Y; evt.axisabs = data->y; dfb_input_dispatch (data->device, &evt); // Dispatch touch event switch (data->action) { case ZYT_ACTION_TOUCH: evt.type = DIET_BUTTONPRESS; break; case ZYT_ACTION_RELEASE: evt.type = DIET_BUTTONRELEASE; break; } evt.flags = DIEF_NONE; evt.button = DIBI_LEFT; dfb_input_dispatch (data->device, &evt); lastAction = data->action; // on enregistre l'évènement gettimeofday(&unT,NULL); // on enregistre quand s'est produit l'évènement lastT = unT.tv_sec*1000000 + unT.tv_usec; if(zytConf.debug==DEBUG){ D_INFO("Zytronic TOUCH : x=%d y=%d action=%d\n", data->x,data->y,data->action); } direct_thread_testcancel (thread); } return NULL; }
/* * Input thread reading from device. * Generates events on incoming data. */ static void* sdlEventThread( DirectThread *thread, void *driver_data ) { SDLInputData *data = (SDLInputData*) driver_data; DFBSDL *dfb_sdl = data->dfb_sdl; while (!data->stop) { DFBInputEvent evt; SDL_Event event; fusion_skirmish_prevail( &dfb_sdl->lock ); /* Check for events */ while ( SDL_PollEvent(&event) ) { fusion_skirmish_dismiss( &dfb_sdl->lock ); switch (event.type) { case SDL_MOUSEMOTION: motion_compress( event.motion.x, event.motion.y ); break; case SDL_MOUSEBUTTONUP: case SDL_MOUSEBUTTONDOWN: motion_realize( data ); if (event.type == SDL_MOUSEBUTTONDOWN) evt.type = DIET_BUTTONPRESS; else evt.type = DIET_BUTTONRELEASE; evt.flags = DIEF_NONE; switch (event.button.button) { case SDL_BUTTON_LEFT: evt.button = DIBI_LEFT; break; case SDL_BUTTON_MIDDLE: evt.button = DIBI_MIDDLE; break; case SDL_BUTTON_RIGHT: evt.button = DIBI_RIGHT; break; case SDL_BUTTON_WHEELUP: case SDL_BUTTON_WHEELDOWN: if (event.type != SDL_MOUSEBUTTONDOWN) { fusion_skirmish_prevail( &dfb_sdl->lock ); continue; } evt.type = DIET_AXISMOTION; evt.flags = DIEF_AXISREL; evt.axis = DIAI_Z; if (event.button.button == SDL_BUTTON_WHEELUP) evt.axisrel = -1; else evt.axisrel = 1; break; default: fusion_skirmish_prevail( &dfb_sdl->lock ); continue; } dfb_input_dispatch( data->device, &evt ); break; case SDL_KEYUP: case SDL_KEYDOWN: if (event.type == SDL_KEYDOWN) evt.type = DIET_KEYPRESS; else evt.type = DIET_KEYRELEASE; /* Get a key id first */ translate_key( event.key.keysym.sym, &evt ); /* If SDL provided a symbol, use it */ if (event.key.keysym.unicode) { evt.flags |= DIEF_KEYSYMBOL; evt.key_symbol = event.key.keysym.unicode; /** * Hack to translate the Control+[letter] * combination to * Modifier: CONTROL, Key Symbol: [letter] * A side effect here is that Control+Backspace * produces Control+h */ if (evt.modifiers == DIMM_CONTROL && evt.key_symbol >= 1 && evt.key_symbol <= ('z'-'a'+1)) { evt.key_symbol += 'a'-1; } } dfb_input_dispatch( data->device, &evt ); break; case SDL_QUIT: evt.type = DIET_KEYPRESS; evt.flags = DIEF_KEYSYMBOL; evt.key_symbol = DIKS_ESCAPE; dfb_input_dispatch( data->device, &evt ); evt.type = DIET_KEYRELEASE; evt.flags = DIEF_KEYSYMBOL; evt.key_symbol = DIKS_ESCAPE; dfb_input_dispatch( data->device, &evt ); break; default: break; } fusion_skirmish_prevail( &dfb_sdl->lock ); } fusion_skirmish_dismiss( &dfb_sdl->lock ); motion_realize( data ); usleep(10000); direct_thread_testcancel( thread ); } return NULL; }
/* the main routine for MouseSystems */ static void* mouseEventThread_mousesystems( DirectThread *thread, void *driver_data ) { SerialMouseData *data = (SerialMouseData*) driver_data; unsigned char buf[256]; unsigned char packet[5]; unsigned char pos = 0; unsigned char last_buttons = 0; int i; int readlen; mouse_motion_initialize( data ); /* Read data */ while ((readlen = read( data->fd, buf, 256 )) >= 0 || errno == EINTR) { direct_thread_testcancel( thread ); for (i = 0; i < readlen; i++) { if (pos == 0 && (buf[i] & 0xf8) != 0x80) continue; packet[pos++] = buf[i]; if (pos == 5) { int dx, dy; int buttons; pos = 0; buttons= (~packet[0]) & 0x07; dx = (signed char) (packet[1]) + (signed char)(packet[3]); dy = - ((signed char) (packet[2]) + (signed char)(packet[4])); mouse_motion_compress( data, dx, dy ); if (!dfb_config->mouse_motion_compression) mouse_motion_realize( data ); if (last_buttons != buttons) { DFBInputEvent evt; unsigned char changed_buttons = last_buttons ^ buttons; /* make sure the compressed motion event is dispatched before any button change */ mouse_motion_realize( data ); if (changed_buttons & 0x04) { evt.type = (buttons & 0x04) ? DIET_BUTTONPRESS : DIET_BUTTONRELEASE; evt.flags = DIEF_NONE; /* button is always valid */ evt.button = DIBI_LEFT; dfb_input_dispatch( data->device, &evt ); } if (changed_buttons & 0x01) { evt.type = (buttons & 0x01) ? DIET_BUTTONPRESS : DIET_BUTTONRELEASE; evt.flags = DIEF_NONE; /* button is always valid */ evt.button = DIBI_MIDDLE; dfb_input_dispatch( data->device, &evt ); } if (changed_buttons & 0x02) { evt.type = (buttons & 0x02) ? DIET_BUTTONPRESS : DIET_BUTTONRELEASE; evt.flags = DIEF_NONE; /* button is always valid */ evt.button = DIBI_RIGHT; dfb_input_dispatch( data->device, &evt ); } last_buttons = buttons; } } } /* make sure the compressed motion event is dispatched, necessary if the last packet was a motion event */ if (readlen > 0) mouse_motion_realize( data ); direct_thread_testcancel( thread ); } D_PERROR ("serial mouse thread died\n"); return NULL; }
/* the main routine for MS mice (plus extensions) */ static void* mouseEventThread_ms( DirectThread *thread, void *driver_data ) { SerialMouseData *data = (SerialMouseData*) driver_data; DFBInputEvent evt; unsigned char buf[256]; unsigned char packet[4]; unsigned char pos = 0; unsigned char last_buttons = 0; int dx, dy; int buttons; int readlen; int i; mouse_motion_initialize( data ); /* Read data */ while ((readlen = read( data->fd, buf, 256 )) >= 0 || errno == EINTR) { direct_thread_testcancel( thread ); for (i = 0; i < readlen; i++) { if (pos == 0 && !(buf[i] & 0x40)) continue; /* We did not reset the position in the mouse event handler since a forth byte may follow. We check for it now and reset the position if this is a start byte. */ if (pos == 3 && buf[i] & 0x40) pos = 0; packet[pos++] = buf[i]; switch (pos) { case 3: if (data->protocol != PROTOCOL_MOUSEMAN) pos = 0; buttons = packet[0] & 0x30; dx = (signed char) (((packet[0] & 0x03) << 6) | (packet[1] & 0x3f)); dy = (signed char) (((packet[0] & 0x0C) << 4) | (packet[2] & 0x3f)); mouse_motion_compress( data, dx, dy ); if (data->protocol == PROTOCOL_MS3) { if (!dx && !dy && buttons == (last_buttons & ~MIDDLE)) buttons = last_buttons ^ MIDDLE; /* toggle */ else buttons |= last_buttons & MIDDLE; /* preserve */ } if (!dfb_config->mouse_motion_compression) mouse_motion_realize( data ); if (last_buttons != buttons) { unsigned char changed_buttons = last_buttons ^ buttons; /* make sure the compressed motion event is dispatched before any button change */ mouse_motion_realize( data ); if (changed_buttons & 0x20) { evt.type = (buttons & 0x20) ? DIET_BUTTONPRESS : DIET_BUTTONRELEASE; evt.flags = DIEF_NONE; evt.button = DIBI_LEFT; dfb_input_dispatch( data->device, &evt ); } if (changed_buttons & 0x10) { evt.type = (buttons & 0x10) ? DIET_BUTTONPRESS : DIET_BUTTONRELEASE; evt.flags = DIEF_NONE; evt.button = DIBI_RIGHT; dfb_input_dispatch( data->device, &evt ); } if (changed_buttons & MIDDLE) { evt.type = (buttons & MIDDLE) ? DIET_BUTTONPRESS : DIET_BUTTONRELEASE; evt.flags = DIEF_NONE; evt.button = DIBI_MIDDLE; dfb_input_dispatch( data->device, &evt ); } last_buttons = buttons; } break; case 4: pos = 0; evt.type = (packet[3] & 0x20) ? DIET_BUTTONPRESS : DIET_BUTTONRELEASE; evt.flags = DIEF_NONE; /* button is always valid */ evt.button = DIBI_MIDDLE; dfb_input_dispatch( data->device, &evt ); break; default: break; } } /* make sure the compressed motion event is dispatched, necessary if the last packet was a motion event */ if (readlen > 0) mouse_motion_realize( data ); direct_thread_testcancel( thread ); } D_PERROR ("serial mouse thread died\n"); return NULL; }
/* * Input thread reading from device. * Generates events on incoming data. */ static void* x11EventThread( DirectThread *thread, void *driver_data ) { X11InputData *data = driver_data; DFBX11 *x11 = data->x11; int x11_fd = ConnectionNumber(x11->display); XExposeEvent expose_event = { 0 }; fd_set in_fds; struct timeval tv; while (!data->stop) { unsigned int pull = 2000; XEvent xEvent; DFBInputEvent dfbEvent; static int nextKeyIsRepeat = false; /* FIXME: Detect key repeats, we're receiving KeyPress, KeyRelease, KeyPress, KeyRelease... !!?? */ if (expose_event.type) { // handle_expose_Async( x11, &expose_event ); expose_event.type = 0; } // Create a File Description Set containing x11_fd FD_ZERO(&in_fds); FD_SET(x11_fd, &in_fds); // Set our timer. tv.tv_sec = 0; tv.tv_usec = 20000; // Wait for X Event or a Timer if (select(x11_fd+1, &in_fds, 0, 0, &tv)) { XLockDisplay( x11->display ); while (!data->stop && pull-- && XPending( x11->display )) { XNextEvent( x11->display, &xEvent ); //D_INFO_LINE_MSG("x11 event %d",xEvent.type); /* is this key repeat? idea from GII */ if ( (xEvent.type == KeyRelease) && (XPending( x11->display )) ) { XEvent peekEvent; XPeekEvent( x11->display, &peekEvent ); if ( (peekEvent.type == KeyPress) && (peekEvent.xkey.keycode == xEvent.xkey.keycode) && (peekEvent.xkey.time - xEvent.xkey.time < 2) ) { nextKeyIsRepeat = true; } } XUnlockDisplay( x11->display ); D_DEBUG_AT( X11_Input, "Event received: %d\n", xEvent.type ); switch (xEvent.type) { case ButtonPress: case ButtonRelease: motion_realize( data ); case MotionNotify: handleMouseEvent( &xEvent, data, x11 ); // crash ??? break; case KeyPress: case KeyRelease: motion_realize( data ); dfbEvent.type = (xEvent.type == KeyPress) ? DIET_KEYPRESS : DIET_KEYRELEASE; dfbEvent.flags = DIEF_KEYCODE | DIEF_TIMESTAMP; dfbEvent.key_code = xEvent.xkey.keycode; dfbEvent.timestamp.tv_sec = xEvent.xkey.time / 1000; dfbEvent.timestamp.tv_usec = (xEvent.xkey.time % 1000) * 1000; if ( (xEvent.type == KeyPress) && nextKeyIsRepeat ) { nextKeyIsRepeat = false; dfbEvent.flags |= DIEF_REPEAT; } dfb_input_dispatch( data->device, &dfbEvent ); break; case Expose: //D_INFO_LINE_MSG("<- expose %d,%d-%dx%d", // xEvent.xexpose.x, xEvent.xexpose.y, xEvent.xexpose.width, xEvent.xexpose.height); if (expose_event.type != 0) { DFBRegion e1 = { expose_event.x, expose_event.y, expose_event.x + expose_event.width - 1, expose_event.y + expose_event.height - 1 }; DFBRegion e2 = { xEvent.xexpose.x, xEvent.xexpose.y, xEvent.xexpose.x + xEvent.xexpose.width - 1, xEvent.xexpose.y + xEvent.xexpose.height - 1 }; dfb_region_region_union( &e1, &e2 ); expose_event.x = e1.x1; expose_event.y = e1.y1; expose_event.width = e1.x2 - e1.x1 + 1; expose_event.height = e1.y2 - e1.y1 + 1; } else expose_event = xEvent.xexpose; //D_INFO_LINE_MSG("-> expose %d,%d-%dx%d", // expose_event.x, expose_event.y, expose_event.width, expose_event.height); break; case DestroyNotify: /* this event is mainly to unblock XNextEvent. */ break; default: break; } XLockDisplay( x11->display ); } XUnlockDisplay( x11->display ); if (!data->stop) motion_realize( data ); } } return NULL; }
static void* ps2mouseEventThread( DirectThread *thread, void *driver_data ) { PS2MouseData *data = (PS2MouseData*) driver_data; unsigned char packet[4]; unsigned char pos = 0; unsigned char last_buttons = 0; int readlen; unsigned char buf[256]; while ( (readlen = read(data->fd, buf, 256)) > 0 ) { int i; direct_thread_testcancel( thread ); for ( i = 0; i < readlen; i++ ) { if ( pos == 0 && (buf[i] & 0xc0) ) { continue; } packet[pos++] = buf[i]; if ( pos == data->packetLength ) { int dx, dy, dz; int buttons; pos = 0; if ( !(packet[0] & 0x08) ) { /* We've lost sync! */ i--; /* does this make sense? oh well, it will resync eventually (will it ?)*/ continue; } buttons = packet[0] & 0x07; dx = (packet[0] & 0x10) ? packet[1]-256 : packet[1]; dy = (packet[0] & 0x20) ? -(packet[2]-256) : -packet[2]; if (data->mouseId == PS2_ID_IMPS2) { /* Just strip off the extra buttons if present and sign extend the 4 bit value */ dz = (s8)((packet[3] & 0x80) ? packet[3] | 0xf0 : packet[3] & 0x0F); if (dz) { DFBInputEvent evt; evt.type = DIET_AXISMOTION; evt.flags = DIEF_AXISREL; evt.axis = DIAI_Z; evt.axisrel = dz; flush_xy( data ); dfb_input_dispatch( data->device, &evt ); } } else { dz = 0; } data->dx += dx; data->dy += dy; if ( !dfb_config->mouse_motion_compression ) flush_xy( data ); if ( last_buttons != buttons ) { DFBInputEvent evt; unsigned char changed_buttons; changed_buttons = last_buttons ^ buttons; /* make sure the compressed motion event is dispatched before any button change */ flush_xy( data ); if ( changed_buttons & 0x01 ) { evt.type = (buttons & 0x01) ? DIET_BUTTONPRESS : DIET_BUTTONRELEASE; evt.flags = DIEF_NONE; evt.button = DIBI_LEFT; dfb_input_dispatch( data->device, &evt ); } if ( changed_buttons & 0x02 ) { evt.type = (buttons & 0x02) ? DIET_BUTTONPRESS : DIET_BUTTONRELEASE; evt.flags = DIEF_NONE; evt.button = DIBI_RIGHT; dfb_input_dispatch( data->device, &evt ); } if ( changed_buttons & 0x04 ) { evt.type = (buttons & 0x04) ? DIET_BUTTONPRESS : DIET_BUTTONRELEASE; evt.flags = DIEF_NONE; evt.button = DIBI_MIDDLE; dfb_input_dispatch( data->device, &evt ); } last_buttons = buttons; } } } /* make sure the compressed motion event is dispatched, necessary if the last packet was a motion event */ flush_xy( data ); } if ( readlen <= 0 && errno != EINTR ) D_PERROR ("psmouse thread died\n"); return NULL; }
static void * h3600tsEventThread( DirectThread *thread, void *driver_data ) { H3600TSData *data = (H3600TSData*) driver_data; TS_EVENT ts_event; int readlen; unsigned short old_x = -1; unsigned short old_y = -1; unsigned short old_pressure = 0; while ((readlen = read(data->fd, &ts_event, sizeof(TS_EVENT))) > 0 || errno == EINTR) { DFBInputEvent evt; direct_thread_testcancel( thread ); if (readlen < 1) continue; if (ts_event.pressure) { if (ts_event.x != old_x) { evt.type = DIET_AXISMOTION; evt.flags = DIEF_AXISABS; evt.axis = DIAI_X; evt.axisabs = ts_event.x; dfb_input_dispatch( data->device, &evt ); old_x = ts_event.x; } if (ts_event.y != old_y) { evt.type = DIET_AXISMOTION; evt.flags = DIEF_AXISABS; evt.axis = DIAI_Y; evt.axisabs = ts_event.y; dfb_input_dispatch( data->device, &evt ); old_y = ts_event.y; } } if ((ts_event.pressure && !old_pressure) || (!ts_event.pressure && old_pressure)) { evt.type = (ts_event.pressure ? DIET_BUTTONPRESS : DIET_BUTTONRELEASE); evt.flags = DIEF_NONE; evt.button = DIBI_LEFT; dfb_input_dispatch( data->device, &evt ); old_pressure = ts_event.pressure; } } if (readlen <= 0) D_PERROR ("H3600 Touchscreen thread died\n"); return NULL; }
/* * Input thread reading from device. * Generates events on incoming data. */ static void* x11EventThread( DirectThread *thread, void *driver_data ) { X11InputData *data = driver_data; DFBX11 *x11 = data->x11; DFBX11Shared *shared = x11->shared; while (!data->stop) { unsigned int pull = 23; XEvent xEvent; DFBInputEvent dfbEvent; static int nextKeyIsRepeat = false; /* FIXME: Detect key repeats, we're receiving KeyPress, KeyRelease, KeyPress, KeyRelease... !!?? */ if (shared->window == 0) { /* no window, so no event */ usleep( 50000 ); continue; } usleep( 10000 ); XLockDisplay( x11->display ); while (!data->stop && pull-- && XPending( x11->display )) { XNextEvent( x11->display, &xEvent ); /* is this key repeat? idea from GII */ if ( (xEvent.type == KeyRelease) && (XPending( x11->display )) ) { XEvent peekEvent; XPeekEvent( x11->display, &peekEvent ); if ( (peekEvent.type == KeyPress) && (peekEvent.xkey.keycode == xEvent.xkey.keycode) && (peekEvent.xkey.time - xEvent.xkey.time < 2) ) { nextKeyIsRepeat = true; } } XUnlockDisplay( x11->display ); D_DEBUG_AT( X11_Input, "Event received: %d\n", xEvent.type ); switch (xEvent.type) { case ButtonPress: case ButtonRelease: motion_realize( data ); case MotionNotify: handleMouseEvent( &xEvent, data ); // crash ??? break; case KeyPress: case KeyRelease: { motion_realize( data ); dfbEvent.type = (xEvent.type == KeyPress) ? DIET_KEYPRESS : DIET_KEYRELEASE; dfbEvent.flags = DIEF_KEYCODE | DIEF_TIMESTAMP; dfbEvent.key_code = xEvent.xkey.keycode; dfbEvent.timestamp.tv_sec = xEvent.xkey.time / 1000; dfbEvent.timestamp.tv_usec = (xEvent.xkey.time % 1000) * 1000; if ( (xEvent.type == KeyPress) && nextKeyIsRepeat ) { nextKeyIsRepeat = false; dfbEvent.flags |= DIEF_REPEAT; } dfb_input_dispatch( data->device, &dfbEvent ); break; } case Expose: //handle_expose( &xEvent.xexpose ); break; case DestroyNotify: /* this event is mainly to unblock XNextEvent. */ break; default: break; } XLockDisplay( x11->display ); } XUnlockDisplay( x11->display ); if (!data->stop) motion_realize( data ); } return NULL; }
static void handleMouseEvent(XEvent* pXEvent, X11InputData* pData) { static int iMouseEventCount = 0; DFBInputEvent dfbEvent; if (pXEvent->type == MotionNotify) { motion_compress( pXEvent->xmotion.x, pXEvent->xmotion.y, pXEvent ); ++iMouseEventCount; } if ( pXEvent->type == ButtonPress || pXEvent->type == ButtonRelease ) { if ( pXEvent->type == ButtonPress ) dfbEvent.type = DIET_BUTTONPRESS; else dfbEvent.type = DIET_BUTTONRELEASE; dfbEvent.flags = DIEF_TIMESTAMP; /* Get pressed button */ switch ( pXEvent->xbutton.button ) { case 1: dfbEvent.button = DIBI_LEFT; break; case 2: dfbEvent.button = DIBI_MIDDLE; break; case 3: dfbEvent.button = DIBI_RIGHT; break; //Wheel events case 4: /*up*/ case 5: /*down*/ case 6: /*left*/ case 7: /*right*/ if (pXEvent->type == ButtonPress) { dfbEvent.type = DIET_AXISMOTION; dfbEvent.flags = DIEF_AXISREL; dfbEvent.axis = DIAI_Z; /*SCROLL UP*/ if ( pXEvent->xbutton.button == 4 ) { dfbEvent.axisrel = -1; } /*SCROLL DOWN */ else if (pXEvent->xbutton.button == 5) { dfbEvent.axisrel = 1; } /*SCROLL LEFT*/ else if (pXEvent->xbutton.button == 6) { dfbEvent.axis = DIAI_X; dfbEvent.axisrel = -1; } /*SCROLL RIGHT*/ else if (pXEvent->xbutton.button == 7 ) { dfbEvent.axis = DIAI_X; dfbEvent.axisrel = 1; } } else return; break; default: break; } dfbEvent.timestamp.tv_sec = pXEvent->xbutton.time / 1000; dfbEvent.timestamp.tv_usec = (pXEvent->xbutton.time % 1000) * 1000; dfb_input_dispatch( pData->device, &dfbEvent ); ++iMouseEventCount; } }