• Unity
  • PMA in linear color space creates black borders

Related Discussions
...

Problem with black borders around sprite parts (neck and hands in this case). Been very careful to save out as PMA and tried different Spine Shaders but problem persists. Been reading the Straight Alpha/Premultiplied Alpha thread several times but not any wiser. Problem related somehow to color space as Gamma Color Space renders out Spine PMA without black borders, but the Linear space we are using creates this problem. Turning off sRBG on texture import settings also gets rid of the black borders, but creates a washed-out white overlay effect on the sprite instead. Being able to use PMA in linear color space would really help out.

If you've exported in the correct format and are using the correct shaders and it's still broken, there's not much on the Spine side that you can do at that point.

Spine doesn't any special form of PMA. This is why you have the freedom to use any PMA shader you choose.
We just bundle a simple one with the package so you can use it right away.

Likewise, you can render any PMA texture onto a mesh and use any PMA shader, or the Spine/Skeleton shader, and it would work exactly the same as if you were using a SkeletonAnimation/SkeletonRenderer.
The main thing Spine does is create an updated-per-frame mesh and manage the materials, and leaves the rendering implementation to Unity.

Have you tried using Straight Alpha blend mode instead?

Hey Pharan.

Yeah, straight alpha works fine and gets clean, nice artwork. I got hooked on the idea of using PMA after reading your write-up on it. This problem got me interested in why it did not work and if there was any good answer to why, but it is not a big loss if I am using straight alpha instead.

5 months later

I've been banging my head against this problem for some time now too


and it turned out that it was because we are also in Linear colorspace for a separate part of our project.

When you mention "Straight Alpha Blend Mode"


are you talking about a different shader? Exporting without PMA? I can't seem to find any option on the skeleton or shader list that suggests this.

Yes, I was talking about exporting the texture without Premultiplied Alpha, AND using a non-PMA shader, so you can use whatever shader you want.
Really, use whatever shader that works with your setup, because it's your setup and Linear colorspace was your decision. The requirement is only that your shader blending, and your texture export settings match.

If you're using animated colors too, you will need to enable or disable Premultiply Vertex Colors on your SkeletonAnimation accordingly.

Note that you can set the default shader on import in Unity Preferences... > Spine so you don't have to set the shader of the material every time you have a new skeleton to import.

Thanks, I had a few more speedbumps, but was able to resolve this. When selecting a straight Unlit Transparent shader, our character had several missing parts due to our artist scaling things negatively to flip them (after a bit of searching this seems to be advertised to be in the editor, but I can't find it for the life of me).

Either way, if anyone else runs into this issue, and wants a Straight Alpha Shader, I've made what seems to be the necessary one-line edit to the Spine Skeleton shader to provide that:

Shader "Spine/Skeleton (Straight)" {
 Properties {
     _Cutoff ("Shadow alpha cutoff", Range(0,1)) = 0.1
     [NoScaleOffset] _MainTex ("Main Texture", 2D) = "black" {}
 }

 SubShader {
     Tags { "Queue"="Transparent" "IgnoreProjector"="True" "RenderType"="Transparent" }

 Fog { Mode Off }
 Cull Off
 ZWrite Off
 Blend SrcAlpha OneMinusSrcAlpha
 Lighting Off

 Pass {
     Fog { Mode Off }
     ColorMaterial AmbientAndDiffuse
     SetTexture [_MainTex] {
         Combine texture * primary
     }
 }

 Pass {
     Name "Caster"
     Tags { "LightMode"="ShadowCaster" }
     Offset 1, 1
     ZWrite On
     ZTest LEqual

     Fog { Mode Off }
     Cull Off
     Lighting Off

     CGPROGRAM
     #pragma vertex vert
     #pragma fragment frag
     #pragma multi_compile_shadowcaster
     #pragma fragmentoption ARB_precision_hint_fastest
     #include "UnityCG.cginc"
     sampler2D _MainTex;
     fixed _Cutoff;

     struct v2f { 
         V2F_SHADOW_CASTER;
         float2  uv : TEXCOORD1;
     };

     v2f vert (appdata_base v) {
         v2f o;
         TRANSFER_SHADOW_CASTER(o)
         o.uv = v.texcoord;
         return o;
     }

     float4 frag (v2f i) : COLOR {
         fixed4 texcol = tex2D(_MainTex, i.uv);
         clip(texcol.a - _Cutoff);
         SHADOW_CASTER_FRAGMENT(i)
     }
     ENDCG
 }
 }

 SubShader {
     Tags { "Queue"="Transparent" "IgnoreProjector"="True" "RenderType"="Transparent" }

 Cull Off
 ZWrite Off
 Blend One OneMinusSrcAlpha
 Lighting Off

 Pass {
     ColorMaterial AmbientAndDiffuse
     SetTexture [_MainTex] {
         Combine texture * primary DOUBLE, texture * primary
     }
 }
 }
}