1
0
mirror of https://github.com/vcmi/vcmi.git synced 2025-11-23 22:37:55 +02:00

screen surface is now private member of ScreenHandler instead of global

This commit is contained in:
Ivan Savenko
2025-02-10 17:23:20 +00:00
parent 31e627f128
commit eb7587c000
16 changed files with 85 additions and 40 deletions

View File

@@ -16,8 +16,6 @@ struct SDL_Surface;
extern SDL_Texture * screenTexture;
extern SDL_Renderer * mainRenderer;
extern SDL_Surface *screen;
/// Notify user about encountered fatal error and terminate the game
/// Defined in clientapp EntryPoint
/// TODO: decide on better location for this method

View File

@@ -20,6 +20,7 @@
#include "../CGameInfo.h"
#include "../adventureMap/AdventureMapInterface.h"
#include "../render/Canvas.h"
#include "../render/Colors.h"
#include "../render/Graphics.h"
#include "../render/IFont.h"
@@ -104,21 +105,13 @@ void CGuiHandler::renderFrame()
if (settings["video"]["showfps"].Bool())
drawFPSCounter();
SDL_UpdateTexture(screenTexture, nullptr, screen->pixels, screen->pitch);
}
SDL_RenderClear(mainRenderer);
SDL_RenderCopy(mainRenderer, screenTexture, nullptr, nullptr);
{
boost::mutex::scoped_lock interfaceLock(GH.interfaceMutex);
CCS->curh->render();
screenHandlerInstance->updateScreenTexture();
windows().onFrameRendered();
CCS->curh->update();
}
SDL_RenderPresent(mainRenderer);
screenHandlerInstance->presetScreenTexture();
framerate().framerateDelay(); // holds a constant FPS
}
@@ -181,19 +174,12 @@ Point CGuiHandler::screenDimensions() const
void CGuiHandler::drawFPSCounter()
{
int scaling = screenHandlerInstance->getScalingFactor();
int x = 7 * scaling;
int y = screen->h-20 * scaling;
int width3digitFPSIncludingPadding = 48 * scaling;
int heightFPSTextIncludingPadding = 11 * scaling;
SDL_Rect overlay = { x, y, width3digitFPSIncludingPadding, heightFPSTextIncludingPadding};
uint32_t black = SDL_MapRGB(screen->format, 10, 10, 10);
SDL_FillRect(screen, &overlay, black);
Canvas target = GH.screenHandler().getScreenCanvas();
Rect targetArea(0, screenDimensions().y - 20, 48, 11);
std::string fps = std::to_string(framerate().getFramerate())+" FPS";
const auto & font = GH.renderHandler().loadFont(FONT_SMALL);
font->renderTextLeft(screen, fps, Colors::WHITE, Point(8 * scaling, screen->h-22 * scaling));
target.drawColor(targetArea, ColorRGBA(10, 10, 10));
target.drawText(targetArea.center(), EFonts::FONT_SMALL, Colors::WHITE, ETextAlignment::CENTER, fps);
}
bool CGuiHandler::amIGuiThread()

View File

@@ -15,6 +15,7 @@
#include "EventDispatcher.h"
#include "Shortcut.h"
#include "../render/Canvas.h"
#include "../render/IScreenHandler.h"
#include "../windows/CMessage.h"
#include "../CMT.h"
@@ -238,7 +239,7 @@ void CIntObject::redraw()
}
else
{
Canvas buffer = Canvas::createFromSurface(screen, CanvasScalingPolicy::AUTO);
Canvas buffer = GH.screenHandler().getScreenCanvas();
showAll(buffer);
}
}

View File

@@ -260,6 +260,11 @@ void CursorHandler::updateSpellcastCursor()
}
void CursorHandler::render()
{
cursor->render();
}
void CursorHandler::update()
{
if(!showing)
return;
@@ -267,7 +272,7 @@ void CursorHandler::render()
if (type == Cursor::Type::SPELLBOOK)
updateSpellcastCursor();
cursor->render();
cursor->update();
}
void CursorHandler::hide()

View File

@@ -179,6 +179,7 @@ public:
Point getPivotOffsetCombat(size_t index);
void render();
void update();
void hide();
void show();

View File

