From a6248daf7eb271315db5a1aaeb8f44f91716cfc3 Mon Sep 17 00:00:00 2001 From: JozsefA Date: Sat, 17 Apr 2021 18:55:29 -0700 Subject: [PATCH] Better spheres and framebuffer compat layer --- .../backend/effects/EffectsHandler.java | 20 ++++--- .../gl/versioned/framebuffer/Blit.java | 45 +++++++++++++++ .../gl/versioned/framebuffer/Framebuffer.java | 57 +++++++++++++++++++ .../create/flywheel/shaders/area_effect.frag | 22 +++---- 4 files changed, 124 insertions(+), 20 deletions(-) create mode 100644 src/main/java/com/simibubi/create/foundation/render/backend/gl/versioned/framebuffer/Blit.java create mode 100644 src/main/java/com/simibubi/create/foundation/render/backend/gl/versioned/framebuffer/Framebuffer.java diff --git a/src/main/java/com/simibubi/create/foundation/render/backend/effects/EffectsHandler.java b/src/main/java/com/simibubi/create/foundation/render/backend/effects/EffectsHandler.java index d3f7f4e06..749b2ca57 100644 --- a/src/main/java/com/simibubi/create/foundation/render/backend/effects/EffectsHandler.java +++ b/src/main/java/com/simibubi/create/foundation/render/backend/effects/EffectsHandler.java @@ -1,5 +1,6 @@ package com.simibubi.create.foundation.render.backend.effects; +import org.lwjgl.opengl.GL11; import org.lwjgl.opengl.GL15; import org.lwjgl.opengl.GL20; import org.lwjgl.opengl.GL30; @@ -87,8 +88,8 @@ public class EffectsHandler { Framebuffer mainBuffer = Minecraft.getInstance().getFramebuffer(); - GL30.glBindFramebuffer(FramebufferConstants.FRAME_BUFFER, framebuffer.framebufferObject); - GL30.glClear(GL30.GL_COLOR_BUFFER_BIT); + Backend.compat.fbo.bindFramebuffer(FramebufferConstants.FRAME_BUFFER, framebuffer.framebufferObject); + GL11.glClear(GL30.GL_COLOR_BUFFER_BIT); SphereFilterProgram program = Backend.getProgram(AllProgramSpecs.CHROMATIC); program.bind(); @@ -106,7 +107,7 @@ public class EffectsHandler { inverseView.invert(); program.bindInverseView(inverseView); - Vector3d pos1 = new Vector3d(852, 79, -204); + Vector3d pos1 = new Vector3d(865.5, 79, -240.5); Vector3d cameraPos = gameRenderer.getActiveRenderInfo().getProjectedView(); program.setCameraPos(cameraPos.inverse()); @@ -126,8 +127,9 @@ public class EffectsHandler { program.addSphere(new SphereFilterProgram.FilterSphere() .setCenter(pos1.subtract(cameraPos)) - .setRadius(40) - .setFeather(20f) + .setRadius(10f) + .setFeather(3f) + .setFade(1.5f) .setHsv(false) .setFilter(filter)); @@ -147,10 +149,10 @@ public class EffectsHandler { program.clear(); program.unbind(); - GL30.glBindFramebuffer(GL30.GL_READ_FRAMEBUFFER, framebuffer.framebufferObject); - GL30.glBindFramebuffer(GL30.GL_DRAW_FRAMEBUFFER, mainBuffer.framebufferObject); - GL30.glBlitFramebuffer(0, 0, mainBuffer.framebufferWidth, mainBuffer.framebufferHeight, 0, 0, mainBuffer.framebufferWidth, mainBuffer.framebufferHeight, GL30.GL_COLOR_BUFFER_BIT, GL20.GL_LINEAR); - GL30.glBindFramebuffer(FramebufferConstants.FRAME_BUFFER, mainBuffer.framebufferObject); + Backend.compat.fbo.bindFramebuffer(GL30.GL_READ_FRAMEBUFFER, framebuffer.framebufferObject); + Backend.compat.fbo.bindFramebuffer(GL30.GL_DRAW_FRAMEBUFFER, mainBuffer.framebufferObject); + Backend.compat.blit.blitFramebuffer(0, 0, mainBuffer.framebufferWidth, mainBuffer.framebufferHeight, 0, 0, mainBuffer.framebufferWidth, mainBuffer.framebufferHeight, GL30.GL_COLOR_BUFFER_BIT, GL20.GL_LINEAR); + Backend.compat.fbo.bindFramebuffer(FramebufferConstants.FRAME_BUFFER, mainBuffer.framebufferObject); } public void delete() { diff --git a/src/main/java/com/simibubi/create/foundation/render/backend/gl/versioned/framebuffer/Blit.java b/src/main/java/com/simibubi/create/foundation/render/backend/gl/versioned/framebuffer/Blit.java new file mode 100644 index 000000000..b5809fa29 --- /dev/null +++ b/src/main/java/com/simibubi/create/foundation/render/backend/gl/versioned/framebuffer/Blit.java @@ -0,0 +1,45 @@ +package com.simibubi.create.foundation.render.backend.gl.versioned.framebuffer; + +import org.lwjgl.opengl.EXTFramebufferBlit; +import org.lwjgl.opengl.GL30; +import org.lwjgl.opengl.GLCapabilities; + +import com.simibubi.create.foundation.render.backend.gl.versioned.GlVersioned; + +public enum Blit implements GlVersioned { + CORE { + @Override + public boolean supported(GLCapabilities caps) { + return caps.OpenGL30; + } + + @Override + public void blitFramebuffer(int srcX0, int srcY0, int srcX1, int srcY1, int dstX0, int dstY0, int dstX1, int dstY1, int mask, int filter) { + GL30.glBlitFramebuffer(srcX0, srcY0, srcX1, srcY1, dstX0, dstY0, dstX1, dstY1, mask, filter); + } + }, + EXT { + @Override + public boolean supported(GLCapabilities caps) { + return caps.GL_EXT_framebuffer_blit; + } + + @Override + public void blitFramebuffer(int srcX0, int srcY0, int srcX1, int srcY1, int dstX0, int dstY0, int dstX1, int dstY1, int mask, int filter) { + EXTFramebufferBlit.glBlitFramebufferEXT(srcX0, srcY0, srcX1, srcY1, dstX0, dstY0, dstX1, dstY1, mask, filter); + } + }, + UNSUPPORTED { + @Override + public boolean supported(GLCapabilities caps) { + return true; + } + + @Override + public void blitFramebuffer(int srcX0, int srcY0, int srcX1, int srcY1, int dstX0, int dstY0, int dstX1, int dstY1, int mask, int filter) { + throw new UnsupportedOperationException("Framebuffer blitting not supported."); + } + }; + + public abstract void blitFramebuffer(int srcX0, int srcY0, int srcX1, int srcY1, int dstX0, int dstY0, int dstX1, int dstY1, int mask, int filter); +} diff --git a/src/main/java/com/simibubi/create/foundation/render/backend/gl/versioned/framebuffer/Framebuffer.java b/src/main/java/com/simibubi/create/foundation/render/backend/gl/versioned/framebuffer/Framebuffer.java new file mode 100644 index 000000000..02b64c8d5 --- /dev/null +++ b/src/main/java/com/simibubi/create/foundation/render/backend/gl/versioned/framebuffer/Framebuffer.java @@ -0,0 +1,57 @@ +package com.simibubi.create.foundation.render.backend.gl.versioned.framebuffer; + +import org.lwjgl.opengl.ARBFramebufferObject; +import org.lwjgl.opengl.EXTFramebufferObject; +import org.lwjgl.opengl.GL30C; +import org.lwjgl.opengl.GLCapabilities; + +import com.simibubi.create.foundation.render.backend.gl.versioned.GlVersioned; + +public enum Framebuffer implements GlVersioned { + CORE { + @Override + public boolean supported(GLCapabilities caps) { + return caps.OpenGL30; + } + + @Override + public void bindFramebuffer(int target, int framebuffer) { + GL30C.glBindFramebuffer(target, framebuffer); + } + }, + ARB { + @Override + public boolean supported(GLCapabilities caps) { + return caps.GL_ARB_framebuffer_object; + } + + @Override + public void bindFramebuffer(int target, int framebuffer) { + ARBFramebufferObject.glBindFramebuffer(target, framebuffer); + } + }, + EXT { + @Override + public boolean supported(GLCapabilities caps) { + return caps.GL_EXT_framebuffer_object; + } + + @Override + public void bindFramebuffer(int target, int framebuffer) { + EXTFramebufferObject.glBindFramebufferEXT(target, framebuffer); + } + }, + UNSUPPORTED { + @Override + public boolean supported(GLCapabilities caps) { + return true; + } + + @Override + public void bindFramebuffer(int target, int framebuffer) { + throw new UnsupportedOperationException("Framebuffers not supported"); + } + }; + + public abstract void bindFramebuffer(int target, int framebuffer); +} diff --git a/src/main/resources/assets/create/flywheel/shaders/area_effect.frag b/src/main/resources/assets/create/flywheel/shaders/area_effect.frag index 005fe91f8..de6fb2f23 100644 --- a/src/main/resources/assets/create/flywheel/shaders/area_effect.frag +++ b/src/main/resources/assets/create/flywheel/shaders/area_effect.frag @@ -16,7 +16,7 @@ uniform vec3 uCameraPos; struct SphereFilter { vec4 sphere;// - vec3 data;// + vec4 data;// mat4 colorOp; }; @@ -49,9 +49,9 @@ float overlayFilterAmount(in vec3 worldPos, in vec4 sphere, in float feather) { return 1 - smoothstep(sphere.w, sphere.w + feather, distance); } -float sphereFilterAmount(in vec3 worldDir, in float depth, in vec4 sphere, in float feather) { - float feathering = 1 - smoothstep(sphere.w, sphere.w + feather, length(sphere.xyz)); - feathering += overlayFilterAmount(worldDir * depth, sphere, feather); +float sphereFilterAmount(in vec3 worldDir, in float depth, in vec4 sphere, in vec4 data) { + float feathering = 1 - smoothstep(sphere.w + data.x, sphere.w + data.x + data.y, length(sphere.xyz)); + feathering += overlayFilterAmount(worldDir * depth, sphere, data.x); vec3 oc = -sphere.xyz; float rayLengthSqr = dot(worldDir, worldDir); @@ -61,7 +61,7 @@ float sphereFilterAmount(in vec3 worldDir, in float depth, in vec4 sphere, in fl float d = 4. * rayLengthSqr; float e = 1. / (2.0*rayLengthSqr); - float radius = sphere.w; + float radius = sphere.w + data.x; float c = sphereDistSqr - radius*radius; float discriminant = b2 - d * c; float hitDepth = (-b - sqrt(discriminant)) * e; @@ -75,8 +75,8 @@ float sphereFilterAmount(in vec3 worldDir, in float depth, in vec4 sphere, in fl vec3 hitPos = worldDir * hitDepth; vec3 normal = normalize(hitPos - sphere.xyz); - - return feathering - dot(normal, normalize(worldDir)) * 1.3 - 0.1; + float normalDot = dot(normal, normalize(worldDir)); + return feathering + normalDot * normalDot; } else { return feathering; } @@ -92,17 +92,17 @@ vec3 applyFilters(in vec3 worldDir, in float depth, in vec3 diffuse) { SphereFilter s = uSpheres[i]; //float strength = overlayFilterAmount(worldPos, s.sphere, s.data.x); - float strength = sphereFilterAmount(worldDir, depth, s.sphere, s.data.x); + float strength = sphereFilterAmount(worldDir, depth, s.sphere, s.data); //accum = vec3(strength, strength, strength); - vec3 toFilter = mix(diffuse, diffuseHSV, s.data.z); + vec3 toFilter = mix(diffuse, diffuseHSV, s.data.w); vec3 filtered = filterColor(s.colorOp, diffuse); - filtered = mix(filtered, hsv2rgbWrapped(filtered), s.data.z); + filtered = mix(filtered, hsv2rgbWrapped(filtered), s.data.w); - accum = mix(accum, filtered, clamp(strength * s.data.y, 0., 1.)); + accum = mix(accum, filtered, clamp(strength * s.data.z, 0., 1.)); } return accum;