raysan5 / raylib

A simple and easy-to-use library to enjoy videogames programming
http://www.raylib.com
zlib License
21.51k stars 2.18k forks source link

[rcore] Tint Alpha not applied to texture when using BLEND_ALPHA_PREMULTIPLY #4269

Closed AITYunivers closed 2 weeks ago

AITYunivers commented 3 weeks ago

Please, before submitting a new issue verify and check:

Issue description

When using an alpha of any value in a DrawTexture call's tint while the blend mode for premultiplied alpha is enabled, the alpha will not be applied to the image, even if it's 0.

Issue Screenshot

Left is with Premultiplied Alpha on with a tint of (255, 255, 255, 105) (Issue) Middle is with Premultiplied Alpha off with a tint of (255, 255, 255, 105) Right is with Premultiplied Alpha on with a tint of WHITE with a shader multiplying the color.rgba by 105

image

Code Example

BeginBlendMode(BLEND_ALPHA_PREMULTIPLY);
    DrawTexture(texture, posX, posY, (Color){ 255, 255, 255, 105 });
EndBlendMode();
veins1 commented 3 weeks ago

Isn't the whole point of pre-multiplied alpha mode is that it doesn't multiply colors by alpha? It's called pre-multiplied because the color were already multiplied by alpha beforehand and you don't want to do it twice.

AITYunivers commented 3 weeks ago

@veins1 What you do and "don't" want to do with premultiplied alphas doesn't change anything. You should still be able to use the tint properly.

veins1 commented 3 weeks ago

@AITYunivers The whole point of pre-multiplied alpha mode is that it doesn't multiply colors by alpha. If you want to multiply colors by alpha - don't use pre-multiplied alpha mode.

AITYunivers commented 3 weeks ago

@veins1 That's the complete opposite of what premultiplied alpha is.

Screenshot_20240819-205030_Google.jpg

veins1 commented 3 weeks ago

@AITYunivers The picture you sent is correct and describes the same thing I wrote in my first message.

It's called pre-multiplied because the color were already multiplied by alpha beforehand and you don't want to do it twice.

Anyways, no matter what it's called, if you want to multiply colors by alpha - don't use pre-multiplied alpha mode.

AITYunivers commented 3 weeks ago

@veins1 What's your problem man? Lol. It's not unreasonable to expect the tint alpha to change the image's alpha, and it's not impossible to do. It shouldn't effect most if not all projects, and it's a normal thing you'd find in any game engine or rendering framework with premultiplied alpha and color tints. It's logically expected behaviour vs your flawed logic's behaviour. Ray said he'd make the choice himself in a few months so there's no use arguing over this.

AITYunivers commented 3 weeks ago

I should add on that I'm fine with it like, not multiplying the color.rgb by tint.a, that's just what I know game engines I've used have done it when you look into the code. But it should most definitely be multiplying color.a by tint.a. Which is the main issue here. If a color has 0 alpha, you 100% should not be seeing that image.

raysan5 commented 3 weeks ago

@AITYunivers sincerely, I don't know how it can be addressed, what is your proposed solution? I agree with @veins1 in the mentioned points.

AITYunivers commented 3 weeks ago

@raysan5 Not really too sure how OpenGL works. But doesn't Raylib have a default fragment shader? Can't you incorporate it into that? Also it could just be a flag in ConfigFlags or a #define. I don't know how you'd do it in compatibility for OpenGL 1.1 though, since iirc that doesn't have fragment shaders.

raysan5 commented 3 weeks ago

@AITYunivers If I modify the default shader it would affect all the drawn elements in all cases, I'm afraid I can't do that. I mean, I have no way to know if a provided texture has pre-multiplied alpha or not.

AITYunivers commented 3 weeks ago

@raysan5 Can't you just check the Blend Mode? That solves the second issue, and by correlation the first issue.

raysan5 commented 3 weeks ago

@AITYunivers What do you mean? The blend mode is setup at OpenGL level, afaik, not much options to consider premultiplied textures in there but feel free to investigate that possibility...

AITYunivers commented 3 weeks ago

@raysan5 The textures are premultiplied on render, right? Do you not store the blend mode from BeginBlendMode?

raysan5 commented 2 weeks ago

@AITYunivers Yes but I'm afraid I can't predict if the provided texture by user has alpha premultiplied or not, so I can't apply a solution. What if the provided texture for blending has no premultiplied alpha? If considering the texture as premultiplied it wouldn't work as expected for those cases.

I'm closing this issue because I can't see a way to address it but, please, if you can find a solution feel free to send a Pull-Request for review.

AITYunivers commented 2 weeks ago

Textures don't just... have premultiplied alpha, that's not how this works.

Premultiplied Alpha is only applied when the blending mode is enabled, and it's applied by OpenGL, not the user. Premultiplied Alpha multiplies the color by the alpha when rendered with the blend mode enabled, it's nothing the user does with their texture.

Raylib has full knowledge of when a texture is going to be drawn with or without premultiplied alpha.

raysan5 commented 2 weeks ago

@AITYunivers Sincerely, no idea how to address this issue. Feel free to send a PR to review.