#include "/Lib/Settings.glsl" #include "/Lib/Utilities.glsl" // MinecraftPT — GbufferData structures #ifndef GBUFFER_DATA_GLSL #define GBUFFER_DATA_GLSL struct Material{ float roughness; float metalness; float emissiveness; float scattering; float reflectionStrength; }; struct GbufferData{ vec3 albedo; float albedoAlpha; vec3 worldNormal; vec3 vertexNormal; vec2 lightmap; float materialID; float parallaxShadow; Material material; }; // Standard material defaults #define material_air Material(1.0, 0.0, 0.0, 0.0, 0.0); #define material_water Material(0.0, 0.018, 0.0, 0.0, 1.0); #define material_glass Material(0.0, 0.04, 0.0, 0.0, 1.0); // Material IDs (written to GBuffer) #define MATID_DEFAULT 0.0 #define MATID_WATER 1.0 #define MATID_STAINEDGLASS 2.0 #define MATID_LEAVES 3.0 #define MATID_GRASS 4.0 // cross plant #define MATID_HAND 5.0 #define MATID_ENTITIES 6.0 #define MATID_ENTITIES_PLAYER 7.0 #define MATID_ENTITIES_SNOW 8.0 #define MATID_LIGHTNING 9.0 #define MATID_SKY 10.0 #define MATID_TORCH 11.0 #define MATID_FIRE 12.0 #define MATID_ENDROD 13.0 #define MATID_AMETHYST 14.0 #define MATID_SOULTORCH 15.0 #define MATID_REDSTONE_TORCH 16.0 #define MATID_PARTICLE 17.0 #define MATID_END_PORTAL 18.0 #define MATID_SELECTION 19.0 #define MATID_COPPER_LANTERN 20.0 #define MATID_BEACON_BEAM 21.0 // Material from specular texture (LAB PBR) Material MaterialFromTex(vec4 specTex){ Material material; material.roughness = 1.0 - specTex.r; material.roughness = material.roughness * material.roughness; material.metalness = specTex.g; material.reflectionStrength = saturate(material.roughness < 0.1 ? 1.0 : pow(specTex.r, 0.2)); material.reflectionStrength = saturate(material.reflectionStrength + material.metalness); material.metalness = max(material.metalness, 0.04); material.emissiveness = specTex.a; material.scattering = 0.0; return material; } // Predefined metal F0 values (from LAB PBR spec) vec3 PredefinedMetalF0(float index){ vec3 f0 = vec3(0.0); if (abs(index - 230.0 / 255.0) < 2e-4){ f0 = vec3(0.56, 0.58, 0.58); // Iron }else if (abs(index - 231.0 / 255.0) < 2e-4){ f0 = vec3(1.00, 0.69, 0.28); // Gold }else if (abs(index - 232.0 / 255.0) < 2e-4){ f0 = vec3(0.81, 0.82, 0.83); // Aluminum }else if (abs(index - 233.0 / 255.0) < 2e-4){ f0 = vec3(0.50, 0.49, 0.49); // Chromium }else if (abs(index - 234.0 / 255.0) < 2e-4){ f0 = vec3(0.95, 0.52, 0.35); // Copper }else if (abs(index - 235.0 / 255.0) < 2e-4){ f0 = vec3(0.81, 0.83, 0.87); // Lead }else if (abs(index - 236.0 / 255.0) < 2e-4){ f0 = vec3(0.66, 0.63, 0.58); // Platinum }else if (abs(index - 237.0 / 255.0) < 2e-4){ f0 = vec3(0.95, 0.91, 0.81); // Silver } return f0; } // Read solid GBuffer data GbufferData GetGbufferDataSoild(ivec2 texelCoord){ GbufferData data; vec4 gbuffer2 = texelFetch(colortex2, texelCoord, 0); vec4 gbuffer3 = texelFetch(colortex3, texelCoord, 0); data.albedo = GammaToLinear(texelFetch(colortex0, texelCoord, 0).rgb); data.albedoAlpha = 1.0; data.worldNormal = DecodeNormal(texelFetch(colortex1, texelCoord, 0).xy); data.vertexNormal = DecodeNormal(texelFetch(colortex1, texelCoord, 0).zw); data.lightmap = gbuffer3.xy; data.materialID = gbuffer2.a; data.parallaxShadow = gbuffer3.b; vec4 specTex = vec4(gbuffer2.r, gbuffer2.g, gbuffer2.b, 0.0); data.material = MaterialFromTex(specTex); return data; } // Read translucent GBuffer data GbufferData GetGbufferDataTranslucent(ivec2 texelCoord, out bool isSmooth){ GbufferData data; vec4 gbuffer5 = texelFetch(colortex5, texelCoord, 0); vec4 gbuffer6 = texelFetch(colortex6, texelCoord, 0); data.worldNormal = DecodeNormal(gbuffer6.xy); data.vertexNormal = DecodeNormal(gbuffer6.zw); data.lightmap = texelFetch(colortex7, texelCoord, 0).xy; data.materialID = gbuffer6.a; data.parallaxShadow = 1.0; isSmooth = false; if (data.materialID == MATID_WATER){ data.albedo = GammaToLinear(gbuffer5.rgb); data.albedoAlpha = gbuffer5.a; data.material = material_water; isSmooth = true; }else if (data.materialID == MATID_STAINEDGLASS){ data.albedo = GammaToLinear(gbuffer5.rgb); data.albedoAlpha = gbuffer5.a; data.material = material_glass; isSmooth = true; }else if (data.materialID == MATID_PARTICLE){ data.albedo = GammaToLinear(gbuffer5.rgb); data.albedoAlpha = gbuffer5.a; data.material = material_air; }else{ data.albedo = GammaToLinear(texelFetch(colortex0, texelCoord, 0).rgb); data.albedoAlpha = 1.0; vec4 specTex = vec4(gbuffer2.r, gbuffer2.g, gbuffer2.b, 0.0); data.material = MaterialFromTex(specTex); } return data; } // Material mask utilities struct MaterialMask{ float sky; float grass; float leaves; float hand; float entityPlayer; float water; float stainedGlass; float lightning; float entitiesSnow; float endrod; float fire; float torch; float lightSource; float redstoneTorch; float soulTorch; float amethyst; float particle; float endPortal; float selection; }; MaterialMask CalculateMasks(float materialIDs){ MaterialMask mask; mask.sky = float(materialIDs == MATID_SKY); mask.grass = float(materialIDs == MATID_GRASS || materialIDs == MATID_BEACON_BEAM); mask.leaves = float(materialIDs == MATID_LEAVES); mask.hand = float(materialIDs == MATID_HAND); mask.water = float(materialIDs == MATID_WATER); mask.stainedGlass = float(materialIDs == MATID_STAINEDGLASS); mask.entityPlayer = float(materialIDs == MATID_ENTITIES_PLAYER); mask.entitiesSnow = float(materialIDs == MATID_ENTITIES_SNOW || materialIDs == MATID_BEACON_BEAM); mask.lightning = float(materialIDs == MATID_LIGHTNING); mask.endrod = float(materialIDs == MATID_ENDROD); mask.fire = float(materialIDs == MATID_FIRE); mask.torch = float(materialIDs == MATID_TORCH); mask.redstoneTorch = float(materialIDs == MATID_REDSTONE_TORCH); mask.amethyst = float(materialIDs == MATID_AMETHYST); mask.soulTorch = float(materialIDs == MATID_SOULTORCH || materialIDs == MATID_COPPER_LANTERN); mask.particle = float(materialIDs == MATID_PARTICLE); mask.endPortal = float(materialIDs == MATID_END_PORTAL); mask.selection = float(materialIDs == MATID_SELECTION); return mask; } void ApplyMaterial(inout Material material, in MaterialMask materialMask, inout bool isSmooth){ if (materialMask.water > 0.5){ material = material_water; isSmooth = true; }else if (materialMask.stainedGlass > 0.5){ material = material_glass; isSmooth = true; } } #endif