diff --git a/src/main/java/com/simibubi/create/content/contraptions/components/structureMovement/render/ContraptionProgram.java b/src/main/java/com/simibubi/create/content/contraptions/components/structureMovement/render/ContraptionProgram.java index 7f0950ca0..4a0a6ffad 100644 --- a/src/main/java/com/simibubi/create/content/contraptions/components/structureMovement/render/ContraptionProgram.java +++ b/src/main/java/com/simibubi/create/content/contraptions/components/structureMovement/render/ContraptionProgram.java @@ -1,5 +1,6 @@ package com.simibubi.create.content.contraptions.components.structureMovement.render; +import com.simibubi.create.foundation.render.backend.gl.shader.ProgramFogMode; import org.lwjgl.opengl.GL20; import com.simibubi.create.foundation.render.backend.gl.BasicProgram; @@ -15,8 +16,8 @@ public class ContraptionProgram extends BasicProgram { protected int uLightVolume; - public ContraptionProgram(ResourceLocation name, int handle) { - super(name, handle); + public ContraptionProgram(ResourceLocation name, int handle, ProgramFogMode.Factory fogFactory) { + super(name, handle, fogFactory); uLightBoxSize = getUniformLocation("uLightBoxSize"); uLightBoxMin = getUniformLocation("uLightBoxMin"); uModel = getUniformLocation("uModel"); diff --git a/src/main/java/com/simibubi/create/content/logistics/block/belts/tunnel/BeltTunnelBlock.java b/src/main/java/com/simibubi/create/content/logistics/block/belts/tunnel/BeltTunnelBlock.java index 334a15976..bd24f2271 100644 --- a/src/main/java/com/simibubi/create/content/logistics/block/belts/tunnel/BeltTunnelBlock.java +++ b/src/main/java/com/simibubi/create/content/logistics/block/belts/tunnel/BeltTunnelBlock.java @@ -26,6 +26,7 @@ import net.minecraft.util.Direction; import net.minecraft.util.Direction.Axis; import net.minecraft.util.Direction.AxisDirection; import net.minecraft.util.IStringSerializable; +import net.minecraft.util.Rotation; import net.minecraft.util.math.BlockPos; import net.minecraft.util.math.shapes.ISelectionContext; import net.minecraft.util.math.shapes.VoxelShape; @@ -211,6 +212,14 @@ public class BeltTunnelBlock extends Block implements ITE, return ActionResultType.SUCCESS; } + @Override + public BlockState rotate(BlockState state, Rotation rotation) { + Direction fromAxis = Direction.getFacingFromAxis(AxisDirection.POSITIVE, state.get(HORIZONTAL_AXIS)); + Direction rotated = rotation.rotate(fromAxis); + + return state.with(HORIZONTAL_AXIS, rotated.getAxis()); + } + @Override public void neighborChanged(BlockState state, World worldIn, BlockPos pos, Block blockIn, BlockPos fromPos, boolean isMoving) { diff --git a/src/main/java/com/simibubi/create/foundation/render/backend/Backend.java b/src/main/java/com/simibubi/create/foundation/render/backend/Backend.java index 5f53ee500..f495f3054 100644 --- a/src/main/java/com/simibubi/create/foundation/render/backend/Backend.java +++ b/src/main/java/com/simibubi/create/foundation/render/backend/Backend.java @@ -4,10 +4,14 @@ import java.io.BufferedInputStream; import java.io.IOException; import java.io.InputStream; import java.nio.FloatBuffer; +import java.util.EnumMap; import java.util.HashMap; import java.util.Map; import java.util.function.Predicate; +import com.simibubi.create.foundation.render.backend.gl.GlFog; +import com.simibubi.create.foundation.render.backend.gl.GlFogMode; +import com.simibubi.create.foundation.render.backend.gl.shader.*; import com.simibubi.create.foundation.render.backend.gl.versioned.GlFeatureCompat; import org.apache.logging.log4j.LogManager; import org.apache.logging.log4j.Logger; @@ -16,10 +20,6 @@ import org.lwjgl.opengl.GLCapabilities; import org.lwjgl.system.MemoryUtil; import com.simibubi.create.foundation.config.AllConfigs; -import com.simibubi.create.foundation.render.backend.gl.shader.GlProgram; -import com.simibubi.create.foundation.render.backend.gl.shader.GlShader; -import com.simibubi.create.foundation.render.backend.gl.shader.ProgramSpec; -import com.simibubi.create.foundation.render.backend.gl.shader.ShaderType; import net.minecraft.client.Minecraft; import net.minecraft.client.renderer.texture.TextureUtil; @@ -31,11 +31,13 @@ import net.minecraftforge.resource.ISelectiveResourceReloadListener; import net.minecraftforge.resource.VanillaResourceType; public class Backend { + public static final Boolean SHADER_DEBUG_OUTPUT = false; + public static final Logger log = LogManager.getLogger(Backend.class); public static final FloatBuffer MATRIX_BUFFER = MemoryUtil.memAllocFloat(16); private static final Map> registry = new HashMap<>(); - private static final Map, GlProgram> programs = new HashMap<>(); + private static final Map, ProgramGroup> programs = new HashMap<>(); private static boolean enabled; @@ -60,7 +62,7 @@ public class Backend { @SuppressWarnings("unchecked") public static

> P getProgram(S spec) { - return (P) programs.get(spec); + return (P) programs.get(spec).get(GlFog.getFogMode()); } public static boolean available() { @@ -109,7 +111,7 @@ public class Backend { if (gl20()) { - programs.values().forEach(GlProgram::delete); + programs.values().forEach(ProgramGroup::delete); programs.clear(); for (ProgramSpec shader : registry.values()) { loadProgram(manager, shader); @@ -123,23 +125,39 @@ public class Backend { } private static

> void loadProgram(IResourceManager manager, S programSpec) { - GlShader vert = null; - GlShader frag = null; try { - vert = loadShader(manager, programSpec.getVert(), ShaderType.VERTEX, programSpec.defines); - frag = loadShader(manager, programSpec.getFrag(), ShaderType.FRAGMENT, programSpec.defines); + Map programGroup = new EnumMap<>(GlFogMode.class); - GlProgram.Builder builder = GlProgram.builder(programSpec.name).attachShader(vert).attachShader(frag); + for (GlFogMode fogMode : GlFogMode.values()) { + programGroup.put(fogMode, loadProgram(manager, programSpec, fogMode)); + } - programSpec.attributes.forEach(builder::addAttribute); - - P program = builder.build(programSpec.factory); - - programs.put(programSpec, program); + programs.put(programSpec, new ProgramGroup<>(programGroup)); log.info("Loaded program {}", programSpec.name); } catch (IOException ex) { log.error("Failed to load program {}", programSpec.name, ex); + return; + } + } + + private static

> P loadProgram(IResourceManager manager, S programSpec, GlFogMode fogMode) throws IOException { + GlShader vert = null; + GlShader frag = null; + try { + ShaderConstants defines = new ShaderConstants(programSpec.defines); + + defines.defineAll(fogMode.getDefines()); + + vert = loadShader(manager, programSpec.getVert(), ShaderType.VERTEX, defines); + frag = loadShader(manager, programSpec.getFrag(), ShaderType.FRAGMENT, defines); + + GlProgram.Builder builder = GlProgram.builder(programSpec.name, fogMode).attachShader(vert).attachShader(frag); + + programSpec.attributes.forEach(builder::addAttribute); + + return builder.build(programSpec.factory); + } finally { if (vert != null) vert.delete(); if (frag != null) frag.delete(); diff --git a/src/main/java/com/simibubi/create/foundation/render/backend/gl/BasicProgram.java b/src/main/java/com/simibubi/create/foundation/render/backend/gl/BasicProgram.java index 2201626c1..bef778f9a 100644 --- a/src/main/java/com/simibubi/create/foundation/render/backend/gl/BasicProgram.java +++ b/src/main/java/com/simibubi/create/foundation/render/backend/gl/BasicProgram.java @@ -1,5 +1,6 @@ package com.simibubi.create.foundation.render.backend.gl; +import com.simibubi.create.foundation.render.backend.gl.shader.ProgramFogMode; import org.lwjgl.opengl.GL20; import com.simibubi.create.foundation.render.backend.Backend; @@ -14,20 +15,20 @@ public class BasicProgram extends GlProgram { protected final int uViewProjection; protected final int uDebug; protected final int uCameraPos; - protected final int uFogRange; - protected final int uFogColor; + + protected final ProgramFogMode fogMode; protected int uBlockAtlas; protected int uLightMap; - public BasicProgram(ResourceLocation name, int handle) { + public BasicProgram(ResourceLocation name, int handle, ProgramFogMode.Factory fogFactory) { super(name, handle); uTime = getUniformLocation("uTime"); uViewProjection = getUniformLocation("uViewProjection"); uDebug = getUniformLocation("uDebug"); uCameraPos = getUniformLocation("uCameraPos"); - uFogRange = getUniformLocation("uFogRange"); - uFogColor = getUniformLocation("uFogColor"); + + fogMode = fogFactory.create(this); bind(); registerSamplers(); @@ -48,8 +49,7 @@ public class BasicProgram extends GlProgram { uploadMatrixUniform(uViewProjection, viewProjection); GL20.glUniform3f(uCameraPos, (float) camX, (float) camY, (float) camZ); - GL20.glUniform2f(uFogRange, GlFog.getFogStart(), GlFog.getFogEnd()); - GL20.glUniform4fv(uFogColor, GlFog.FOG_COLOR); + fogMode.bind(); } protected static void uploadMatrixUniform(int uniform, Matrix4f mat) { diff --git a/src/main/java/com/simibubi/create/foundation/render/backend/gl/GlFog.java b/src/main/java/com/simibubi/create/foundation/render/backend/gl/GlFog.java index de7958b8c..c56a789a8 100644 --- a/src/main/java/com/simibubi/create/foundation/render/backend/gl/GlFog.java +++ b/src/main/java/com/simibubi/create/foundation/render/backend/gl/GlFog.java @@ -1,6 +1,7 @@ package com.simibubi.create.foundation.render.backend.gl; import com.mojang.blaze3d.platform.GlStateManager; +import org.lwjgl.opengl.GL11; public class GlFog { public static float[] FOG_COLOR = new float[] {0, 0, 0, 0}; @@ -9,7 +10,7 @@ public class GlFog { return GlStateManager.FOG.field_179049_a.field_179201_b; } - public static int getFogMode() { + public static int getFogModeGlEnum() { return GlStateManager.FOG.field_179047_b; } @@ -24,4 +25,22 @@ public class GlFog { public static float getFogStart() { return GlStateManager.FOG.field_179045_d; } + + public static GlFogMode getFogMode() { + if (!fogEnabled()) { + return GlFogMode.NONE; + } + + int mode = getFogModeGlEnum(); + + switch (mode) { + case GL11.GL_EXP2: + case GL11.GL_EXP: + return GlFogMode.EXP2; + case GL11.GL_LINEAR: + return GlFogMode.LINEAR; + default: + throw new UnsupportedOperationException("Unknown fog mode: " + mode); + } + } } diff --git a/src/main/java/com/simibubi/create/foundation/render/backend/gl/GlFogMode.java b/src/main/java/com/simibubi/create/foundation/render/backend/gl/GlFogMode.java new file mode 100644 index 000000000..996763bab --- /dev/null +++ b/src/main/java/com/simibubi/create/foundation/render/backend/gl/GlFogMode.java @@ -0,0 +1,39 @@ +package com.simibubi.create.foundation.render.backend.gl; + +import com.google.common.collect.Lists; +import com.simibubi.create.foundation.render.backend.gl.shader.GlShader; +import com.simibubi.create.foundation.render.backend.gl.shader.ProgramFogMode; +import org.lwjgl.opengl.GL11; + +import java.util.Collections; +import java.util.List; + +public enum GlFogMode { + NONE(ProgramFogMode.None::new), + LINEAR(ProgramFogMode.Linear::new, "USE_FOG_LINEAR"), + EXP2(ProgramFogMode.Exp2::new, "USE_FOG_EXP2"), + ; + + public static final String USE_FOG = "USE_FOG"; + + private final ProgramFogMode.Factory fogFactory; + private final List defines; + + GlFogMode(ProgramFogMode.Factory fogFactory) { + this.fogFactory = fogFactory; + this.defines = Collections.emptyList(); + } + + GlFogMode(ProgramFogMode.Factory fogFactory, String name) { + this.fogFactory = fogFactory; + this.defines = Lists.newArrayList(USE_FOG, name); + } + + public List getDefines() { + return defines; + } + + public ProgramFogMode.Factory getFogFactory() { + return fogFactory; + } +} diff --git a/src/main/java/com/simibubi/create/foundation/render/backend/gl/shader/GlProgram.java b/src/main/java/com/simibubi/create/foundation/render/backend/gl/shader/GlProgram.java index c911eea5f..09fdde86d 100644 --- a/src/main/java/com/simibubi/create/foundation/render/backend/gl/shader/GlProgram.java +++ b/src/main/java/com/simibubi/create/foundation/render/backend/gl/shader/GlProgram.java @@ -1,5 +1,6 @@ package com.simibubi.create.foundation.render.backend.gl.shader; +import com.simibubi.create.foundation.render.backend.gl.GlFogMode; import org.lwjgl.opengl.GL20; import com.simibubi.create.foundation.render.backend.Backend; @@ -17,8 +18,8 @@ public abstract class GlProgram extends GlObject { this.name = name; } - public static Builder builder(ResourceLocation name) { - return new Builder(name); + public static Builder builder(ResourceLocation name, GlFogMode fogMode) { + return new Builder(name, fogMode); } public void bind() { @@ -37,7 +38,7 @@ public abstract class GlProgram extends GlObject { public int getUniformLocation(String uniform) { int index = GL20.glGetUniformLocation(this.handle(), uniform); - if (index < 0) { + if (index < 0 && Backend.SHADER_DEBUG_OUTPUT) { Backend.log.warn("No active uniform '{}' exists in program '{}'. Could be unused.", uniform, this.name); } @@ -69,12 +70,14 @@ public abstract class GlProgram extends GlObject { public static class Builder { private final ResourceLocation name; private final int program; + private final GlFogMode fogMode; private int attributeIndex; - public Builder(ResourceLocation name) { + public Builder(ResourceLocation name, GlFogMode fogMode) { this.name = name; this.program = GL20.glCreateProgram(); + this.fogMode = fogMode; } public Builder attachShader(GlShader shader) { @@ -113,12 +116,12 @@ public abstract class GlProgram extends GlObject { throw new RuntimeException("Shader program linking failed, see log for details"); } - return factory.create(this.name, this.program); + return factory.create(this.name, this.program, this.fogMode.getFogFactory()); } } @FunctionalInterface public interface ProgramFactory

{ - P create(ResourceLocation name, int handle); + P create(ResourceLocation name, int handle, ProgramFogMode.Factory fogFactory); } } diff --git a/src/main/java/com/simibubi/create/foundation/render/backend/gl/shader/GlShader.java b/src/main/java/com/simibubi/create/foundation/render/backend/gl/shader/GlShader.java index 8ef265920..6f7076a18 100644 --- a/src/main/java/com/simibubi/create/foundation/render/backend/gl/shader/GlShader.java +++ b/src/main/java/com/simibubi/create/foundation/render/backend/gl/shader/GlShader.java @@ -19,7 +19,9 @@ public class GlShader extends GlObject { if (preProcessor != null) { source = preProcessor.process(source); - Backend.log.info("Preprocessor run on " + name);// + ":\n" + source); + + if (Backend.SHADER_DEBUG_OUTPUT) + Backend.log.info("Preprocessor run on " + name);// + ":\n" + source); } GL20.glShaderSource(handle, source); diff --git a/src/main/java/com/simibubi/create/foundation/render/backend/gl/shader/ProgramFogMode.java b/src/main/java/com/simibubi/create/foundation/render/backend/gl/shader/ProgramFogMode.java new file mode 100644 index 000000000..804aa5073 --- /dev/null +++ b/src/main/java/com/simibubi/create/foundation/render/backend/gl/shader/ProgramFogMode.java @@ -0,0 +1,57 @@ +package com.simibubi.create.foundation.render.backend.gl.shader; + +import com.simibubi.create.foundation.render.backend.gl.GlFog; +import org.lwjgl.opengl.GL20; + +public abstract class ProgramFogMode { + + public abstract void bind(); + + public static class None extends ProgramFogMode { + + public None(GlProgram program) { + + } + + @Override + public void bind() { + + } + } + + public static class Linear extends ProgramFogMode { + private final int uFogColor; + private final int uFogRange; + + public Linear(GlProgram program) { + this.uFogColor = program.getUniformLocation("uFogColor"); + this.uFogRange = program.getUniformLocation("uFogRange"); + } + + @Override + public void bind() { + GL20.glUniform2f(uFogRange, GlFog.getFogStart(), GlFog.getFogEnd()); + GL20.glUniform4fv(uFogColor, GlFog.FOG_COLOR); + } + } + + public static class Exp2 extends ProgramFogMode { + private final int uFogColor; + private final int uFogDensity; + + public Exp2(GlProgram program) { + this.uFogColor = program.getUniformLocation("uFogColor"); + this.uFogDensity = program.getUniformLocation("uFogDensity"); + } + + @Override + public void bind() { + GL20.glUniform1f(uFogDensity, GlFog.getFogDensity()); + GL20.glUniform4fv(uFogColor, GlFog.FOG_COLOR); + } + } + + public interface Factory { + ProgramFogMode create(GlProgram program); + } +} diff --git a/src/main/java/com/simibubi/create/foundation/render/backend/gl/shader/ProgramGroup.java b/src/main/java/com/simibubi/create/foundation/render/backend/gl/shader/ProgramGroup.java new file mode 100644 index 000000000..b31ae0237 --- /dev/null +++ b/src/main/java/com/simibubi/create/foundation/render/backend/gl/shader/ProgramGroup.java @@ -0,0 +1,22 @@ +package com.simibubi.create.foundation.render.backend.gl.shader; + +import com.simibubi.create.foundation.render.backend.gl.GlFogMode; + +import java.util.Map; + +public class ProgramGroup

{ + + private final Map programs; + + public ProgramGroup(Map programs) { + this.programs = programs; + } + + public P get(GlFogMode fogMode) { + return programs.get(fogMode); + } + + public void delete() { + programs.values().forEach(GlProgram::delete); + } +} diff --git a/src/main/java/com/simibubi/create/foundation/render/backend/gl/shader/ProgramSpec.java b/src/main/java/com/simibubi/create/foundation/render/backend/gl/shader/ProgramSpec.java index 7c2a2ca93..a7bc130af 100644 --- a/src/main/java/com/simibubi/create/foundation/render/backend/gl/shader/ProgramSpec.java +++ b/src/main/java/com/simibubi/create/foundation/render/backend/gl/shader/ProgramSpec.java @@ -50,7 +50,7 @@ public class ProgramSpec

{ public static class Builder

{ private ResourceLocation vert; private ResourceLocation frag; - private ShaderConstants defines = null; + private ShaderConstants defines = ShaderConstants.EMPTY; private final ResourceLocation name; private final GlProgram.ProgramFactory

factory; diff --git a/src/main/java/com/simibubi/create/foundation/render/backend/gl/shader/ShaderConstants.java b/src/main/java/com/simibubi/create/foundation/render/backend/gl/shader/ShaderConstants.java index 3f1ed6c09..9c509cc7d 100644 --- a/src/main/java/com/simibubi/create/foundation/render/backend/gl/shader/ShaderConstants.java +++ b/src/main/java/com/simibubi/create/foundation/render/backend/gl/shader/ShaderConstants.java @@ -1,12 +1,16 @@ package com.simibubi.create.foundation.render.backend.gl.shader; +import com.google.common.collect.Lists; + import java.io.BufferedReader; import java.io.StringReader; import java.util.ArrayList; +import java.util.Collection; import java.util.stream.Collectors; import java.util.stream.Stream; public class ShaderConstants implements GlShader.PreProcessor { + public static final ShaderConstants EMPTY = new ShaderConstants(); private final ArrayList defines; @@ -14,6 +18,10 @@ public class ShaderConstants implements GlShader.PreProcessor { defines = new ArrayList<>(); } + public ShaderConstants(ShaderConstants other) { + this.defines = Lists.newArrayList(other.defines); + } + public static ShaderConstants define(String def) { return new ShaderConstants().def(def); } @@ -23,6 +31,11 @@ public class ShaderConstants implements GlShader.PreProcessor { return this; } + public ShaderConstants defineAll(Collection defines) { + this.defines.addAll(defines); + return this; + } + public ArrayList getDefines() { return defines; } diff --git a/src/main/resources/assets/create/shader/belt.vert b/src/main/resources/assets/create/shader/belt.vert index c150f012b..14921cb7a 100644 --- a/src/main/resources/assets/create/shader/belt.vert +++ b/src/main/resources/assets/create/shader/belt.vert @@ -33,7 +33,10 @@ uniform mat4 uViewProjection; uniform int uDebug; uniform vec3 uCameraPos; + +#if defined(USE_FOG) varying float FragDistance; +#endif mat4 rotate(vec3 axis, float angle) { float s = sin(angle); @@ -71,12 +74,16 @@ void main() { mat4 normalMat = uModel * localRotation; BoxCoord = (worldPos.xyz - uLightBoxMin) / uLightBoxSize; + #if defined(USE_FOG) FragDistance = length(worldPos.xyz); + #endif #else mat4 normalMat = localRotation; + #if defined(USE_FOG) FragDistance = length(worldPos.xyz - uCameraPos); #endif + #endif vec3 norm = normalize(normalMat * vec4(aNormal, 0.)).xyz; diff --git a/src/main/resources/assets/create/shader/contraption.frag b/src/main/resources/assets/create/shader/contraption.frag index 5d90b40ff..9049221f1 100644 --- a/src/main/resources/assets/create/shader/contraption.frag +++ b/src/main/resources/assets/create/shader/contraption.frag @@ -4,17 +4,35 @@ varying vec2 TexCoords; varying vec4 Color; varying float Diffuse; varying vec2 Light; -varying float FragDistance; varying vec3 BoxCoord; -uniform vec2 uFogRange; -uniform vec4 uFogColor; - uniform sampler2D uBlockAtlas; uniform sampler2D uLightMap; uniform sampler3D uLightVolume; +#if defined(USE_FOG) +varying float FragDistance; +uniform vec4 uFogColor; +#endif + +#if defined(USE_FOG_LINEAR) +uniform vec2 uFogRange; + +float fogFactor() { + return (uFogRange.y - FragDistance) / (uFogRange.y - uFogRange.x); +} +#endif + +#ifdef USE_FOG_EXP2 +uniform float uFogDensity; + +float fogFactor() { + float dist = FragDistance * uFogDensity; + return 1. / exp2(dist * dist); +} +#endif + vec4 light() { vec2 lm = texture3D(uLightVolume, BoxCoord).rg * 0.9375 + 0.03125; return texture2D(uLightMap, max(lm, Light)); @@ -25,9 +43,12 @@ void main() { vec4 color = vec4(tex.rgb * light().rgb * Diffuse * Color.rgb, tex.a); - float fog = (uFogRange.y - FragDistance) / (uFogRange.y - uFogRange.x); - fog = clamp(fog, 0., 1.); +#if defined(USE_FOG) + float fog = clamp(fogFactor(), 0., 1.); gl_FragColor = mix(uFogColor, color, fog); gl_FragColor.a = color.a; +#else + gl_FragColor = color; +#endif } \ No newline at end of file diff --git a/src/main/resources/assets/create/shader/contraption_actor.vert b/src/main/resources/assets/create/shader/contraption_actor.vert index 7dbae771c..cc31d18ed 100644 --- a/src/main/resources/assets/create/shader/contraption_actor.vert +++ b/src/main/resources/assets/create/shader/contraption_actor.vert @@ -29,7 +29,10 @@ uniform mat4 uViewProjection; uniform int uDebug; uniform vec3 uCameraPos; + +#if defined(USE_FOG) varying float FragDistance; +#endif mat4 rotate(vec3 axis, float angle) { float s = sin(angle); @@ -77,9 +80,12 @@ void main() { Diffuse = diffuse(norm); TexCoords = aTexCoords; Light = aModelLight; - FragDistance = length(worldPos.xyz); gl_Position = uViewProjection * worldPos; + #if defined(USE_FOG) + FragDistance = length(worldPos.xyz); + #endif + if (uDebug == 2) { Color = vec4(norm, 1.); } else { diff --git a/src/main/resources/assets/create/shader/contraption_structure.vert b/src/main/resources/assets/create/shader/contraption_structure.vert index a665ea8ff..0e053db27 100644 --- a/src/main/resources/assets/create/shader/contraption_structure.vert +++ b/src/main/resources/assets/create/shader/contraption_structure.vert @@ -22,7 +22,10 @@ uniform mat4 uViewProjection; uniform int uDebug; uniform vec3 uCameraPos; + +#if defined(USE_FOG) varying float FragDistance; +#endif mat4 rotate(vec3 axis, float angle) { float s = sin(angle); @@ -52,8 +55,10 @@ void main() { Color = aColor / diffuse(aNormal); TexCoords = aTexCoords; Light = aModelLight; - FragDistance = length(viewPos.xyz); gl_Position = uViewProjection * viewPos; + #if defined(USE_FOG) + FragDistance = length(viewPos.xyz); + #endif if (uDebug == 2) { Color = vec4(norm, 1.); diff --git a/src/main/resources/assets/create/shader/flap.vert b/src/main/resources/assets/create/shader/flap.vert index bd982595d..a70fdf1ad 100644 --- a/src/main/resources/assets/create/shader/flap.vert +++ b/src/main/resources/assets/create/shader/flap.vert @@ -35,7 +35,10 @@ uniform mat4 uViewProjection; uniform int uDebug; uniform vec3 uCameraPos; + +#if defined(USE_FOG) varying float FragDistance; +#endif float diffuse(vec3 normal) { float x = normal.x; @@ -86,12 +89,16 @@ void main() { mat4 normalMat = uModel * orientation * flapRotation; BoxCoord = (worldPos.xyz - uLightBoxMin) / uLightBoxSize; + #if defined(USE_FOG) FragDistance = length(worldPos.xyz); + #endif #else mat4 normalMat = orientation * flapRotation; + #if defined(USE_FOG) FragDistance = length(worldPos.xyz - uCameraPos); #endif + #endif vec3 norm = normalize(normalMat * vec4(aNormal, 0.)).xyz; diff --git a/src/main/resources/assets/create/shader/instanced.frag b/src/main/resources/assets/create/shader/instanced.frag index cb85241f5..e8ffaa00c 100644 --- a/src/main/resources/assets/create/shader/instanced.frag +++ b/src/main/resources/assets/create/shader/instanced.frag @@ -4,14 +4,32 @@ varying vec2 TexCoords; varying vec2 Light; varying float Diffuse; varying vec4 Color; -varying float FragDistance; - -uniform vec2 uFogRange; -uniform vec4 uFogColor; uniform sampler2D uBlockAtlas; uniform sampler2D uLightMap; +#if defined(USE_FOG) +varying float FragDistance; +uniform vec4 uFogColor; +#endif + +#if defined(USE_FOG_LINEAR) +uniform vec2 uFogRange; + +float fogFactor() { + return (uFogRange.y - FragDistance) / (uFogRange.y - uFogRange.x); +} +#endif + +#ifdef USE_FOG_EXP2 +uniform float uFogDensity; + +float fogFactor() { + float dist = FragDistance * uFogDensity; + return 1. / exp2(dist * dist); +} +#endif + vec4 light() { vec2 lm = Light * 0.9375 + 0.03125; return texture2D(uLightMap, lm); @@ -22,9 +40,12 @@ void main() { vec4 color = vec4(tex.rgb * light().rgb * Diffuse, tex.a) * Color; - float fog = (uFogRange.y - FragDistance) / (uFogRange.y - uFogRange.x); - fog = clamp(fog, 0., 1.); +#if defined(USE_FOG) + float fog = clamp(fogFactor(), 0., 1.); gl_FragColor = mix(uFogColor, color, fog); gl_FragColor.a = color.a; +#else + gl_FragColor = color; +#endif } \ No newline at end of file diff --git a/src/main/resources/assets/create/shader/rotating.vert b/src/main/resources/assets/create/shader/rotating.vert index a1f803139..afa32c38c 100644 --- a/src/main/resources/assets/create/shader/rotating.vert +++ b/src/main/resources/assets/create/shader/rotating.vert @@ -29,7 +29,10 @@ uniform mat4 uViewProjection; uniform int uDebug; uniform vec3 uCameraPos; + +#if defined(USE_FOG) varying float FragDistance; +#endif mat4 rotate(vec3 axis, float angle) { float s = sin(angle); @@ -69,12 +72,16 @@ void main() { mat4 normalMat = uModel * kineticRotation; BoxCoord = (worldPos.xyz - uLightBoxMin) / uLightBoxSize; + #if defined(USE_FOG) FragDistance = length(worldPos.xyz); + #endif #else mat4 normalMat = kineticRotation; + #if defined(USE_FOG) FragDistance = length(worldPos.xyz - uCameraPos); #endif + #endif vec3 norm = normalize(normalMat * vec4(aNormal, 0.)).xyz;