Skip to content

Commit

Permalink
Use sdl2::SurfacePtr in CCursor.
Browse files Browse the repository at this point in the history
Add `sdl2::CursorPtr`.
  • Loading branch information
Jarod42 committed Mar 22, 2024
1 parent 6aa6d81 commit 413a7d5
Show file tree
Hide file tree
Showing 3 changed files with 52 additions and 41 deletions.
5 changes: 3 additions & 2 deletions src/include/cursor.h
Original file line number Diff line number Diff line change
Expand Up @@ -106,6 +106,7 @@
-- Includes
----------------------------------------------------------------------------*/

#include "sdl2_helper.h"
#include "vec2i.h"

#include <SDL.h>
Expand Down Expand Up @@ -146,8 +147,8 @@ class CCursor
CGraphic *G = nullptr; /// Cursor sprite image

private:
std::vector<SDL_Cursor*> SdlCursors;
std::vector<SDL_Surface*> SdlCursorSurfaces;
std::vector<sdl2::CursorPtr> SdlCursors;
std::vector<sdl2::SurfacePtr> SdlCursorSurfaces;
};

/// Cursor config reference
Expand Down
25 changes: 21 additions & 4 deletions src/include/sdl2_helper.h
Original file line number Diff line number Diff line change
Expand Up @@ -35,10 +35,26 @@
namespace sdl2 {
struct SDL_Deleter
{
void operator()(SDL_Surface* ptr) { if (ptr) SDL_FreeSurface(ptr); }
void operator()(SDL_Texture* ptr) { if (ptr) SDL_DestroyTexture(ptr); }
void operator()(SDL_Renderer* ptr) { if (ptr) SDL_DestroyRenderer(ptr); }
void operator()(SDL_Window* ptr) { if (ptr) SDL_DestroyWindow(ptr); }
void operator()(SDL_Cursor *ptr) const
{
if (ptr) SDL_FreeCursor(ptr);
}
void operator()(SDL_Surface *ptr) const
{
if (ptr) SDL_FreeSurface(ptr);
}
void operator()(SDL_Texture *ptr) const
{
if (ptr) SDL_DestroyTexture(ptr);
}
void operator()(SDL_Renderer *ptr) const
{
if (ptr) SDL_DestroyRenderer(ptr);
}
void operator()(SDL_Window *ptr) const
{
if (ptr) SDL_DestroyWindow(ptr);
}
};

template<typename T>
Expand All @@ -50,6 +66,7 @@ namespace sdl2 {
};


using CursorPtr = std::unique_ptr<SDL_Cursor, SDL_Deleter>;
using SurfacePtr = std::unique_ptr<SDL_Surface, SDL_Deleter>;
using TexturePtr = std::unique_ptr<SDL_Texture, SDL_Deleter>;
using RendererPtr = std::unique_ptr<SDL_Renderer, SDL_Deleter>;
Expand Down
63 changes: 28 additions & 35 deletions src/video/cursor.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -88,7 +88,7 @@ static CCursor *ActuallyVisibleGameCursor;
static unsigned int VisibleGameCursorFrame;


static SDL_Surface *HiddenSurface;
static sdl2::SurfacePtr HiddenSurface;

/*----------------------------------------------------------------------------
-- Functions
Expand Down Expand Up @@ -119,39 +119,32 @@ SDL_Cursor *CCursor::GetSDLCursor()

SDL_Rect srect = {G->frame_map[i].x, G->frame_map[i].y, G->getWidth(), G->getHeight()};

SDL_Surface *intermediate = SDL_CreateRGBSurface(0, srect.w, srect.h, 32, RMASK, GMASK, BMASK, AMASK);
SDL_BlitSurface(G->getSurface(), &srect, intermediate, nullptr);
sdl2::SurfacePtr intermediate{
SDL_CreateRGBSurface(0, srect.w, srect.h, 32, RMASK, GMASK, BMASK, AMASK)};
SDL_BlitSurface(G->getSurface(), &srect, intermediate.get(), nullptr);

SDL_Surface *cursorFrame = SDL_CreateRGBSurface(0, w, h, 32, RMASK, GMASK, BMASK, AMASK);
SDL_BlitScaled(intermediate, nullptr, cursorFrame, nullptr);
sdl2::SurfacePtr cursorFrame{
SDL_CreateRGBSurface(0, w, h, 32, RMASK, GMASK, BMASK, AMASK)};
SDL_BlitScaled(intermediate.get(), nullptr, cursorFrame.get(), nullptr);

SDL_FreeSurface(intermediate);
intermediate.reset();

SdlCursorSurfaces.push_back(cursorFrame);
SDL_Cursor *cur = SDL_CreateColorCursor(cursorFrame, floor(HotPos.x * xScale), floor(HotPos.y * yScale));
SdlCursors.push_back(cur);
SdlCursorSurfaces.push_back(std::move(cursorFrame));
sdl2::CursorPtr cur{SDL_CreateColorCursor(SdlCursorSurfaces.back().get(),
floor(HotPos.x * xScale),
floor(HotPos.y * yScale))};
SdlCursors.push_back(std::move(cur));
}
}
return SdlCursors[SpriteFrame];
return SdlCursors[SpriteFrame].get();
}

CCursor::~CCursor()
{
for (auto sdlCur : SdlCursors) {
SDL_FreeCursor(sdlCur);
}
for (auto sdlSurface : SdlCursorSurfaces) {
SDL_FreeSurface(sdlSurface);
}
}

void CCursor::Reset() {
for (auto sdlCur : SdlCursors) {
SDL_FreeCursor(sdlCur);
}
for (auto sdlSurface : SdlCursorSurfaces) {
SDL_FreeSurface(sdlSurface);
}
void CCursor::Reset()
{
SdlCursors.clear();
SdlCursorSurfaces.clear();
}
Expand Down Expand Up @@ -354,20 +347,20 @@ void DrawCursor()
|| HiddenSurface->w != GameCursor->G->getWidth()
|| HiddenSurface->h != GameCursor->G->getHeight()) {
if (HiddenSurface) {
VideoPaletteListRemove(HiddenSurface);
SDL_FreeSurface(HiddenSurface);
VideoPaletteListRemove(HiddenSurface.get());
SDL_FreeSurface(HiddenSurface.get());
}
HiddenSurface = SDL_CreateRGBSurface(SDL_SWSURFACE,
GameCursor->G->getWidth(),
GameCursor->G->getHeight(),
TheScreen->format->BitsPerPixel,
TheScreen->format->Rmask,
TheScreen->format->Gmask,
TheScreen->format->Bmask,
TheScreen->format->Amask);
HiddenSurface.reset(SDL_CreateRGBSurface(SDL_SWSURFACE,
GameCursor->G->getWidth(),
GameCursor->G->getHeight(),
TheScreen->format->BitsPerPixel,
TheScreen->format->Rmask,
TheScreen->format->Gmask,
TheScreen->format->Bmask,
TheScreen->format->Amask));
}
SDL_Rect srcRect = { Sint16(pos.x), Sint16(pos.y), Uint16(GameCursor->G->getWidth()), Uint16(GameCursor->G->getHeight())};
SDL_BlitSurface(TheScreen, &srcRect, HiddenSurface, nullptr);
SDL_BlitSurface(TheScreen, &srcRect, HiddenSurface.get(), nullptr);
}

if (!GameCursor->G->IsLoaded()) {
Expand Down Expand Up @@ -395,7 +388,7 @@ void HideCursor()
if (!Preference.HardwareCursor && !GameRunning && !Editor.Running && GameCursor) {
const PixelPos pos = CursorScreenPos - GameCursor->HotPos;
SDL_Rect dstRect = {Sint16(pos.x), Sint16(pos.y), 0, 0 };
SDL_BlitSurface(HiddenSurface, nullptr, TheScreen, &dstRect);
SDL_BlitSurface(HiddenSurface.get(), nullptr, TheScreen, &dstRect);
} else {
SDL_SetCursor(Video.blankCursor);
ActuallyVisibleGameCursor = nullptr;
Expand Down

0 comments on commit 413a7d5

Please sign in to comment.