summaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
authorThorbjørn Lindeijer <bjorn@lindeijer.nl>2025-03-31 16:52:21 +0200
committerThorbjørn Lindeijer <bjorn@lindeijer.nl>2025-03-31 16:56:38 +0200
commitc3ebaad314653009b2c985156fac2e022a2acb74 (patch)
treed769388cda3fda1144b15a54cf4738bd5ddae325 /src
parent49beab3c3415d40d9a1d4326474d16547c4ae9ac (diff)
downloadmana-c3ebaad314653009b2c985156fac2e022a2acb74.tar.gz
mana-c3ebaad314653009b2c985156fac2e022a2acb74.tar.bz2
mana-c3ebaad314653009b2c985156fac2e022a2acb74.tar.xz
mana-c3ebaad314653009b2c985156fac2e022a2acb74.zip
Use color modulation to render text in different colors
No need to cache the image in different colors since color modulation is cheap these days.
Diffstat (limited to 'src')
-rw-r--r--src/gui/truetypefont.cpp25
-rw-r--r--src/sdlgraphics.cpp39
2 files changed, 43 insertions, 21 deletions
diff --git a/src/gui/truetypefont.cpp b/src/gui/truetypefont.cpp
index 30037f84..444641b5 100644
--- a/src/gui/truetypefont.cpp
+++ b/src/gui/truetypefont.cpp
@@ -56,16 +56,16 @@ bool operator==(SDL_Color lhs, SDL_Color rhs)
class TextChunk
{
public:
- TextChunk(const std::string &text, SDL_Color color)
+ TextChunk(const std::string &text)
: text(text)
- , color(color)
{}
void generate(TTF_Font *font)
{
+ // Always render in white, we'll use color modulation when rendering
SDL_Surface *surface = TTF_RenderUTF8_Blended(font,
getSafeUtf8String(text),
- color);
+ SDL_Color { 255, 255, 255, 255 });
if (!surface)
return;
@@ -77,7 +77,6 @@ public:
std::unique_ptr<Image> img;
const std::string text;
- const SDL_Color color;
};
std::list<TrueTypeFont*> TrueTypeFont::mFonts;
@@ -124,24 +123,13 @@ void TrueTypeFont::drawString(gcn::Graphics *graphics,
return;
auto *g = static_cast<Graphics *>(graphics);
- const gcn::Color col = g->getColor();
-
- /* The alpha value is ignored at image generation to avoid caching the
- * same text with different alpha values.
- */
- const SDL_Color color = {
- static_cast<Uint8>(col.r),
- static_cast<Uint8>(col.g),
- static_cast<Uint8>(col.b),
- 255
- };
bool found = false;
for (auto i = mCache.begin(); i != mCache.end(); ++i)
{
auto &chunk = *i;
- if (chunk.text == text && chunk.color == color)
+ if (chunk.text == text)
{
// Raise priority: move it to front
mCache.splice(mCache.begin(), mCache, i);
@@ -154,18 +142,17 @@ void TrueTypeFont::drawString(gcn::Graphics *graphics,
{
if (mCache.size() >= CACHE_SIZE)
mCache.pop_back();
- mCache.emplace_front(text, color);
+ mCache.emplace_front(text);
mCache.front().generate(mFont);
}
if (auto img = mCache.front().img.get())
{
- img->setAlpha(col.a / 255.0f);
g->drawRescaledImageF(img, 0, 0, x, y,
img->getWidth(),
img->getHeight(),
img->getWidth() / mScale,
- img->getHeight() / mScale);
+ img->getHeight() / mScale, true);
}
}
diff --git a/src/sdlgraphics.cpp b/src/sdlgraphics.cpp
index 23336313..0fec9ab7 100644
--- a/src/sdlgraphics.cpp
+++ b/src/sdlgraphics.cpp
@@ -30,6 +30,39 @@
#include <cmath>
+class SetColorAlphaMod
+{
+public:
+ SetColorAlphaMod(SDL_Texture *texture, gcn::Color color, bool enabled)
+ : mTexture(texture)
+ , mEnabled(texture != nullptr && enabled)
+ {
+ if (mEnabled)
+ {
+ SDL_GetTextureColorMod(texture, &mOriginal.r, &mOriginal.g, &mOriginal.b);
+ SDL_GetTextureAlphaMod(texture, &mOriginal.a);
+
+ SDL_SetTextureColorMod(texture, color.r, color.g, color.b);
+ SDL_SetTextureAlphaMod(texture, color.a * mOriginal.a / 255);
+ }
+ }
+
+ ~SetColorAlphaMod()
+ {
+ if (mEnabled)
+ {
+ SDL_SetTextureAlphaMod(mTexture, mOriginal.a);
+ SDL_SetTextureColorMod(mTexture, mOriginal.r, mOriginal.g, mOriginal.b);
+ }
+ }
+
+private:
+ SDL_Texture *mTexture = nullptr;
+ SDL_Color mOriginal;
+ const bool mEnabled;
+};
+
+
std::unique_ptr<Graphics> SDLGraphics::create(SDL_Window *window, const VideoSettings &settings)
{
int rendererFlags = 0;
@@ -134,7 +167,8 @@ bool SDLGraphics::drawRescaledImage(const Image *image,
dstRect.w = desiredWidth;
dstRect.h = desiredHeight;
- return !(SDL_RenderCopy(mRenderer, image->mTexture, &srcRect, &dstRect) < 0);
+ SetColorAlphaMod mod(image->mTexture, mColor, useColor);
+ return SDL_RenderCopy(mRenderer, image->mTexture, &srcRect, &dstRect) != 0;
}
#if SDL_VERSION_ATLEAST(2, 0, 10)
@@ -164,7 +198,8 @@ bool SDLGraphics::drawRescaledImageF(const Image *image,
dstRect.w = desiredWidth;
dstRect.h = desiredHeight;
- return !(SDL_RenderCopyF(mRenderer, image->mTexture, &srcRect, &dstRect) < 0);
+ SetColorAlphaMod mod(image->mTexture, mColor, useColor);
+ return SDL_RenderCopyF(mRenderer, image->mTexture, &srcRect, &dstRect) == 0;
}
#endif