mirror of
https://github.com/vcmi/vcmi.git
synced 2025-08-13 19:54:17 +02:00
Fixed handling of special palette colors in palette transformations
Fixes black color turning semi-transparent in some creatures from mods
This commit is contained in:
@@ -88,16 +88,13 @@ BattleStacksController::BattleStacksController(BattleInterface & owner):
|
|||||||
static const auto shifterNegative = ColorFilter::genRangeShifter( 0.f, 0.f, 0.f, 1.0f, 0.2f, 0.2f );
|
static const auto shifterNegative = ColorFilter::genRangeShifter( 0.f, 0.f, 0.f, 1.0f, 0.2f, 0.2f );
|
||||||
static const auto shifterNeutral = ColorFilter::genRangeShifter( 0.f, 0.f, 0.f, 1.0f, 1.0f, 0.2f );
|
static const auto shifterNeutral = ColorFilter::genRangeShifter( 0.f, 0.f, 0.f, 1.0f, 1.0f, 0.2f );
|
||||||
|
|
||||||
amountNormal->adjustPalette(shifterNormal, 0);
|
// do not change border color
|
||||||
amountPositive->adjustPalette(shifterPositive, 0);
|
static const int32_t ignoredMask = 1 << 26;
|
||||||
amountNegative->adjustPalette(shifterNegative, 0);
|
|
||||||
amountEffNeutral->adjustPalette(shifterNeutral, 0);
|
|
||||||
|
|
||||||
//Restore border color {255, 231, 132, 255} to its original state
|
amountNormal->adjustPalette(shifterNormal, ignoredMask);
|
||||||
amountNormal->resetPalette(26);
|
amountPositive->adjustPalette(shifterPositive, ignoredMask);
|
||||||
amountPositive->resetPalette(26);
|
amountNegative->adjustPalette(shifterNegative, ignoredMask);
|
||||||
amountNegative->resetPalette(26);
|
amountEffNeutral->adjustPalette(shifterNeutral, ignoredMask);
|
||||||
amountEffNeutral->resetPalette(26);
|
|
||||||
|
|
||||||
std::vector<const CStack*> stacks = owner.curInt->cb->battleGetAllStacks(true);
|
std::vector<const CStack*> stacks = owner.curInt->cb->battleGetAllStacks(true);
|
||||||
for(const CStack * s : stacks)
|
for(const CStack * s : stacks)
|
||||||
|
@@ -343,13 +343,14 @@ static SDL_Color addColors(const SDL_Color & base, const SDL_Color & over)
|
|||||||
|
|
||||||
void CreatureAnimation::genSpecialPalette(IImage::SpecialPalette & target)
|
void CreatureAnimation::genSpecialPalette(IImage::SpecialPalette & target)
|
||||||
{
|
{
|
||||||
target[0] = genShadow(shadowAlpha / 2);
|
target.resize(8);
|
||||||
|
target[0] = genShadow(0);
|
||||||
target[1] = genShadow(shadowAlpha / 2);
|
target[1] = genShadow(shadowAlpha / 2);
|
||||||
target[2] = genShadow(shadowAlpha);
|
target[2] = genShadow(shadowAlpha / 2);
|
||||||
target[3] = genShadow(shadowAlpha);
|
// colors 2 & 3 are not used in creatures
|
||||||
target[4] = genBorderColor(getBorderStrength(elapsedTime), border);
|
target[5] = genBorderColor(getBorderStrength(elapsedTime), border);
|
||||||
target[5] = addColors(genShadow(shadowAlpha), genBorderColor(getBorderStrength(elapsedTime), border));
|
target[6] = addColors(genShadow(shadowAlpha), genBorderColor(getBorderStrength(elapsedTime), border));
|
||||||
target[6] = addColors(genShadow(shadowAlpha / 2), genBorderColor(getBorderStrength(elapsedTime), border));
|
target[7] = addColors(genShadow(shadowAlpha / 2), genBorderColor(getBorderStrength(elapsedTime), border));
|
||||||
}
|
}
|
||||||
|
|
||||||
void CreatureAnimation::nextFrame(Canvas & canvas, const ColorFilter & shifter, bool facingRight)
|
void CreatureAnimation::nextFrame(Canvas & canvas, const ColorFilter & shifter, bool facingRight)
|
||||||
@@ -371,8 +372,8 @@ void CreatureAnimation::nextFrame(Canvas & canvas, const ColorFilter & shifter,
|
|||||||
IImage::SpecialPalette SpecialPalette;
|
IImage::SpecialPalette SpecialPalette;
|
||||||
genSpecialPalette(SpecialPalette);
|
genSpecialPalette(SpecialPalette);
|
||||||
|
|
||||||
image->setSpecialPallete(SpecialPalette);
|
image->setSpecialPallete(SpecialPalette, IImage::SPECIAL_PALETTE_MASK_CREATURES);
|
||||||
image->adjustPalette(shifter, 8);
|
image->adjustPalette(shifter, IImage::SPECIAL_PALETTE_MASK_CREATURES);
|
||||||
|
|
||||||
canvas.draw(image, pos.topLeft(), Rect(0, 0, pos.w, pos.h));
|
canvas.draw(image, pos.topLeft(), Rect(0, 0, pos.w, pos.h));
|
||||||
|
|
||||||
|
@@ -40,7 +40,8 @@ enum class EImageBlitMode : uint8_t
|
|||||||
class IImage
|
class IImage
|
||||||
{
|
{
|
||||||
public:
|
public:
|
||||||
using SpecialPalette = std::array<SDL_Color, 7>;
|
using SpecialPalette = std::vector<SDL_Color>;
|
||||||
|
static constexpr int32_t SPECIAL_PALETTE_MASK_CREATURES = 0b11110011;
|
||||||
|
|
||||||
//draws image on surface "where" at position
|
//draws image on surface "where" at position
|
||||||
virtual void draw(SDL_Surface * where, int posX = 0, int posY = 0, const Rect * src = nullptr) const = 0;
|
virtual void draw(SDL_Surface * where, int posX = 0, int posY = 0, const Rect * src = nullptr) const = 0;
|
||||||
@@ -65,7 +66,7 @@ public:
|
|||||||
|
|
||||||
//only indexed bitmaps, 16 colors maximum
|
//only indexed bitmaps, 16 colors maximum
|
||||||
virtual void shiftPalette(uint32_t firstColorID, uint32_t colorsToMove, uint32_t distanceToMove) = 0;
|
virtual void shiftPalette(uint32_t firstColorID, uint32_t colorsToMove, uint32_t distanceToMove) = 0;
|
||||||
virtual void adjustPalette(const ColorFilter & shifter, size_t colorsToSkip) = 0;
|
virtual void adjustPalette(const ColorFilter & shifter, uint32_t colorsToSkipMask) = 0;
|
||||||
virtual void resetPalette(int colorID) = 0;
|
virtual void resetPalette(int colorID) = 0;
|
||||||
virtual void resetPalette() = 0;
|
virtual void resetPalette() = 0;
|
||||||
|
|
||||||
@@ -73,7 +74,7 @@ public:
|
|||||||
virtual void setBlitMode(EImageBlitMode mode) = 0;
|
virtual void setBlitMode(EImageBlitMode mode) = 0;
|
||||||
|
|
||||||
//only indexed bitmaps with 7 special colors
|
//only indexed bitmaps with 7 special colors
|
||||||
virtual void setSpecialPallete(const SpecialPalette & SpecialPalette) = 0;
|
virtual void setSpecialPallete(const SpecialPalette & SpecialPalette, uint32_t colorsToSkipMask) = 0;
|
||||||
|
|
||||||
virtual void horizontalFlip() = 0;
|
virtual void horizontalFlip() = 0;
|
||||||
virtual void verticalFlip() = 0;
|
virtual void verticalFlip() = 0;
|
||||||
|
@@ -308,7 +308,7 @@ void SDLImage::shiftPalette(uint32_t firstColorID, uint32_t colorsToMove, uint32
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void SDLImage::adjustPalette(const ColorFilter & shifter, size_t colorsToSkip)
|
void SDLImage::adjustPalette(const ColorFilter & shifter, uint32_t colorsToSkipMask)
|
||||||
{
|
{
|
||||||
if(originalPalette == nullptr)
|
if(originalPalette == nullptr)
|
||||||
return;
|
return;
|
||||||
@@ -316,8 +316,11 @@ void SDLImage::adjustPalette(const ColorFilter & shifter, size_t colorsToSkip)
|
|||||||
SDL_Palette* palette = surf->format->palette;
|
SDL_Palette* palette = surf->format->palette;
|
||||||
|
|
||||||
// Note: here we skip first colors in the palette that are predefined in H3 images
|
// Note: here we skip first colors in the palette that are predefined in H3 images
|
||||||
for(int i = colorsToSkip; i < palette->ncolors; i++)
|
for(int i = 0; i < palette->ncolors; i++)
|
||||||
{
|
{
|
||||||
|
if(i < std::numeric_limits<uint32_t>::digits && ((colorsToSkipMask >> i) & 1) == 1)
|
||||||
|
continue;
|
||||||
|
|
||||||
palette->colors[i] = shifter.shiftColor(originalPalette->colors[i]);
|
palette->colors[i] = shifter.shiftColor(originalPalette->colors[i]);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -340,11 +343,17 @@ void SDLImage::resetPalette( int colorID )
|
|||||||
SDL_SetPaletteColors(surf->format->palette, originalPalette->colors + colorID, colorID, 1);
|
SDL_SetPaletteColors(surf->format->palette, originalPalette->colors + colorID, colorID, 1);
|
||||||
}
|
}
|
||||||
|
|
||||||
void SDLImage::setSpecialPallete(const IImage::SpecialPalette & SpecialPalette)
|
void SDLImage::setSpecialPallete(const IImage::SpecialPalette & specialPalette, uint32_t colorsToSkipMask)
|
||||||
{
|
{
|
||||||
if(surf->format->palette)
|
if(surf->format->palette)
|
||||||
{
|
{
|
||||||
CSDL_Ext::setColors(surf, const_cast<SDL_Color *>(SpecialPalette.data()), 1, 7);
|
size_t last = std::min<size_t>(specialPalette.size(), surf->format->palette->ncolors);
|
||||||
|
|
||||||
|
for (size_t i = 0; i < last; ++i)
|
||||||
|
{
|
||||||
|
if(i < std::numeric_limits<uint32_t>::digits && ((colorsToSkipMask >> i) & 1) == 1)
|
||||||
|
surf->format->palette->colors[i] = specialPalette[i];
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@@ -66,14 +66,14 @@ public:
|
|||||||
void verticalFlip() override;
|
void verticalFlip() override;
|
||||||
|
|
||||||
void shiftPalette(uint32_t firstColorID, uint32_t colorsToMove, uint32_t distanceToMove) override;
|
void shiftPalette(uint32_t firstColorID, uint32_t colorsToMove, uint32_t distanceToMove) override;
|
||||||
void adjustPalette(const ColorFilter & shifter, size_t colorsToSkip) override;
|
void adjustPalette(const ColorFilter & shifter, uint32_t colorsToSkipMask) override;
|
||||||
void resetPalette(int colorID) override;
|
void resetPalette(int colorID) override;
|
||||||
void resetPalette() override;
|
void resetPalette() override;
|
||||||
|
|
||||||
void setAlpha(uint8_t value) override;
|
void setAlpha(uint8_t value) override;
|
||||||
void setBlitMode(EImageBlitMode mode) override;
|
void setBlitMode(EImageBlitMode mode) override;
|
||||||
|
|
||||||
void setSpecialPallete(const SpecialPalette & SpecialPalette) override;
|
void setSpecialPallete(const SpecialPalette & SpecialPalette, uint32_t colorsToSkipMask) override;
|
||||||
|
|
||||||
friend class SDLImageLoader;
|
friend class SDLImageLoader;
|
||||||
|
|
||||||
|
Reference in New Issue
Block a user