uint32_t EventHandler::_getButtonState( XEvent& event ) { const int xState = event.xbutton.state; uint32_t state = 0; if( xState & Button1Mask ) state |= PTR_BUTTON1; if( xState & Button2Mask ) state |= PTR_BUTTON2; if( xState & Button3Mask ) state |= PTR_BUTTON3; if( xState & Button4Mask ) state |= PTR_BUTTON4; if( xState & Button5Mask ) state |= PTR_BUTTON5; switch( event.type ) { // state is state before event case ButtonPress: state |= _getButtonAction( event ); break; case ButtonRelease: state &= ~_getButtonAction( event ); break; default: break; } return state; }
void GLXEventHandler::_processEvent( GLXWindowEvent& event ) { EQ_TS_THREAD( _thread ); XEvent& xEvent = event.xEvent; XID drawable = xEvent.xany.window; if( _window->getXDrawable() != drawable ) return; Window* window = _window->getWindow(); switch( xEvent.type ) { case Expose: if( xEvent.xexpose.count ) // Only report last expose event return; event.type = Event::WINDOW_EXPOSE; break; case ConfigureNotify: event.type = Event::WINDOW_RESIZE; _getWindowSize( xEvent.xany.display, drawable, event.resize ); break; case UnmapNotify: event.type = Event::WINDOW_HIDE; _getWindowSize( xEvent.xany.display, drawable, event.resize ); break; case MapNotify: event.type = Event::WINDOW_SHOW; _getWindowSize( xEvent.xany.display, drawable, event.resize ); break; case ClientMessage: { Atom deleteAtom = XInternAtom( xEvent.xany.display, "WM_DELETE_WINDOW", False ); if( static_cast<Atom>( xEvent.xclient.data.l[0] ) != deleteAtom ) return; // not a delete message, ignore. } // else: delete message, fall through case DestroyNotify: event.type = Event::WINDOW_CLOSE; break; case MotionNotify: event.type = Event::WINDOW_POINTER_MOTION; event.pointerMotion.x = xEvent.xmotion.x; event.pointerMotion.y = xEvent.xmotion.y; event.pointerMotion.buttons = _getButtonState( xEvent ); event.pointerMotion.button = PTR_BUTTON_NONE; _computePointerDelta( window, event ); _getRenderContext( window, event ); break; case ButtonPress: event.type = Event::WINDOW_POINTER_BUTTON_PRESS; event.pointerButtonPress.x = xEvent.xbutton.x; event.pointerButtonPress.y = xEvent.xbutton.y; event.pointerButtonPress.buttons = _getButtonState( xEvent ); event.pointerButtonPress.button = _getButtonAction( xEvent ); // Translate wheel events switch( event.pointerButtonPress.button ) { case PTR_BUTTON4: event.pointerWheel.xAxis = 1; break; case PTR_BUTTON5: event.pointerWheel.xAxis = -1; break; case PTR_BUTTON6: event.pointerWheel.yAxis = 1; break; case PTR_BUTTON7: event.pointerWheel.yAxis = -1; break; } switch( event.pointerButtonPress.button ) { case PTR_BUTTON4: case PTR_BUTTON5: case PTR_BUTTON6: case PTR_BUTTON7: event.type = Event::WINDOW_POINTER_WHEEL; event.pointerWheel.button = PTR_BUTTON_NONE; } _computePointerDelta( window, event ); _getRenderContext( window, event ); break; case ButtonRelease: event.type = Event::WINDOW_POINTER_BUTTON_RELEASE; event.pointerButtonRelease.x = xEvent.xbutton.x; event.pointerButtonRelease.y = xEvent.xbutton.y; event.pointerButtonRelease.buttons = _getButtonState( xEvent ); event.pointerButtonRelease.button = _getButtonAction( xEvent); _computePointerDelta( window, event ); _getRenderContext( window, event ); break; case KeyPress: event.type = Event::KEY_PRESS; event.keyPress.key = _getKey( xEvent ); break; case KeyRelease: event.type = Event::KEY_RELEASE; event.keyPress.key = _getKey( xEvent ); break; case ReparentNotify: case VisibilityNotify: event.type = Event::UNKNOWN; EQINFO << "Ignored X event, type " << xEvent.type << std::endl; break; default: event.type = Event::UNKNOWN; EQWARN << "Unhandled X event, type " << xEvent.type << std::endl; break; } event.originator = window->getID(); event.serial = window->getSerial(); _window->processEvent( event ); }
void EventHandler::_processEvent( WindowEvent& event ) { LB_TS_THREAD( _thread ); XEvent& xEvent = event.xEvent; XID drawable = xEvent.xany.window; if( _window->getXDrawable() != drawable ) return; switch( xEvent.type ) { case Expose: if( xEvent.xexpose.count ) // Only report last expose event return; event.type = Event::WINDOW_EXPOSE; break; case ConfigureNotify: event.type = Event::WINDOW_RESIZE; _getWindowSize( xEvent.xany.display, drawable, event.resize ); break; case UnmapNotify: event.type = Event::WINDOW_HIDE; _getWindowSize( xEvent.xany.display, drawable, event.resize ); break; case MapNotify: event.type = Event::WINDOW_SHOW; _getWindowSize( xEvent.xany.display, drawable, event.resize ); break; case ClientMessage: { #ifdef EQUALIZER_USE_MAGELLAN_GLX spnav_event spev; /* spacenav event */ if( spnav_x11_event( &xEvent, &spev )) { switch( spev.type ) { case SPNAV_EVENT_MOTION: event.type = Event::MAGELLAN_AXIS; event.magellan.xAxis = spev.motion.x; event.magellan.yAxis = spev.motion.y; event.magellan.zAxis = -spev.motion.z; event.magellan.xRotation = -spev.motion.rx; event.magellan.yRotation = -spev.motion.ry; event.magellan.zRotation = spev.motion.rz; break; case SPNAV_EVENT_BUTTON: event.type = Event::MAGELLAN_BUTTON; event.magellan.buttons = spev.button.press; event.magellan.button = spev.button.bnum; break; default: LBUNIMPLEMENTED; return; } /* remove any other queued motion events */ //? spnav_remove_events( SPNAV_EVENT_MOTION ); break; } #endif Atom deleteAtom = XInternAtom( xEvent.xany.display, "WM_DELETE_WINDOW", False ); if( static_cast<Atom>( xEvent.xclient.data.l[0] ) != deleteAtom ) return; // not a delete message, ignore. } // else: delete message, fall through case DestroyNotify: event.type = Event::WINDOW_CLOSE; break; case MotionNotify: event.type = Event::WINDOW_POINTER_MOTION; event.pointerMotion.x = xEvent.xmotion.x; event.pointerMotion.y = xEvent.xmotion.y; event.pointerMotion.buttons = _getButtonState( xEvent ); event.pointerMotion.button = PTR_BUTTON_NONE; _computePointerDelta( event ); break; case ButtonPress: event.type = Event::WINDOW_POINTER_BUTTON_PRESS; event.pointerButtonPress.x = xEvent.xbutton.x; event.pointerButtonPress.y = xEvent.xbutton.y; event.pointerButtonPress.buttons = _getButtonState( xEvent ); event.pointerButtonPress.button = _getButtonAction( xEvent ); // Translate wheel events switch( event.pointerButtonPress.button ) { case PTR_BUTTON4: event.pointerWheel.yAxis = 1; break; case PTR_BUTTON5: event.pointerWheel.yAxis = -1; break; case PTR_BUTTON6: event.pointerWheel.xAxis = 1; break; case PTR_BUTTON7: event.pointerWheel.xAxis = -1; break; } switch( event.pointerButtonPress.button ) { case PTR_BUTTON4: case PTR_BUTTON5: case PTR_BUTTON6: case PTR_BUTTON7: event.type = Event::WINDOW_POINTER_WHEEL; event.pointerWheel.button = PTR_BUTTON_NONE; } _computePointerDelta( event ); break; case ButtonRelease: event.type = Event::WINDOW_POINTER_BUTTON_RELEASE; event.pointerButtonRelease.x = xEvent.xbutton.x; event.pointerButtonRelease.y = xEvent.xbutton.y; event.pointerButtonRelease.buttons = _getButtonState( xEvent ); event.pointerButtonRelease.button = _getButtonAction( xEvent); _computePointerDelta( event ); break; case KeyPress: event.type = Event::KEY_PRESS; event.keyPress.key = _getKey( xEvent ); break; case KeyRelease: event.type = Event::KEY_RELEASE; event.keyPress.key = _getKey( xEvent ); break; case ReparentNotify: case VisibilityNotify: event.type = Event::UNKNOWN; LBVERB << "Ignored X event, type " << xEvent.type << std::endl; break; default: event.type = Event::UNKNOWN; LBWARN << "Unhandled X event, type " << xEvent.type << std::endl; break; } _window->processEvent( event ); }
bool EventHandler::_processEvent( const XEvent& event ) { LB_TS_THREAD( _thread ); XID drawable = event.xany.window; if( _window->getXDrawable() != drawable ) return false; switch( event.type ) { case Expose: if( event.xexpose.count ) // Only report last expose event return true; return _window->processEvent( EVENT_WINDOW_EXPOSE, event ); case ConfigureNotify: { SizeEvent sizeEvent; _getWindowSize( event.xany.display, drawable, sizeEvent ); return _window->processEvent( EVENT_WINDOW_RESIZE, event, sizeEvent ); } case UnmapNotify: { SizeEvent sizeEvent; _getWindowSize( event.xany.display, drawable, sizeEvent ); return _window->processEvent( EVENT_WINDOW_HIDE, event, sizeEvent ); } case MapNotify: { SizeEvent sizeEvent; _getWindowSize( event.xany.display, drawable, sizeEvent ); return _window->processEvent( EVENT_WINDOW_SHOW, event, sizeEvent ); } case ClientMessage: { #ifdef EQUALIZER_USE_MAGELLAN_GLX spnav_event spev; if( spnav_x11_event( &event, &spev )) // spacenav event { switch( spev.type ) { case SPNAV_EVENT_MOTION: { AxisEvent axisEvent; axisEvent.xAxis = spev.motion.x; axisEvent.yAxis = spev.motion.y; axisEvent.zAxis = -spev.motion.z; axisEvent.xRotation = -spev.motion.rx; axisEvent.yRotation = -spev.motion.ry; axisEvent.zRotation = spev.motion.rz; return _window->processEvent( event, axisEvent ); } case SPNAV_EVENT_BUTTON: { ButtonEvent buttonEvent; buttonEvent.buttons = spev.button.press; buttonEvent.button = spev.button.bnum; return _window->processEvent( event, buttonEvent ); } default: LBUNIMPLEMENTED; return false; } break; } #endif Atom deleteAtom = XInternAtom( event.xany.display, "WM_DELETE_WINDOW", False ); if( static_cast<Atom>( event.xclient.data.l[0] ) != deleteAtom ) return false; // not a delete message, ignore. } // else: delete message, fall through case DestroyNotify: return _window->processEvent( EVENT_WINDOW_CLOSE, event ); case MotionNotify: { PointerEvent pointerEvent; pointerEvent.x = event.xmotion.x; pointerEvent.y = event.xmotion.y; pointerEvent.buttons = _getButtonState( event ); pointerEvent.button = PTR_BUTTON_NONE; pointerEvent.modifiers = _getKeyModifiers( event.xbutton.state ); _computePointerDelta( EVENT_WINDOW_POINTER_MOTION, pointerEvent ); return _window->processEvent( EVENT_WINDOW_POINTER_MOTION, event, pointerEvent ); } case ButtonPress: { PointerEvent pointerEvent; pointerEvent.x = event.xbutton.x; pointerEvent.y = event.xbutton.y; pointerEvent.buttons = _getButtonState( event ); pointerEvent.button = _getButtonAction( event ); pointerEvent.modifiers = _getKeyModifiers( event.xbutton.state ); switch( pointerEvent.button ) // Translate wheel events { case PTR_BUTTON4: pointerEvent.yAxis = 1; break; case PTR_BUTTON5: pointerEvent.yAxis = -1; break; case PTR_BUTTON6: pointerEvent.xAxis = 1; break; case PTR_BUTTON7: pointerEvent.xAxis = -1; break; } switch( pointerEvent.button ) { case PTR_BUTTON4: case PTR_BUTTON5: case PTR_BUTTON6: case PTR_BUTTON7: pointerEvent.button = PTR_BUTTON_NONE; _computePointerDelta( EVENT_WINDOW_POINTER_WHEEL, pointerEvent ); return _window->processEvent( EVENT_WINDOW_POINTER_WHEEL, event, pointerEvent ); } _computePointerDelta( EVENT_WINDOW_POINTER_BUTTON_PRESS, pointerEvent ); return _window->processEvent( EVENT_WINDOW_POINTER_BUTTON_PRESS, event, pointerEvent ); } case ButtonRelease: { PointerEvent pointerEvent; pointerEvent.x = event.xbutton.x; pointerEvent.y = event.xbutton.y; pointerEvent.buttons = _getButtonState( event ); pointerEvent.button = _getButtonAction( event); pointerEvent.modifiers = _getKeyModifiers( event.xbutton.state ); _computePointerDelta( EVENT_WINDOW_POINTER_BUTTON_RELEASE, pointerEvent ); return _window->processEvent( EVENT_WINDOW_POINTER_BUTTON_RELEASE, event, pointerEvent ); } case KeyPress: { KeyEvent keyEvent; keyEvent.key = _getKey( event ); keyEvent.modifiers = _getKeyModifiers( event.xkey.state ); return _window->processEvent( EVENT_KEY_PRESS, event, keyEvent ); } case KeyRelease: { KeyEvent keyEvent; keyEvent.key = _getKey( event ); keyEvent.modifiers = _getKeyModifiers( event.xkey.state ); return _window->processEvent( EVENT_KEY_RELEASE, event, keyEvent ); } default: LBWARN << "Unhandled X event, type " << event.type << std::endl; // no break; case ReparentNotify: case VisibilityNotify: return _window->processEvent( EVENT_UNKNOWN, event ); } }