static void handle_events() { int screen_domain = screen_get_domain(); int navigator_domain = navigator_get_domain(); int sensor_domain = sensor_get_domain(); int rc; //Request and process available BPS events for(;;) { bps_event_t *event = NULL; rc = bps_get_event(&event, 0); assert(rc == BPS_SUCCESS); if (event) { int domain = bps_event_get_domain(event); if (domain == screen_domain) { handleScreenEvent(event); } else if (domain == navigator_domain) { handleNavigatorEvent(event); } else if (domain == sensor_domain) { handleSensorEvent(event); } } else { //No more events in the queue break; } } }
void* eventLoop(void* data) { FREContext ctx = (FREContext) data; float x, y, z; bps_event_t *event = NULL; char buffer[256]; // Initialize BPS bps_initialize(); // Start the gyroscope if (sensor_request_events(SENSOR_TYPE_GYROSCOPE) != BPS_SUCCESS) { shutdown = true; } // Receive events through the event channel while (!shutdown) { event = NULL; if (bps_get_event(&event, 50) != BPS_SUCCESS) return NULL; if (event) { if (bps_event_get_domain(event) == sensor_get_domain()) { if (bps_event_get_code(event) == SENSOR_GYROSCOPE_READING) { if (sensor_event_get_xyz(event, &x, &y, &z) == BPS_SUCCESS) { sprintf(buffer, "%f&%f&%f", x, y, z); fprintf(stdout, "Sensor event: %f&%f&%f\n", x, y, z); fflush(stdout); if(ctx != NULL) { FREDispatchStatusEventAsync(ctx, (uint8_t*)"CHANGE", (uint8_t*)buffer); } } } } } } if (sensor_stop_events(SENSOR_TYPE_GYROSCOPE) != BPS_SUCCESS) { fprintf(stdout, "Unable to stop sensor\n"); fflush(stdout); } // Stop BPS bps_shutdown(); return NULL; }
/** * Thread that handles accelerometer events and * sends relevant information to a dialog. * * @param p Unused. */ static void * accel_main (void *p) { bool run = true; bps_event_t *event; float force_x, force_y, force_z; bps_initialize(); /* * Each thread that calls bps_initialize() will have its * own unique channel ID. Protect it inside a mutex and * condition variable to avoid race condition where main * thread tries to use it before we assign it. */ pthread_mutex_lock(&chidMutex); accel_chid = bps_channel_get_active(); pthread_cond_signal(&chidCond); pthread_mutex_unlock(&chidMutex); /* * Create and display a dialog that will show the data. */ create_bottom_dialog(); show_bottom_dialog_message("\n\nThis is the Accelerometer Dialog"); if (BPS_SUCCESS != sensor_request_events(SENSOR_TYPE_ACCELEROMETER)) { fprintf(stderr, "Error requesting sensor's accelerometer events: %s", strerror(errno)); bps_shutdown(); return NULL; } sensor_set_rate(SENSOR_TYPE_ACCELEROMETER, ACCELEROMETER_RATE); sensor_set_skip_duplicates(SENSOR_TYPE_ACCELEROMETER, true); while (run) { /* * Block, at the very least we'll get the "STOP" event */ bps_get_event(&event, -1); if (bps_event_get_domain(event) == local_event_domain) { if (bps_event_get_code(event) == STOP_REQUEST) { run = false; } } if (bps_event_get_domain(event) == sensor_get_domain()) { if (SENSOR_ACCELEROMETER_READING == bps_event_get_code(event)) { sensor_event_get_xyz(event, &force_x, &force_y, &force_z); display_accelerometer_reading(force_x, force_y, force_z); } } } sensor_stop_events(0); destroy_bottom_dialog(); bps_shutdown(); fprintf(stderr, "Exiting accelerometer thread\n"); return NULL; }
void BlackberryMain::runMain() { bool running = true; while (running && !g_quitRequested) { input_state.mouse_valid = false; input_state.accelerometer_valid = false; while (true) { // Handle Blackberry events bps_event_t *event = NULL; bps_get_event(&event, 0); if (event == NULL) break; // Ran out of events int domain = bps_event_get_domain(event); if (domain == screen_get_domain()) { handleInput(screen_event_get_event(event)); } else if (domain == navigator_get_domain()) { switch(bps_event_get_code(event)) { case NAVIGATOR_INVOKE_TARGET: { const navigator_invoke_invocation_t *invoke = navigator_invoke_event_get_invocation(event); if(invoke) { boot_filename = navigator_invoke_invocation_get_uri(invoke)+7; // Remove file:// } } break; case NAVIGATOR_ORIENTATION: sensor_remap_coordinates(navigator_event_get_orientation_angle(event)); break; case NAVIGATOR_BACK: case NAVIGATOR_SWIPE_DOWN: NativeKey(KeyInput(DEVICE_ID_KEYBOARD, NKCODE_ESCAPE, KEY_DOWN)); break; case NAVIGATOR_EXIT: return; } } else if (domain == sensor_get_domain()) { if (SENSOR_ACCELEROMETER_READING == bps_event_get_code(event)) { sensor_event_get_xyz(event, &(input_state.acc.y), &(input_state.acc.x), &(input_state.acc.z)); AxisInput axis; axis.deviceId = DEVICE_ID_ACCELEROMETER; axis.flags = 0; axis.axisId = JOYSTICK_AXIS_ACCELEROMETER_X; axis.value = input_state.acc.x; NativeAxis(axis); axis.axisId = JOYSTICK_AXIS_ACCELEROMETER_Y; axis.value = input_state.acc.y; NativeAxis(axis); axis.axisId = JOYSTICK_AXIS_ACCELEROMETER_Z; axis.value = input_state.acc.z; NativeAxis(axis); } } } UpdateInputState(&input_state); NativeUpdate(input_state); // Work in Progress // Currently: Render to HDMI port (eg. 1080p) when in game. Render to device when in menu. // Idea: Render to all displays. Controls go to internal, game goes to external(s). if (GetUIState() == UISTATE_INGAME && !emulating) { emulating = true; switchDisplay(screen_emu); if (g_Config.iShowFPSCounter == 4) { int options = SCREEN_DEBUG_STATISTICS; screen_set_window_property_iv(screen_win[0], SCREEN_PROPERTY_DEBUG, &options); } } else if (GetUIState() != UISTATE_INGAME && emulating) { emulating = false; switchDisplay(screen_ui); } NativeRender(); EndInputState(&input_state); time_update(); // This handles VSync if (emulating) eglSwapBuffers(egl_disp[screen_emu], egl_surf[screen_emu]); else eglSwapBuffers(egl_disp[screen_ui], egl_surf[screen_ui]); } }
bool CCEGLView::handleEvents() { bps_event_t* event = NULL; mtouch_event_t mtouch_event; int touch_id = 0; int val = 0; int rc = 0; int domain = 0; char buf[4] = {0}; for (;;) { rc = bps_get_event(&event, 1); assert(rc == BPS_SUCCESS); // break if no more events if (event == NULL) break; domain = bps_event_get_domain(event); if (domain == navigator_get_domain()) { switch (bps_event_get_code(event)) { case NAVIGATOR_SWIPE_DOWN: CCDirector::sharedDirector()->getKeypadDispatcher()->dispatchKeypadMSG(kTypeMenuClicked); break; case NAVIGATOR_EXIT: // exit the application // release(); end(); break; case NAVIGATOR_WINDOW_INACTIVE: if (m_isWindowActive) { CCApplication::sharedApplication()->applicationDidEnterBackground(); m_isWindowActive = false; } break; case NAVIGATOR_WINDOW_ACTIVE: if (!m_isWindowActive) { CCApplication::sharedApplication()->applicationWillEnterForeground(); m_isWindowActive = true; } break; case NAVIGATOR_WINDOW_STATE: { switch(navigator_event_get_window_state(event)) { case NAVIGATOR_WINDOW_FULLSCREEN: if (!m_isWindowActive) { CCApplication::sharedApplication()->applicationWillEnterForeground(); m_isWindowActive = true; } break; case NAVIGATOR_WINDOW_THUMBNAIL: if (m_isWindowActive) { CCApplication::sharedApplication()->applicationDidEnterBackground(); m_isWindowActive = false; } break; } break; } default: break; } } else if (domain == screen_get_domain()) { m_screenEvent = screen_event_get_event(event); rc = screen_get_event_property_iv(m_screenEvent, SCREEN_PROPERTY_TYPE, &val); if (rc || val == SCREEN_EVENT_NONE) break; float x, y; switch (val) { case SCREEN_EVENT_CLOSE: fprintf(stderr, "SCREEN CLOSE EVENT!\n"); break; case SCREEN_EVENT_MTOUCH_RELEASE: screen_get_mtouch_event(m_screenEvent, &mtouch_event, 0); touch_id = mtouch_event.contact_id; x = mtouch_event.x; y = mtouch_event.y; handleTouchesEnd(1, &touch_id, &x, &y); break; case SCREEN_EVENT_MTOUCH_TOUCH: screen_get_mtouch_event(m_screenEvent, &mtouch_event, 0); touch_id = mtouch_event.contact_id; x = mtouch_event.x; y = mtouch_event.y; handleTouchesBegin(1, &touch_id, &x, &y); break; case SCREEN_EVENT_MTOUCH_MOVE: screen_get_mtouch_event(m_screenEvent, &mtouch_event, 0); touch_id = mtouch_event.contact_id; x = mtouch_event.x; y = mtouch_event.y; handleTouchesMove(1, &touch_id, &x, &y); break; case SCREEN_EVENT_POINTER: { int buttons = 0; int pair_[2] = {0}; float pair[2] = {0.0f}; static bool mouse_pressed = false; // this is a mouse move event, it is applicable to a device with a usb mouse or simulator screen_get_event_property_iv(m_screenEvent, SCREEN_PROPERTY_BUTTONS, &buttons); screen_get_event_property_iv(m_screenEvent, SCREEN_PROPERTY_SOURCE_POSITION, pair_); pair[0] = (float)pair_[0]; pair[1] = (float)pair_[1]; if (buttons & SCREEN_LEFT_MOUSE_BUTTON) { if (mouse_pressed) { handleTouchesMove(1, &touch_id, &pair[0], &pair[1]); } else { // Left mouse button is pressed mouse_pressed = true; handleTouchesBegin(1, &touch_id, &pair[0], &pair[1]); } } else { if (mouse_pressed) { mouse_pressed = false; handleTouchesEnd(1, &touch_id, &pair[0], &pair[1]); } } } break; case SCREEN_EVENT_KEYBOARD: screen_get_event_property_iv(m_screenEvent, SCREEN_PROPERTY_KEY_FLAGS, &val); if (val & KEY_DOWN) { screen_get_event_property_iv(m_screenEvent, SCREEN_PROPERTY_KEY_SYM, &val); if (val >= ' ' && val < '~') { buf[0] = val; buf[1]= '\0'; CCIMEDispatcher::sharedDispatcher()->dispatchInsertText(buf, 1); } else { val = val - 0xf000; buf[0] = val; buf[1]= '\0'; switch (val) { case 8: // backspace // CCKeypadDispatcher::sharedDispatcher()->dispatchKeypadMSG(kTypeBackClicked); CCIMEDispatcher::sharedDispatcher()->dispatchDeleteBackward(); break; default: CCIMEDispatcher::sharedDispatcher()->dispatchInsertText(buf, 1); break; } } } break; default: break; } } else if (domain == sensor_get_domain()) { if (bps_event_get_code(event) == SENSOR_ACCELEROMETER_READING) { struct timespec time_struct; long current_time; float x, y, z; clock_gettime(CLOCK_REALTIME, &time_struct); current_time = time2millis(&time_struct); sensor_event_get_xyz(event, &x, &y, &z); CCDirector::sharedDirector()->getAccelerometer()->update(current_time, -x, -y, z); } } } return true; }
int Platform::enterMessagePump() { GP_ASSERT(_game); int rc; int eventType; int flags; int value; int position[2]; int domain; mtouch_event_t touchEvent; bool suspended = false; // Get the initial time. clock_gettime(CLOCK_REALTIME, &__timespec); __timeStart = timespec2millis(&__timespec); __timeAbsolute = 0L; _game->run(); // Message loop. while (true) { bps_event_t* event = NULL; while (true) { rc = bps_get_event(&event, 1); GP_ASSERT(rc == BPS_SUCCESS); if (event == NULL) break; domain = bps_event_get_domain(event); if (domain == screen_get_domain()) { __screenEvent = screen_event_get_event(event); screen_get_event_property_iv(__screenEvent, SCREEN_PROPERTY_TYPE, &eventType); switch (eventType) { case SCREEN_EVENT_MTOUCH_TOUCH: { screen_get_mtouch_event(__screenEvent, &touchEvent, 0); if (__gestureEventsProcessed.any()) rc = gestures_set_process_event(__gestureSet, &touchEvent, NULL); if ( !rc && (__multiTouch || touchEvent.contact_id == 0) ) { gameplay::Platform::touchEventInternal(Touch::TOUCH_PRESS, touchEvent.x, touchEvent.y, touchEvent.contact_id); } break; } case SCREEN_EVENT_MTOUCH_RELEASE: { screen_get_mtouch_event(__screenEvent, &touchEvent, 0); if (__gestureEventsProcessed.any()) rc = gestures_set_process_event(__gestureSet, &touchEvent, NULL); if ( !rc && (__multiTouch || touchEvent.contact_id == 0) ) { gameplay::Platform::touchEventInternal(Touch::TOUCH_RELEASE, touchEvent.x, touchEvent.y, touchEvent.contact_id); } if (__gestureSwipeRecognized) { __gestureSwipeRecognized = false; } break; } case SCREEN_EVENT_MTOUCH_MOVE: { screen_get_mtouch_event(__screenEvent, &touchEvent, 0); if (__gestureEventsProcessed.any()) rc = gestures_set_process_event(__gestureSet, &touchEvent, NULL); if ( !rc && (__multiTouch || touchEvent.contact_id == 0) ) { gameplay::Platform::touchEventInternal(Touch::TOUCH_MOVE, touchEvent.x, touchEvent.y, touchEvent.contact_id); } break; } case SCREEN_EVENT_POINTER: { static int mouse_pressed = 0; int buttons; int wheel; // A move event will be fired unless a button state changed. bool move = true; bool left_move = false; // This is a mouse move event, it is applicable to a device with a usb mouse or simulator. screen_get_event_property_iv(__screenEvent, SCREEN_PROPERTY_BUTTONS, &buttons); screen_get_event_property_iv(__screenEvent, SCREEN_PROPERTY_SOURCE_POSITION, position); screen_get_event_property_iv(__screenEvent, SCREEN_PROPERTY_MOUSE_WHEEL, &wheel); // Handle left mouse. Interpret as touch if the left mouse event is not consumed. if (buttons & SCREEN_LEFT_MOUSE_BUTTON) { if (mouse_pressed & SCREEN_LEFT_MOUSE_BUTTON) { left_move = true; } else { move = false; mouse_pressed |= SCREEN_LEFT_MOUSE_BUTTON; mouseOrTouchEvent(Mouse::MOUSE_PRESS_LEFT_BUTTON, Touch::TOUCH_PRESS, position[0], position[1]); } } else if (mouse_pressed & SCREEN_LEFT_MOUSE_BUTTON) { move = false; mouse_pressed &= ~SCREEN_LEFT_MOUSE_BUTTON; mouseOrTouchEvent(Mouse::MOUSE_RELEASE_LEFT_BUTTON, Touch::TOUCH_RELEASE, position[0], position[1]); } // Handle right mouse. if (buttons & SCREEN_RIGHT_MOUSE_BUTTON) { if ((mouse_pressed & SCREEN_RIGHT_MOUSE_BUTTON) == 0) { move = false; mouse_pressed |= SCREEN_RIGHT_MOUSE_BUTTON; gameplay::Platform::mouseEventInternal(Mouse::MOUSE_PRESS_RIGHT_BUTTON, position[0], position[1], 0); } } else if (mouse_pressed & SCREEN_RIGHT_MOUSE_BUTTON) { move = false; mouse_pressed &= ~SCREEN_RIGHT_MOUSE_BUTTON; gameplay::Platform::mouseEventInternal(Mouse::MOUSE_RELEASE_RIGHT_BUTTON, position[0], position[1], 0); } // Handle middle mouse. if (buttons & SCREEN_MIDDLE_MOUSE_BUTTON) { if ((mouse_pressed & SCREEN_MIDDLE_MOUSE_BUTTON) == 0) { move = false; mouse_pressed |= SCREEN_MIDDLE_MOUSE_BUTTON; gameplay::Platform::mouseEventInternal(Mouse::MOUSE_PRESS_MIDDLE_BUTTON, position[0], position[1], 0); } } else if (mouse_pressed & SCREEN_MIDDLE_MOUSE_BUTTON) { move = false; mouse_pressed &= ~SCREEN_MIDDLE_MOUSE_BUTTON; gameplay::Platform::mouseEventInternal(Mouse::MOUSE_RELEASE_MIDDLE_BUTTON, position[0], position[1], 0); } // Fire a move event if none of the buttons changed. if (left_move) { mouseOrTouchEvent(Mouse::MOUSE_MOVE, Touch::TOUCH_MOVE, position[0], position[1]); } else if (move) { gameplay::Platform::mouseEventInternal(Mouse::MOUSE_MOVE, position[0], position[1], 0); } // Handle mouse wheel events. if (wheel) { gameplay::Platform::mouseEventInternal(Mouse::MOUSE_WHEEL, position[0], position[1], -wheel); } break; } case SCREEN_EVENT_KEYBOARD: { screen_get_event_property_iv(__screenEvent, SCREEN_PROPERTY_KEY_FLAGS, &flags); screen_get_event_property_iv(__screenEvent, SCREEN_PROPERTY_KEY_SYM, &value); gameplay::Keyboard::KeyEvent evt = (flags & KEY_DOWN) ? gameplay::Keyboard::KEY_PRESS : gameplay::Keyboard::KEY_RELEASE; // Suppress key repeats. if ((flags & KEY_REPEAT) == 0) { keyEventInternal(evt, getKey(value)); if (evt == gameplay::Keyboard::KEY_PRESS && (flags & KEY_SYM_VALID)) { int unicode = getUnicode(value); if (unicode) keyEventInternal(gameplay::Keyboard::KEY_CHAR, unicode); } } break; } } } else if (domain == navigator_get_domain()) { switch (bps_event_get_code(event)) { case NAVIGATOR_SWIPE_DOWN: _game->menuEvent(); break; case NAVIGATOR_WINDOW_STATE: { navigator_window_state_t state = navigator_event_get_window_state(event); switch (state) { case NAVIGATOR_WINDOW_FULLSCREEN: _game->resume(); suspended = false; break; case NAVIGATOR_WINDOW_THUMBNAIL: case NAVIGATOR_WINDOW_INVISIBLE: if (!suspended) _game->pause(); suspended = true; break; } break; } case NAVIGATOR_EXIT: _game->exit(); break; } } else if (domain == sensor_get_domain()) { if (bps_event_get_code(event) == SENSOR_AZIMUTH_PITCH_ROLL_READING) { float azimuth; sensor_event_get_apr(event, &azimuth, &__pitch, &__roll); } } } // If we are done, then exit. if (_game->getState() == Game::UNINITIALIZED) break; if (!suspended) { _game->frame(); // Post the new frame to the display. // Note that there are a couple cases where eglSwapBuffers could fail // with an error code that requires a certain level of re-initialization: // // 1) EGL_BAD_NATIVE_WINDOW - Called when the surface we're currently using // is invalidated. This would require us to destroy our EGL surface, // close our OpenKODE window, and start again. // // 2) EGL_CONTEXT_LOST - Power management event that led to our EGL context // being lost. Requires us to re-create and re-initalize our EGL context // and all OpenGL ES state. // // For now, if we get these, we'll simply exit. rc = eglSwapBuffers(__eglDisplay, __eglSurface); if (rc != EGL_TRUE) { _game->exit(); perror("eglSwapBuffers"); break; } } } screen_stop_events(__screenContext); bps_shutdown(); screen_destroy_context(__screenContext); return 0; }