Refactor SDL2 cursor manipulation

This commit is contained in:
Nikita Lisitsa 2022-04-06 17:52:32 +03:00
parent 5c401d6d50
commit bbeb05f34e
4 changed files with 38 additions and 19 deletions

View file

@ -5,4 +5,4 @@ file(GLOB_RECURSE PSEMEK_SDL2_SOURCES RELATIVE "${CMAKE_CURRENT_SOURCE_DIR}" "so
psemek_add_library(psemek-sdl2 ${PSEMEK_SDL2_HEADERS} ${PSEMEK_SDL2_SOURCES}) psemek_add_library(psemek-sdl2 ${PSEMEK_SDL2_HEADERS} ${PSEMEK_SDL2_SOURCES})
target_include_directories(psemek-sdl2 PUBLIC "${CMAKE_CURRENT_SOURCE_DIR}/include") target_include_directories(psemek-sdl2 PUBLIC "${CMAKE_CURRENT_SOURCE_DIR}/include")
target_link_libraries(psemek-sdl2 PUBLIC psemek-log SDL2) target_link_libraries(psemek-sdl2 PUBLIC psemek-log psemek-util SDL2)

View file

@ -5,13 +5,18 @@
namespace psemek::sdl2 namespace psemek::sdl2
{ {
enum class cursor_type
{
arrow,
beam,
hand,
};
struct cursor; struct cursor;
struct cursor_provider struct cursor_provider
{ {
virtual cursor const & arrow() const = 0; virtual cursor const & get(cursor_type type) const = 0;
virtual cursor const & beam() const = 0;
virtual cursor const & hand() const = 0;
virtual ~cursor_provider() {} virtual ~cursor_provider() {}
}; };
@ -21,6 +26,6 @@ namespace psemek::sdl2
std::unique_ptr<cursor_provider> set_cursor_provider(std::unique_ptr<cursor_provider> new_provider); std::unique_ptr<cursor_provider> set_cursor_provider(std::unique_ptr<cursor_provider> new_provider);
cursor_provider const * get_cursor_provider(); cursor_provider const * get_cursor_provider();
void set_cursor(cursor const & c); void set_cursor(cursor_type type);
} }

View file

@ -1,5 +1,6 @@
#include <psemek/sdl2/cursor.hpp> #include <psemek/sdl2/cursor.hpp>
#include <psemek/log/log.hpp> #include <psemek/log/log.hpp>
#include <psemek/util/enum.hpp>
#include <SDL2/SDL_mouse.h> #include <SDL2/SDL_mouse.h>
@ -25,7 +26,7 @@ namespace psemek::sdl2
struct cursor struct cursor
{ {
cursor_ptr cursor; std::unique_ptr<SDL_Cursor, cursor_deleter> cursor;
}; };
namespace namespace
@ -49,9 +50,17 @@ namespace psemek::sdl2
hand_.cursor.reset(create_system_cursor(SDL_SYSTEM_CURSOR_HAND)); hand_.cursor.reset(create_system_cursor(SDL_SYSTEM_CURSOR_HAND));
} }
cursor const & arrow() const override { return arrow_; } cursor const & get(cursor_type type) const override
cursor const & beam() const override { return beam_; } {
cursor const & hand() const override { return hand_; } switch (type)
{
case cursor_type::arrow: return arrow_;
case cursor_type::beam: return beam_;
case cursor_type::hand: return hand_;
}
throw util::unknown_enum_value_exception<cursor_type>(type);
}
private: private:
cursor arrow_; cursor arrow_;
@ -76,15 +85,20 @@ namespace psemek::sdl2
cursor_provider const * get_cursor_provider() cursor_provider const * get_cursor_provider()
{ {
static system_cursor_provider_impl const fallback; static std::unique_ptr<cursor_provider> fallback;
if (!current_provider)
return &fallback; if (current_provider)
return current_provider.get(); return current_provider.get();
if (!fallback)
fallback = system_cursor_provider();
return fallback.get();
} }
void set_cursor(cursor const & c) void set_cursor(cursor_type type)
{ {
SDL_SetCursor(c.cursor.get()); SDL_SetCursor(get_cursor_provider()->get(type).cursor.get());
} }

View file

@ -98,21 +98,21 @@ namespace psemek::ui
if (mouseover) if (mouseover)
{ {
state_ = state_t::mouseover; state_ = state_t::mouseover;
sdl2::set_cursor(sdl2::get_cursor_provider()->beam()); sdl2::set_cursor(sdl2::cursor_type::beam);
} }
break; break;
case state_t::mouseover: case state_t::mouseover:
if (!mouseover) if (!mouseover)
{ {
state_ = state_t::normal; state_ = state_t::normal;
sdl2::set_cursor(sdl2::get_cursor_provider()->arrow()); sdl2::set_cursor(sdl2::cursor_type::arrow);
} }
break; break;
case state_t::editing: case state_t::editing:
if (mouseover) if (mouseover)
sdl2::set_cursor(sdl2::get_cursor_provider()->beam()); sdl2::set_cursor(sdl2::cursor_type::beam);
else else
sdl2::set_cursor(sdl2::get_cursor_provider()->arrow()); sdl2::set_cursor(sdl2::cursor_type::arrow);
break; break;
} }