sdlwindow: Forward cursor in absolute mode to host compositor
This commit is contained in:
parent
86ff9cfc58
commit
2d7ec208c4
4 changed files with 75 additions and 7 deletions
|
@ -34,6 +34,7 @@ enum UserEvents
|
|||
USER_EVENT_TITLE,
|
||||
USER_EVENT_VISIBLE,
|
||||
USER_EVENT_GRAB,
|
||||
USER_EVENT_CURSOR,
|
||||
|
||||
USER_EVENT_COUNT
|
||||
};
|
||||
|
@ -44,6 +45,15 @@ static std::mutex g_SDLWindowTitleLock;
|
|||
static std::string g_SDLWindowTitle;
|
||||
static bool g_bUpdateSDLWindowTitle = false;
|
||||
|
||||
struct SDLPendingCursor
|
||||
{
|
||||
uint32_t width, height, xhot, yhot;
|
||||
std::vector<uint32_t> data;
|
||||
};
|
||||
static std::mutex g_SDLCursorLock;
|
||||
static SDLPendingCursor g_SDLPendingCursorData;
|
||||
static bool g_bUpdateSDLCursor = false;
|
||||
|
||||
//-----------------------------------------------------------------------------
|
||||
// Purpose: Convert from the remote scancode to a Linux event keycode
|
||||
//-----------------------------------------------------------------------------
|
||||
|
@ -316,6 +326,24 @@ void inputSDLThreadRun( void )
|
|||
bRelativeMouse = grab;
|
||||
}
|
||||
}
|
||||
if ( event.type == g_unSDLUserEventID + USER_EVENT_CURSOR )
|
||||
{
|
||||
std::unique_lock lock(g_SDLCursorLock);
|
||||
if ( g_bUpdateSDLCursor )
|
||||
{
|
||||
SDL_Surface *surface = SDL_CreateRGBSurfaceFrom(
|
||||
g_SDLPendingCursorData.data.data(),
|
||||
g_SDLPendingCursorData.width,
|
||||
g_SDLPendingCursorData.height,
|
||||
32,
|
||||
g_SDLPendingCursorData.width * sizeof(uint32_t),
|
||||
0x00FF0000, 0x0000FF00, 0x000000FF, 0xFF000000);
|
||||
|
||||
SDL_Cursor *cursor = SDL_CreateColorCursor( surface, g_SDLPendingCursorData.xhot, g_SDLPendingCursorData.yhot );
|
||||
SDL_SetCursor( cursor );
|
||||
g_bUpdateSDLCursor = false;
|
||||
}
|
||||
}
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
@ -372,8 +400,39 @@ void sdlwindow_grab( bool bGrab )
|
|||
if ( g_bForceRelativeMouse )
|
||||
return;
|
||||
|
||||
static bool s_bWasGrabbed = false;
|
||||
|
||||
if ( s_bWasGrabbed == bGrab )
|
||||
return;
|
||||
|
||||
s_bWasGrabbed = bGrab;
|
||||
|
||||
SDL_Event event;
|
||||
event.type = g_unSDLUserEventID + USER_EVENT_GRAB;
|
||||
event.user.code = bGrab ? 1 : 0;
|
||||
SDL_PushEvent( &event );
|
||||
}
|
||||
|
||||
void sdlwindow_cursor(void* pixels, uint32_t width, uint32_t height, uint32_t xhot, uint32_t yhot)
|
||||
{
|
||||
if ( !BIsNested() )
|
||||
return;
|
||||
|
||||
if ( g_bForceRelativeMouse )
|
||||
return;
|
||||
|
||||
{
|
||||
std::unique_lock lock( g_SDLCursorLock );
|
||||
g_SDLPendingCursorData.width = width;
|
||||
g_SDLPendingCursorData.height = height;
|
||||
g_SDLPendingCursorData.xhot = xhot;
|
||||
g_SDLPendingCursorData.yhot = yhot;
|
||||
g_SDLPendingCursorData.data.resize( width * height );
|
||||
memcpy(g_SDLPendingCursorData.data.data(), pixels, width * height * sizeof(uint32_t));
|
||||
g_bUpdateSDLCursor = true;
|
||||
}
|
||||
|
||||
SDL_Event event;
|
||||
event.type = g_unSDLUserEventID + USER_EVENT_CURSOR;
|
||||
SDL_PushEvent( &event );
|
||||
}
|
||||
|
|
|
@ -13,5 +13,6 @@ void sdlwindow_title( const char* title );
|
|||
// called from other threads with interesting things have happened with clients that might warrant updating the nested window
|
||||
void sdlwindow_visible( bool bVisible );
|
||||
void sdlwindow_grab( bool bGrab );
|
||||
void sdlwindow_cursor(void* pixels, uint32_t width, uint32_t height, uint32_t xhot, uint32_t yhot);
|
||||
|
||||
extern SDL_Window *g_SDLWindow;
|
||||
|
|
|
@ -1364,14 +1364,12 @@ bool MouseCursor::getTexture()
|
|||
}
|
||||
}
|
||||
|
||||
if (bNoCursor != m_imageEmpty) {
|
||||
m_imageEmpty = bNoCursor;
|
||||
m_imageEmpty = bNoCursor;
|
||||
|
||||
if ( !g_bForceRelativeMouse )
|
||||
{
|
||||
sdlwindow_grab( m_imageEmpty );
|
||||
bSteamCompMgrGrab = BIsNested() && m_imageEmpty;
|
||||
}
|
||||
if ( !g_bForceRelativeMouse )
|
||||
{
|
||||
sdlwindow_grab( m_imageEmpty );
|
||||
bSteamCompMgrGrab = BIsNested() && m_imageEmpty;
|
||||
}
|
||||
|
||||
m_dirty = false;
|
||||
|
@ -1391,6 +1389,7 @@ bool MouseCursor::getTexture()
|
|||
}
|
||||
|
||||
m_texture = vulkan_create_texture_from_bits(surfaceWidth, surfaceHeight, image->width, image->height, DRM_FORMAT_ARGB8888, texCreateFlags, cursorBuffer.data());
|
||||
sdlwindow_cursor(cursorBuffer.data(), image->width, image->height, image->xhot, image->yhot);
|
||||
assert(m_texture);
|
||||
XFree(image);
|
||||
|
||||
|
@ -1910,6 +1909,13 @@ paint_all(bool async)
|
|||
}
|
||||
}
|
||||
|
||||
if (input)
|
||||
{
|
||||
// Make sure to un-dirty the texture before we do any painting logic.
|
||||
// We determine whether we are grabbed etc this way.
|
||||
global_focus.cursor->undirty();
|
||||
}
|
||||
|
||||
bool bForceHideCursor = BIsNested() && !bSteamCompMgrGrab;
|
||||
|
||||
bool bDrewCursor = false;
|
||||
|
|
|
@ -71,6 +71,8 @@ public:
|
|||
m_y = y;
|
||||
}
|
||||
|
||||
void undirty() { getTexture(); }
|
||||
|
||||
private:
|
||||
void warp(int x, int y);
|
||||
void checkSuspension();
|
||||
|
|
Loading…
Reference in a new issue