From 66f90a40c93c97ede730da880cfb86ffaf06d2b0 Mon Sep 17 00:00:00 2001 From: Fabio Battaglia Date: Thu, 21 Jan 2010 18:31:46 +0000 Subject: N64: change input related code to better fit mouse support svn-id: r47420 --- backends/platform/n64/osys_n64.h | 7 +- backends/platform/n64/osys_n64_base.cpp | 8 +-- backends/platform/n64/osys_n64_events.cpp | 99 ++++++++++++++++++---------- backends/platform/n64/osys_n64_utilities.cpp | 2 + 4 files changed, 74 insertions(+), 42 deletions(-) diff --git a/backends/platform/n64/osys_n64.h b/backends/platform/n64/osys_n64.h index 51a11a5401..4bce59a93a 100644 --- a/backends/platform/n64/osys_n64.h +++ b/backends/platform/n64/osys_n64.h @@ -112,11 +112,11 @@ protected: bool _overlayVisible; bool _mouseVisible; - int _mouseX, _mouseY; - int _mouseMaxX, _mouseMaxY; + volatile int _mouseX, _mouseY; + volatile int _tempMouseX, _tempMouseY; + volatile int _mouseMaxX, _mouseMaxY; int _mouseHotspotX, _mouseHotspotY; - controller_data_buttons *_ctrlData; // Controller data read from the N64 serial interface uint8 _controllerPort; int8 _mousePort; bool _controllerHasRumble; @@ -201,6 +201,7 @@ public: void setupMixer(void); void detectControllers(void); + void readControllerAnalogInput(void); // read controller analog nub position }; #endif /* __OSYS_N64_H__ */ diff --git a/backends/platform/n64/osys_n64_base.cpp b/backends/platform/n64/osys_n64_base.cpp index f2b1603c1f..f755f1e899 100644 --- a/backends/platform/n64/osys_n64_base.cpp +++ b/backends/platform/n64/osys_n64_base.cpp @@ -118,13 +118,12 @@ OSystem_N64::OSystem_N64() { // Initialize ROMFS access interface initRomFSmanager((uint8*)(((uint32)&_romfs + (uint32)0xc00) | (uint32)0xB0000000)); - // Register vblank callback - registerVIhandler(vblCallback); - _mouseVisible = false; _mouseX = _overlayWidth / 2; _mouseY = _overlayHeight / 2; + _tempMouseX = _mouseX; + _tempMouseY = _mouseY; _mouseMaxX = _overlayWidth; _mouseMaxY = _overlayHeight; @@ -136,11 +135,12 @@ OSystem_N64::OSystem_N64() { detectControllers(); - _ctrlData = (controller_data_buttons*)memalign(8, sizeof(controller_data_buttons)); _controllerHasRumble = (identifyPak(_controllerPort) == 2); _fsFactory = new N64FilesystemFactory(); + // Register vblank callback (this MUST be done at the END of init). + registerVIhandler(vblCallback); } OSystem_N64::~OSystem_N64() { diff --git a/backends/platform/n64/osys_n64_events.cpp b/backends/platform/n64/osys_n64_events.cpp index afbb31c2f6..216226d3a6 100644 --- a/backends/platform/n64/osys_n64_events.cpp +++ b/backends/platform/n64/osys_n64_events.cpp @@ -46,10 +46,61 @@ #define CD_BUTTON(a) (a & 0x0004) #define MOUSE_DEADZONE 0 -#define PAD_DEADZONE 5 -#define PAD_ACCELERATION 10 +#define PAD_DEADZONE 0 +#define PAD_ACCELERATION 15 #define PAD_CHECK_TIME 40 +static controller_data_buttons _ctrlData; + +void OSystem_N64::readControllerAnalogInput(void) { + int8 pad_analogX, pad_analogY; + int8 pad_mouseX, pad_mouseY; + + // Read current controller status + controller_Read_Buttons(&_ctrlData); + + pad_analogX = (_ctrlData.c[_controllerPort].throttle >> 8) & 0xFF; + pad_analogY = (_ctrlData.c[_controllerPort].throttle >> 0) & 0xFF; + + pad_mouseX = 0; + pad_mouseY = 0; + + if (_mousePort >= 0) { // If mouse is present, read movement values + pad_mouseX = (_ctrlData.c[_mousePort].throttle >> 8) & 0xFF; + pad_mouseY = (_ctrlData.c[_mousePort].throttle >> 0) & 0xFF; + } + + int32 mx = _tempMouseX; + int32 my = _tempMouseY; + + if (abs(pad_analogX) > PAD_DEADZONE) + mx += pad_analogX / (PAD_ACCELERATION - (abs(pad_analogX) / 20)); + + if (abs(pad_analogY) > PAD_DEADZONE) + my -= pad_analogY / (PAD_ACCELERATION - (abs(pad_analogY) / 20)); + + if (abs(pad_mouseX) > MOUSE_DEADZONE) + mx += pad_mouseX; + + if (abs(pad_mouseY) > MOUSE_DEADZONE) + my -= pad_mouseY; + + if (mx < 0) + mx = 0; + + if (mx >= _mouseMaxX) + mx = _mouseMaxX - 1; + + if (my < 0) + my = 0; + + if (my >= _mouseMaxY) + my = _mouseMaxY - 1; + + _tempMouseX = mx; + _tempMouseY = my; +} + bool OSystem_N64::pollEvent(Common::Event &event) { // Check Timers. Not the best place, but checking in interrupts proved to be unsafe checkTimers(); @@ -58,16 +109,16 @@ bool OSystem_N64::pollEvent(Common::Event &event) { refillAudioBuffers(); // Read current controller status - controller_Read_Buttons(_ctrlData); + controller_Read_Buttons(&_ctrlData); static uint16 oldButtons = 0; // old button data... used for button press/release static uint16 oldMouseButtons = 0; - uint16 newButtons = _ctrlData->c[_controllerPort].buttons; // Read from controller + uint16 newButtons = _ctrlData.c[_controllerPort].buttons; // Read from controller uint16 newMouseButtons = 0; if (_mousePort >= 0) - newMouseButtons = _ctrlData->c[_mousePort].buttons; + newMouseButtons = _ctrlData.c[_mousePort].buttons; bool buttonPressed = false; static bool left_digital = false; @@ -75,17 +126,6 @@ bool OSystem_N64::pollEvent(Common::Event &event) { static bool up_digital = false; static bool down_digital = false; - int8 analogX = (_ctrlData->c[_controllerPort].throttle >> 8) & 0xFF; - int8 analogY = (_ctrlData->c[_controllerPort].throttle >> 0) & 0xFF; - - int8 mouseX = 0; - int8 mouseY = 0; - - if (_mousePort >= 0) { // If mouse is present, read movement values - mouseX = (_ctrlData->c[_mousePort].throttle >> 8) & 0xFF; - mouseY = (_ctrlData->c[_mousePort].throttle >> 0) & 0xFF; - } - if (newButtons != oldButtons) { // Check PAD button press if (DL_BUTTON(newButtons) && !DL_BUTTON(oldButtons)) // Pressed LEFT left_digital = true; @@ -232,31 +272,20 @@ bool OSystem_N64::pollEvent(Common::Event &event) { if ((curTime - _lastPadCheck) > PAD_CHECK_TIME) { _lastPadCheck = curTime; - int32 mx = _mouseX; - int32 my = _mouseY; + int32 mx = _tempMouseX; + int32 my = _tempMouseY; if (left_digital || right_digital || up_digital || down_digital) { if (left_digital) - mx -= 5; + mx -= 2; else if (right_digital) - mx += 5; + mx += 2; if (up_digital) - my -= 5; + my -= 2; else if (down_digital) - my += 5; + my += 2; } - if (abs(analogX) > PAD_DEADZONE) - mx += analogX / (PAD_ACCELERATION - (abs(analogX) / 16)); - - if (abs(analogY) > PAD_DEADZONE) - my -= analogY / (PAD_ACCELERATION - (abs(analogY) / 16)); - - if (abs(mouseX) > MOUSE_DEADZONE) - mx += mouseX; - if (abs(mouseY) > MOUSE_DEADZONE) - my -= mouseY; - if (mx < 0) mx = 0; @@ -272,8 +301,8 @@ bool OSystem_N64::pollEvent(Common::Event &event) { if ((mx != _mouseX) || (my != _mouseY)) { event.type = Common::EVENT_MOUSEMOVE; - event.mouse.x = _mouseX = mx; - event.mouse.y = _mouseY = my; + event.mouse.x = _tempMouseX = _mouseX = mx; + event.mouse.y = _tempMouseY = _mouseY = my; _dirtyOffscreen = true; diff --git a/backends/platform/n64/osys_n64_utilities.cpp b/backends/platform/n64/osys_n64_utilities.cpp index 969cbb8560..e0c9e94f81 100644 --- a/backends/platform/n64/osys_n64_utilities.cpp +++ b/backends/platform/n64/osys_n64_utilities.cpp @@ -86,6 +86,8 @@ void vblCallback(void) { sndCallback(); sndCallback(); } + + ((OSystem_N64*)g_system)->readControllerAnalogInput(); } void sndCallback() { -- cgit v1.2.3