From 07e22b033b566d61e99d077b2588fa1de6e5c5f8 Mon Sep 17 00:00:00 2001 From: Semphriss <66701383+Semphriss@users.noreply.github.com> Date: Sun, 23 Apr 2023 04:32:11 -0400 Subject: [PATCH] Hide the cursor during gameplay (#4861) * Hide the cursor during gameplay The cursor will show back up whenever: - The mouse is moved - The game is paused - The race finished This is probably not the best implementation, but it's a start. * Wrap mouse display code in PT_MAIN checker * Moved mouse display code to updateGraphics * Protect SDL calls with #ifndef SERVER_ONLY --------- Co-authored-by: Semphris --- src/modes/world.cpp | 49 ++++++++++++++++++++++++++++++++++++++++++++- src/modes/world.hpp | 5 +++++ 2 files changed, 53 insertions(+), 1 deletion(-) diff --git a/src/modes/world.cpp b/src/modes/world.cpp index 5cb55833c..a0207df70 100644 --- a/src/modes/world.cpp +++ b/src/modes/world.cpp @@ -91,6 +91,9 @@ #include #include +/** Hide the cursor after this many seconds without movement */ +#define HIDE_CURSOR_STARTINGAT 1.0f + World* World::m_world[PT_COUNT]; /** The main world class is used to handle the track and the karts. @@ -161,6 +164,8 @@ void World::init() { m_ended_early = false; m_faster_music_active = false; + m_time_since_last_mouse_mvmt = HIDE_CURSOR_STARTINGAT; + m_force_show_cursor = false; m_fastest_kart = 0; m_eliminated_karts = 0; m_eliminated_players = 0; @@ -419,6 +424,16 @@ void World::reset(bool restart) // Start music from beginning music_manager->stopMusic(); +#ifndef SERVER_ONLY + if (m_process_type == PT_MAIN) + { + m_force_show_cursor = false; + m_time_since_last_mouse_mvmt = HIDE_CURSOR_STARTINGAT; + SDL_GetMouseState(&m_last_mouse_pos_x, &m_last_mouse_pos_y); + SDL_ShowCursor(SDL_DISABLE); + } +#endif + // Enable SFX again SFXManager::get()->resumeAll(); @@ -609,6 +624,11 @@ World::~World() { if (m_process_type == PT_MAIN) { +#ifndef SERVER_ONLY + // This shouldn't be necessary, but just to be sure + SDL_ShowCursor(SDL_ENABLE); +#endif + GUIEngine::getDevice()->setResizable(false); material_manager->unloadAllTextures(); } @@ -727,6 +747,8 @@ void World::onGo() */ void World::terminateRace() { + m_force_show_cursor = true; + // In case the user opened paused dialog in network if (!GUIEngine::isNoGraphics()) { @@ -1006,7 +1028,6 @@ void World::updateWorld(int ticks) assert(m_magic_number == 0xB01D6543); #endif - if (m_schedule_pause) { pause(m_scheduled_pause_phase); @@ -1122,6 +1143,27 @@ void World::scheduleTutorial() */ void World::updateGraphics(float dt) { +#ifndef SERVER_ONLY + if (m_process_type == PT_MAIN) + { + int x, y; + SDL_GetMouseState(&x, &y); + if (m_last_mouse_pos_x != x || m_last_mouse_pos_y != y) + { + m_time_since_last_mouse_mvmt = 0; + m_last_mouse_pos_x = x; + m_last_mouse_pos_y = y; + } + else + { + m_time_since_last_mouse_mvmt += dt; + } + + SDL_ShowCursor((m_time_since_last_mouse_mvmt < HIDE_CURSOR_STARTINGAT + || m_force_show_cursor) ? SDL_ENABLE : SDL_DISABLE); + } +#endif + if (auto cl = LobbyProtocol::get()) { // Reset all smooth network body of rewinders so the rubber band effect @@ -1479,6 +1521,8 @@ void World::getDefaultCollectibles(int *collectible_type, int *amount ) */ void World::pause(Phase phase) { + m_force_show_cursor = true; + if (m_stop_music_when_dialog_open) music_manager->pauseMusic(); SFXManager::get()->pauseAll(); @@ -1489,6 +1533,9 @@ void World::pause(Phase phase) //----------------------------------------------------------------------------- void World::unpause() { + m_force_show_cursor = false; + m_time_since_last_mouse_mvmt = HIDE_CURSOR_STARTINGAT; + if (m_stop_music_when_dialog_open) music_manager->resumeMusic(); SFXManager::get()->resumeAll(); diff --git a/src/modes/world.hpp b/src/modes/world.hpp index eb76b941e..3c05dc2c9 100644 --- a/src/modes/world.hpp +++ b/src/modes/world.hpp @@ -184,6 +184,11 @@ protected: bool m_ended_early; + int m_last_mouse_pos_x; + int m_last_mouse_pos_y; + float m_time_since_last_mouse_mvmt; + bool m_force_show_cursor; + virtual void onGo() OVERRIDE; /** Returns true if the race is over. Must be defined by all modes. */ virtual bool isRaceOver() = 0;