#ifndef FOGCOLOR_DECLARED
#define FOGCOLOR_DECLARED
uniform vec3 fogColor;
#endif

vec4 netherNether  = vec4(vec3(NETHER_NR, NETHER_NG, NETHER_NB) / 255.0, 1.0) * NETHER_NI;
vec4 netherValley  = vec4(vec3(NETHER_VR, NETHER_VG, NETHER_VB) / 255.0, 1.0) * NETHER_VI;
vec4 netherCrimson = vec4(vec3(NETHER_CR, NETHER_CG, NETHER_CB) / 255.0, 1.0) * NETHER_CI;
vec4 netherWarped  = vec4(vec3(NETHER_WR, NETHER_WG, NETHER_WB) / 255.0, 1.0) * NETHER_WI;
vec4 netherBasalt  = vec4(vec3(NETHER_BR, NETHER_BG, NETHER_BB) / 255.0, 1.0) * NETHER_BI;

#ifdef NETHER_VANILLA
vec4 netherColSqrt = vec4(normalize(fogColor + 0.0001), length(fogColor));
#else
#ifdef WEATHER_PERBIOME
uniform float isValley, isCrimson, isWarped, isBasalt;
float nBiomeWeight = isValley + isCrimson + isWarped + isBasalt;

vec4 netherColSqrt = mix(
    netherNether,
    (
        netherValley  * isValley  + netherCrimson * isCrimson +
        netherWarped  * isWarped  + netherBasalt  * isBasalt
    ) / max(nBiomeWeight, 0.0001),
    nBiomeWeight
);
#else
vec4 netherColSqrt = netherNether;
#endif
#endif

// ===== Modded Nether biome recoloring (fogColor-based detection) =====
// Each biome gets its own match radius: tight where its fog is near a vanilla biome
// (so it doesn't bleed), wide where its fog is isolated (so blended/edge fog still
// registers). Disabled biomes contribute weight 0.
#ifdef NETHER_SBR
float wSBR = 1.0 - smoothstep(0.150, 0.300, distance(fogColor, vec3(154.0, 144.0,  49.0) / 255.0));
#else
float wSBR = 0.0;
#endif
#ifdef NETHER_BNR
float wBNR = 1.0 - smoothstep(0.210, 0.420, distance(fogColor, vec3( 47.0, 221.0, 202.0) / 255.0));
#else
float wBNR = 0.0;
#endif
#ifdef NETHER_JUN
float wJUN = 1.0 - smoothstep(0.110, 0.200, distance(fogColor, vec3( 62.0, 169.0,  61.0) / 255.0));
#else
float wJUN = 0.0;
#endif
#ifdef NETHER_UDF
float wUDF = 1.0 - smoothstep(0.150, 0.300, distance(fogColor, vec3(111.0, 188.0, 111.0) / 255.0));
#else
float wUDF = 0.0;
#endif
#ifdef NETHER_BBN
float wBBN = 1.0 - smoothstep(0.033, 0.060, distance(fogColor, vec3(  6.0,   9.0,  27.0) / 255.0));
#else
float wBBN = 0.0;
#endif
#ifdef NETHER_GLM
float wGLM = 1.0 - smoothstep(0.084, 0.152, distance(fogColor, vec3( 66.0,  12.0, 104.0) / 255.0));
#else
float wGLM = 0.0;
#endif
#ifdef NETHER_MYC
float wMYC = 1.0 - smoothstep(0.070, 0.130, distance(fogColor, vec3(163.0, 139.0,  36.0) / 255.0));
#else
float wMYC = 0.0;
#endif

float wMax = max(max(max(wSBR, wBNR), max(wJUN, wUDF)), max(max(wBBN, wGLM), wMYC));

// Winner (biome with the highest match weight) supplies the color + influence.
vec3 mbColor =
    (wMax > 0.0 && wMax == wSBR) ? vec3(NETHER_SBR_R, NETHER_SBR_G, NETHER_SBR_B) / 255.0 * NETHER_SBR_I :
    (wMax > 0.0 && wMax == wBNR) ? vec3(NETHER_BNR_R, NETHER_BNR_G, NETHER_BNR_B) / 255.0 * NETHER_BNR_I :
    (wMax > 0.0 && wMax == wJUN) ? vec3(NETHER_JUN_R, NETHER_JUN_G, NETHER_JUN_B) / 255.0 * NETHER_JUN_I :
    (wMax > 0.0 && wMax == wUDF) ? vec3(NETHER_UDF_R, NETHER_UDF_G, NETHER_UDF_B) / 255.0 * NETHER_UDF_I :
    (wMax > 0.0 && wMax == wBBN) ? vec3(NETHER_BBN_R, NETHER_BBN_G, NETHER_BBN_B) / 255.0 * NETHER_BBN_I :
    (wMax > 0.0 && wMax == wGLM) ? vec3(NETHER_GLM_R, NETHER_GLM_G, NETHER_GLM_B) / 255.0 * NETHER_GLM_I :
                                   vec3(NETHER_MYC_R, NETHER_MYC_G, NETHER_MYC_B) / 255.0 * NETHER_MYC_I ;
float mbInf =
    (wMax > 0.0 && wMax == wSBR) ? float(NETHER_SBR_INF) :
    (wMax > 0.0 && wMax == wBNR) ? float(NETHER_BNR_INF) :
    (wMax > 0.0 && wMax == wJUN) ? float(NETHER_JUN_INF) :
    (wMax > 0.0 && wMax == wUDF) ? float(NETHER_UDF_INF) :
    (wMax > 0.0 && wMax == wBBN) ? float(NETHER_BBN_INF) :
    (wMax > 0.0 && wMax == wGLM) ? float(NETHER_GLM_INF) :
                                   float(NETHER_MYC_INF) ;

// Influence blends the user's color with the biome's real (vanilla) fog color.
float mbInfF = clamp(mbInf / 100.0, 0.0, 1.0);
vec3 mbApplied = mix(fogColor, mbColor, mbInfF);
float mbMatch = clamp(wMax, 0.0, 1.0);
vec3 netherSqrtFinal = mix(netherColSqrt.rgb, mbApplied, mbMatch);
vec4 netherCol = vec4(netherSqrtFinal * netherSqrtFinal, netherColSqrt.a * netherColSqrt.a);
