#version 330 core
out vec4 FragColor;

in vec4 vsColor;
in vec2 vsTexCoord;
in vec3 vsFragPos;
in vec3 vsNormal;

uniform sampler2D texSDF;

// uniforms for font color, outlining, and drop shadows / glow
uniform vec4 fontColor    = vec4( 1.0, 1.0, 1.0, 1.0 ); // All .a channels handled as 1.0 unless transparency is supported
uniform vec4 outlineColor = vec4( 0.0, 1.0, 0.0, 1.0 ); // Same as the vsColor.a usually 1.0
uniform vec4 glowColor    = vec4( 0.0, 0.0, 1.0, 1.0 ); // Transparent shapes not being dealt with in June 2025

uniform bool isSoftEdges = false;
uniform bool isOutline   = false;
uniform bool isOuterGlow = false;

uniform float fontEdgeVal       = 0.50;  // Value of SDF texture where the sharp edge of the font should appear.  Size of the font.  0 (large) - 0.5.
uniform float antiAliasRange    = 0.005; // Antialiasing range +/- for Hermitian interpolation upper / lower bound
uniform float outlineInEdgeVal  = 0.51;  // Inner size of the outline. 0 (max size) - 0.51 (slight font overlap)
uniform float outlineThick      = 0.02;  // Outline thickness, 0 = no outline, 0.5 = large outline (subtract from InEdge and clips at 0.0)
uniform float glowEdgeVal       = 0.43;  // Size of the glow/shadow, same as fontEdge, 0 = large glow, 0.5 = small glow
uniform float glowRange         = 0.125; // Value of SDF texture where the glow should appear. Usually between 0 and 0.5 (to >= font edge)
uniform vec2  glowOffset        = vec2( 0.0, 0.0 ); // Between 0 and spread / textureSize

void main(){
    vec4 baseColor      = fontColor;
    float distAlphaMask = texture( texSDF, vsTexCoord.xy ).a;

    if( isSoftEdges ){
        float softEdgeMin  = fontEdgeVal - antiAliasRange;
        float softEdgeMax  = fontEdgeVal + antiAliasRange;
        baseColor.a *= smoothstep( softEdgeMin, softEdgeMax, distAlphaMask );
    } else {
        if( distAlphaMask >= fontEdgeVal ){ baseColor.a *= 1.0; }
        else                              { baseColor.a  = 0.0; }
    }

    if( isOutline ){
        float outlineOutEdgeValue = outlineInEdgeVal    - outlineThick;
        float outlineMaxValue0    = outlineInEdgeVal    - antiAliasRange;
        float outlineMaxValue1    = outlineInEdgeVal    + antiAliasRange;
        float outlineMinValue0    = outlineOutEdgeValue - antiAliasRange;
        float outlineMinValue1    = outlineOutEdgeValue + antiAliasRange;
        if( ( distAlphaMask >= outlineMinValue0 ) && ( distAlphaMask <= outlineMaxValue1 ) ){
            float outlineAlpha = 1.0;
            if( distAlphaMask <= outlineMinValue1 ){
                outlineAlpha = smoothstep( outlineMinValue0, outlineMinValue1, distAlphaMask );
            } else {
                outlineAlpha = smoothstep( outlineMaxValue1, outlineMaxValue0, distAlphaMask );
            }
            baseColor = mix( baseColor, outlineColor, outlineAlpha );
            //baseColor = vec4( mix( baseColor.rgb, outlineColor.rgb, outlineAlpha ), max( baseColor.a, outlineAlpha ) );
        }
    }

    if( isOuterGlow ){
        float outerGlowMinValue = glowEdgeVal - glowRange;
        float outerGlowMaxValue = glowEdgeVal + glowRange;
        float glowAlpha = texture( texSDF, vsTexCoord.xy + glowOffset.xy ).a;
        vec4 glowc     = vec4( glowColor.rgb, glowColor.a * smoothstep( outerGlowMinValue, outerGlowMaxValue, glowAlpha ) );
        //baseColor      = mix( glowc, baseColor, baseColor.a );
        baseColor      = vec4( mix( glowc.rgb, baseColor.rgb, baseColor.a ), max( glowc.a, baseColor.a ) );
        //baseColor      = glowc * ( 1.0 - baseColor.a ) + baseColor * baseColor.a;
    }

    if( baseColor.a < 0.02 ){ discard; }

    gl_FragColor = baseColor;
}