@@ -17,6 +17,7 @@
#include "../CMT.h"
#include "../CGameInfo.h"
#include "../render/Canvas.h"
#include "../render/IScreenHandler.h"
#include "../render/Colors.h"
#include "../renderSDL/SDL_Extensions.h"
@@ -108,7 +109,7 @@ void WindowHandler::totalRedrawImpl()
{
logGlobal->debug("totalRedraw requested!");
Canvas target = Canvas::createFromSurface(screen, CanvasScalingPolicy::AUTO);
Canvas target = GH.screenHandler().getScreenCanvas();
for(auto & elem : windowsStack)
elem->showAll(target);
@@ -126,7 +127,7 @@ void WindowHandler::simpleRedraw()
void WindowHandler::simpleRedrawImpl()
{
Canvas target = Canvas::createFromSurface(screen, CanvasScalingPolicy::AUTO);
Canvas target = GH.screenHandler().getScreenCanvas();
if(!windowsStack.empty())
windowsStack.back()->show(target); //blit active interface/window

View File

@@ -23,6 +23,7 @@ public:
virtual void setImage(std::shared_ptr<IImage> image, const Point & pivotOffset) = 0;
virtual void setCursorPosition( const Point & newPos ) = 0;
virtual void render() = 0;
virtual void update() = 0;
virtual void setVisible( bool on) = 0;
};

View File

@@ -15,6 +15,8 @@ class Point;
class Rect;
VCMI_LIB_NAMESPACE_END
class Canvas;
class IScreenHandler
{
public:
@@ -29,6 +31,15 @@ public:
/// Fills screen with black color, erasing any existing content
virtual void clearScreen() = 0;
/// Returns canvas that can be used to display objects on screen
virtual Canvas getScreenCanvas() const = 0;
/// Synchronizes internal screen texture. Screen canvas may not be modified during this call
virtual void updateScreenTexture() = 0;
/// Presents screen texture on the screen
virtual void presetScreenTexture() = 0;
/// Returns list of resolutions supported by current screen
virtual std::vector<Point> getSupportedResolutions() const = 0;

View File

@@ -92,3 +92,8 @@ void CursorHardware::render()
{
//no-op
}
void CursorHardware::update()
{
//no-op
}

View File

@@ -30,6 +30,7 @@ public:
void setImage(std::shared_ptr<IImage> image, const Point & pivotOffset) override;
void setCursorPosition( const Point & newPos ) override;
void render() override;
void update() override;
void setVisible( bool on) override;
};

View File

@@ -21,12 +21,15 @@
#include <SDL_render.h>
#include <SDL_events.h>
void CursorSoftware::render()
void CursorSoftware::update()
{
//texture must be updated in the main (renderer) thread, but changes to cursor type may come from other threads
if (needUpdate)
updateTexture();
}
void CursorSoftware::render()
{
Point renderPos = pos - pivot;
SDL_Rect destRect;

View File

@@ -38,6 +38,7 @@ public:
void setImage(std::shared_ptr<IImage> image, const Point & pivotOffset) override;
void setCursorPosition( const Point & newPos ) override;
void render() override;
void update() override;
void setVisible( bool on) override;
};

View File

@@ -211,7 +211,7 @@ SDLImageScaler::SDLImageScaler(SDL_Surface * surf, const Rect & virtualDimension
if (optimizeImage)
{
SDLImageOptimizer optimizer(surf, virtualDimensions);
optimizer.optimizeSurface(screen);
optimizer.optimizeSurface(nullptr);
intermediate = optimizer.acquireResultSurface();
virtualDimensionsInput = optimizer.getResultDimensions();
}

View File

@@ -71,24 +71,29 @@ void CSDL_Ext::setAlpha(SDL_Surface * bg, int value)
SDL_Surface * CSDL_Ext::newSurface(const Point & dimensions)
{
return newSurface(dimensions, screen);
return newSurface(dimensions, nullptr);
}
SDL_Surface * CSDL_Ext::newSurface(const Point & dimensions, SDL_Surface * mod) //creates new surface, with flags/format same as in surface given
{
SDL_Surface * ret = SDL_CreateRGBSurface(0,dimensions.x,dimensions.y,mod->format->BitsPerPixel,mod->format->Rmask,mod->format->Gmask,mod->format->Bmask,mod->format->Amask);
SDL_Surface * ret = nullptr;
if (mod != nullptr)
ret = SDL_CreateRGBSurface(0,dimensions.x,dimensions.y,mod->format->BitsPerPixel,mod->format->Rmask,mod->format->Gmask,mod->format->Bmask,mod->format->Amask);
else
ret = SDL_CreateRGBSurfaceWithFormat(0,dimensions.x,dimensions.y,32,SDL_PixelFormatEnum::SDL_PIXELFORMAT_ARGB8888);
if(ret == nullptr)
{
const char * error = SDL_GetError();
std::string messagePattern = "Failed to create SDL Surface of size %d x %d, %d bpp. Reason: %s";
std::string message = boost::str(boost::format(messagePattern) % dimensions.x % dimensions.y % mod->format->BitsPerPixel % error);
std::string messagePattern = "Failed to create SDL Surface of size %d x %d. Reason: %s";
std::string message = boost::str(boost::format(messagePattern) % dimensions.x % dimensions.y % error);
handleFatalError(message, true);
}
if (mod->format->palette)
if (mod && mod->format->palette)
{
assert(ret->format->palette);
assert(ret->format->palette->ncolors >= mod->format->palette->ncolors);

View File

@@ -11,11 +11,14 @@
#include "StdInc.h"
#include "ScreenHandler.h"
#include "../CGameInfo.h"
#include "../CMT.h"
#include "../eventsSDL/NotificationHandler.h"
#include "../gui/CGuiHandler.h"
#include "../gui/CursorHandler.h"
#include "../gui/WindowHandler.h"
#include "../render/Canvas.h"
#include "../renderSDL/SDL_Extensions.h"
#include "CMT.h"
#include "../../lib/CConfigHandler.h"
#include "../../lib/constants/StringConstants.h"
@@ -34,7 +37,6 @@
static SDL_Window * mainWindow = nullptr;
SDL_Renderer * mainRenderer = nullptr;
SDL_Texture * screenTexture = nullptr;
SDL_Surface * screen = nullptr; //main screen surface
static const std::string NAME = GameConstants::VCMI_VERSION; //application name
static constexpr Point heroes3Resolution = Point(800, 600);
@@ -621,6 +623,24 @@ void ScreenHandler::clearScreen()
SDL_RenderPresent(mainRenderer);
}
Canvas ScreenHandler::getScreenCanvas() const
{
return Canvas::createFromSurface(screen, CanvasScalingPolicy::AUTO);
}
void ScreenHandler::updateScreenTexture()
{
SDL_UpdateTexture(screenTexture, nullptr, screen->pixels, screen->pitch);
}
void ScreenHandler::presetScreenTexture()
{
SDL_RenderClear(mainRenderer);
SDL_RenderCopy(mainRenderer, screenTexture, nullptr, nullptr);
CCS->curh->render();
SDL_RenderPresent(mainRenderer);
}
std::vector<Point> ScreenHandler::getSupportedResolutions() const
{
int displayID = getPreferredDisplayIndex();

View File

@@ -10,14 +10,14 @@
#pragma once
#include "../../lib/Point.h"
#include "../render/IScreenHandler.h"
struct SDL_Texture;
struct SDL_Window;
struct SDL_Renderer;
struct SDL_Surface;
#include "../../lib/Point.h"
#include "../render/IScreenHandler.h"
enum class EWindowMode
{
// game runs in a window that covers part of the screen
@@ -44,6 +44,8 @@ enum class EUpscalingFilter
/// This class is responsible for management of game window and its main rendering surface
class ScreenHandler final : public IScreenHandler
{
SDL_Surface * screen = nullptr; //main screen surface
EUpscalingFilter upscalingFilter = EUpscalingFilter::AUTO;
/// Dimensions of target surfaces/textures, this value is what game logic views as screen size
@@ -114,6 +116,10 @@ public:
int getInterfaceScalingPercentage() const final;
Canvas getScreenCanvas() const final;
void updateScreenTexture() final;
void presetScreenTexture() final;
std::vector<Point> getSupportedResolutions() const final;
std::vector<Point> getSupportedResolutions(int displayIndex) const;
std::tuple<int, int> getSupportedScalingRange() const final;