diff --git a/CHANGELOG.md b/CHANGELOG.md index 9d326869b..864608373 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -70,6 +70,7 @@ * Fixed renderer to work with 3.6 changes. Sadly, two color tinting does not work, as the vertex format in SFML is fixed. * Added support for clipping. * Added support for vertex effects. See raptor example. + * Added premultiplied alpha support to `SkeletonDrawable`. ### Unreal Engine 4 * Fixed renderer to work with 3.6 changes diff --git a/spine-sfml/src/spine/spine-sfml.cpp b/spine-sfml/src/spine/spine-sfml.cpp index cde60e0b2..0ef19e61a 100644 --- a/spine-sfml/src/spine/spine-sfml.cpp +++ b/spine-sfml/src/spine/spine-sfml.cpp @@ -36,6 +36,16 @@ using namespace sf; +sf::BlendMode normal = sf::BlendMode(sf::BlendMode::SrcAlpha, sf::BlendMode::OneMinusSrcAlpha); +sf::BlendMode additive = sf::BlendMode(sf::BlendMode::SrcAlpha, sf::BlendMode::One); +sf::BlendMode multiply = sf::BlendMode(sf::BlendMode::DstColor, sf::BlendMode::OneMinusSrcAlpha); +sf::BlendMode screen = sf::BlendMode(sf::BlendMode::One, sf::BlendMode::OneMinusSrcColor); + +sf::BlendMode normalPma = sf::BlendMode(sf::BlendMode::One, sf::BlendMode::OneMinusSrcAlpha); +sf::BlendMode additivePma = sf::BlendMode(sf::BlendMode::One, sf::BlendMode::One); +sf::BlendMode multiplyPma = sf::BlendMode(sf::BlendMode::DstColor, sf::BlendMode::OneMinusSrcAlpha); +sf::BlendMode screenPma = sf::BlendMode(sf::BlendMode::One, sf::BlendMode::OneMinusSrcColor); + _SP_ARRAY_IMPLEMENT_TYPE(spColorArray, spColor) void _AtlasPage_createTexture (AtlasPage* self, const char* path){ @@ -163,16 +173,40 @@ void SkeletonDrawable::draw (RenderTarget& target, RenderStates states) const { light.a = a / 255.0f; sf::BlendMode blend; - switch (slot->data->blendMode) { - case BLEND_MODE_ADDITIVE: - blend = BlendAdd; - break; - case BLEND_MODE_MULTIPLY: - blend = BlendMultiply; - break; - case BLEND_MODE_SCREEN: // Unsupported, fall through. - default: - blend = BlendAlpha; + if (!usePremultipliedAlpha) { + switch (slot->data->blendMode) { + case BLEND_MODE_NORMAL: + blend = normal; + break; + case BLEND_MODE_ADDITIVE: + blend = additive; + break; + case BLEND_MODE_MULTIPLY: + blend = multiply; + break; + case BLEND_MODE_SCREEN: + blend = screen; + break; + default: + blend = normal; + } + } else { + switch (slot->data->blendMode) { + case BLEND_MODE_NORMAL: + blend = normalPma; + break; + case BLEND_MODE_ADDITIVE: + blend = additivePma; + break; + case BLEND_MODE_MULTIPLY: + blend = multiplyPma; + break; + case BLEND_MODE_SCREEN: + blend = screenPma; + break; + default: + blend = normalPma; + } } if (states.texture == 0) states.texture = texture; diff --git a/spine-sfml/src/spine/spine-sfml.h b/spine-sfml/src/spine/spine-sfml.h index 4074b71f0..879066ca5 100644 --- a/spine-sfml/src/spine/spine-sfml.h +++ b/spine-sfml/src/spine/spine-sfml.h @@ -58,12 +58,16 @@ public: void update (float deltaTime); virtual void draw (sf::RenderTarget& target, sf::RenderStates states) const; + + void setUsePremultipliedAlpha(bool usePMA) { usePremultipliedAlpha = usePMA; }; + bool getUsePremultipliedAlpha() { return usePremultipliedAlpha; }; private: bool ownsAnimationStateData; float* worldVertices; spFloatArray* tempUvs; spColorArray* tempColors; spSkeletonClipping* clipper; + bool usePremultipliedAlpha; }; } /* namespace spine */