Effects and context
The blending works fine as long as transparent pixels in the source texture (the eye layer texture) are pure black (#00 00 00). However, if transparent pixels are not black, the body and eye layer textures are blended incorrectly, as if the eye layer texture didn't have transparent pixels at all. A screenshot that shows the results is attached, with a eye layer PNG texture that reproduces this issue by virtue of not having black transparent pixels. A resource pack that exhibits the problem is also attached.
I'd like to highlight that non-black transparent pixels are a normal condition in well-formed PNG files, which can be generated by an encoder that does not care or wants to clear the color values of transparent pixels, or an artist that purposefully desires to leave a hidden message. Therefore, under most circumstances, a correct program should not end up rendering transparent pixels as non-transparent, no matter what their color values are.
Analysis and possible fix
The assets/minecraft/shaders/core/rendertype_eyes.json
render program file, which is used to define the shader stages responsible for rendering the entity eye layers for Endermen, the Ender Dragon, Phantoms and spiders, reads as follows in its first lines:
"blend": {
"func": "add",
"srcrgb": "srcalpha",
"dstrgb": "1-srcalpha"
},
In addition, Minecraft code assigns a ADDITIVE_TRANSPARENCY
render state shard, which initializes glBlendFunc
with both blending factor parameters set to GL_ONE
, while creating the entity eyes render type, in the field EYES
, at the net.minecraft.client.renderer.RenderType
class. By itself, this blending mode would just sum the colors and alpha values of both blended textures, which would look wrong in all cases. To try to counter this fact, rendertype_eyes.json
declares that the source color blending factor is the alpha of the source texture. But this fails to take into account the blending factor for the alpha channel, which was fixed to 1 by the render state shard. Therefore, the end result is that colors from the blended textures are just added together without any regard for the alpha channels at all, which is likely not intended given the render program declaration, and causes the issue described in this report.
A fix that would not require any Java code change at all would be modifying the first lines of rendertype_eyes.json
so they read as follows:
"blend": {
"func": "add",
"srcrgb": "srcalpha",
"dstrgb": "1-srcalpha",
"srcalpha": "srcalpha",
"dstalpha": "1-srcalpha"
},
This fix was tested by me to work on a resource pack affected by this issue, without any noticeable performance impact.
Disclaimer
Even though the attached screenshot shows that I'm using the Sodium mod, this issue also happens in vanilla 1.17.1, without any mod loaded. It's not caused by modding the game.
Attachments
Comments 4
This issue is blocked by MC-276988 as a result of there no longer being any blending at all
Hey! I do not want to put pressure or anything, but seeing that almost a week has passed and this bug seems relatively easy to confirm/mark as invalid, I'm curious about whether someone will do it at some point. To generate PNG files that exhibit this bug I've used GIMP, and enabled the checkbox to keep the color of transparent pixels in the PNG export options. Thanks.