wip hiz
This commit is contained in:
@@ -11,7 +11,11 @@ public class GlFramebuffer extends TrackedObject {
|
||||
}
|
||||
|
||||
public GlFramebuffer bind(int attachment, GlTexture texture) {
|
||||
glNamedFramebufferTexture(this.id, attachment, texture.id, 0);
|
||||
return this.bind(attachment, texture, 0);
|
||||
}
|
||||
|
||||
public GlFramebuffer bind(int attachment, GlTexture texture, int lvl) {
|
||||
glNamedFramebufferTexture(this.id, attachment, texture.id, lvl);
|
||||
return this;
|
||||
}
|
||||
|
||||
|
||||
@@ -5,11 +5,13 @@ import me.cortex.voxy.client.core.gl.shader.Shader;
|
||||
import me.cortex.voxy.client.core.gl.shader.ShaderType;
|
||||
import me.cortex.voxy.client.core.rendering.util.UploadStream;
|
||||
import me.cortex.voxy.client.mixin.joml.AccessFrustumIntersection;
|
||||
import net.minecraft.client.MinecraftClient;
|
||||
import net.minecraft.client.render.RenderLayer;
|
||||
import org.joml.Matrix4f;
|
||||
import org.joml.Vector3f;
|
||||
import org.lwjgl.system.MemoryUtil;
|
||||
|
||||
import static org.lwjgl.opengl.ARBDirectStateAccess.glGetNamedFramebufferAttachmentParameteriv;
|
||||
import static org.lwjgl.opengl.ARBIndirectParameters.GL_PARAMETER_BUFFER_ARB;
|
||||
import static org.lwjgl.opengl.GL11.*;
|
||||
import static org.lwjgl.opengl.GL14C.glBlendFuncSeparate;
|
||||
@@ -56,9 +58,10 @@ public class Gl46MeshletsFarWorldRenderer extends AbstractFarWorldRenderer<Gl46M
|
||||
|
||||
private final GlBuffer glDrawIndirect;
|
||||
private final GlBuffer meshletBuffer;
|
||||
private final HiZBuffer hiZBuffer = new HiZBuffer();
|
||||
|
||||
public Gl46MeshletsFarWorldRenderer(int geometrySize, int maxSections) {
|
||||
super(new DefaultGeometryManager(alignUp(geometrySize*8L, 8*64), maxSections, 8*64));
|
||||
super(new DefaultGeometryManager(alignUp(geometrySize*8L, 8*32), maxSections, 8*32));
|
||||
this.glDrawIndirect = new GlBuffer(4*5);
|
||||
this.meshletBuffer = new GlBuffer(4*1000000);//TODO: Make max meshlet count configurable, not just 1 million (even tho thats a max of 126 million quads per frame)
|
||||
}
|
||||
@@ -147,6 +150,14 @@ public class Gl46MeshletsFarWorldRenderer extends AbstractFarWorldRenderer<Gl46M
|
||||
|
||||
glMemoryBarrier(GL_SHADER_STORAGE_BARRIER_BIT);
|
||||
|
||||
|
||||
|
||||
var i = new int[1];
|
||||
glGetFramebufferAttachmentParameteriv(GL_FRAMEBUFFER, GL_DEPTH_ATTACHMENT, GL_FRAMEBUFFER_ATTACHMENT_OBJECT_NAME, i);
|
||||
this.hiZBuffer.buildMipChain(i[0], MinecraftClient.getInstance().getFramebuffer().textureWidth, MinecraftClient.getInstance().getFramebuffer().textureHeight);
|
||||
|
||||
|
||||
|
||||
glBindVertexArray(0);
|
||||
glBindSampler(0, 0);
|
||||
glBindTextureUnit(0, 0);
|
||||
@@ -173,6 +184,8 @@ public class Gl46MeshletsFarWorldRenderer extends AbstractFarWorldRenderer<Gl46M
|
||||
|
||||
this.glDrawIndirect.free();
|
||||
this.meshletBuffer.free();
|
||||
|
||||
this.hiZBuffer.free();
|
||||
}
|
||||
|
||||
public static long alignUp(long n, long alignment) {
|
||||
|
||||
@@ -0,0 +1,98 @@
|
||||
package me.cortex.voxy.client.core.rendering;
|
||||
|
||||
import me.cortex.voxy.client.core.gl.GlFramebuffer;
|
||||
import me.cortex.voxy.client.core.gl.GlTexture;
|
||||
import me.cortex.voxy.client.core.gl.shader.Shader;
|
||||
import me.cortex.voxy.client.core.gl.shader.ShaderType;
|
||||
import org.lwjgl.opengl.GL11;
|
||||
|
||||
import static org.lwjgl.opengl.ARBDirectStateAccess.*;
|
||||
import static org.lwjgl.opengl.GL11C.*;
|
||||
import static org.lwjgl.opengl.GL30C.*;
|
||||
import static org.lwjgl.opengl.GL33.glBindSampler;
|
||||
import static org.lwjgl.opengl.GL33.glGenSamplers;
|
||||
import static org.lwjgl.opengl.GL33C.glDeleteSamplers;
|
||||
import static org.lwjgl.opengl.GL45C.glNamedFramebufferTexture;
|
||||
|
||||
public class HiZBuffer {
|
||||
private final Shader hiz = Shader.make()
|
||||
.add(ShaderType.VERTEX, "voxy:hiz/blit.vsh")
|
||||
.add(ShaderType.FRAGMENT, "voxy:hiz/blit.fsh")
|
||||
.compile();
|
||||
private final GlFramebuffer fb = new GlFramebuffer();
|
||||
private final int sampler = glGenSamplers();
|
||||
private GlTexture texture;
|
||||
private int levels;
|
||||
private int width;
|
||||
private int height;
|
||||
|
||||
public HiZBuffer() {
|
||||
glNamedFramebufferDrawBuffer(this.fb.id, GL_NONE);
|
||||
}
|
||||
|
||||
private void alloc(int width, int height) {
|
||||
this.levels = (int)Math.ceil(Math.log(Math.max(width, height))/Math.log(2));
|
||||
//We dont care about e.g. 1x1 size texture since you dont get meshlets that big to cover such a large area
|
||||
this.levels -= 3;//Arbitrary size, shinks the max level by alot and saves a significant amount of processing time
|
||||
// (could probably increase it to be defined by a max meshlet coverage computation thing)
|
||||
|
||||
//We do a hack where we assume (which is probably wrong) that we will on average never
|
||||
// get a meshlet that uses 0 mipping
|
||||
this.levels--;
|
||||
this.texture = new GlTexture().store(GL_DEPTH_COMPONENT32, this.levels, width/2, height/2);
|
||||
glTextureParameteri(this.texture.id, GL_TEXTURE_MIN_FILTER, GL_NEAREST);
|
||||
glTextureParameteri(this.texture.id, GL_TEXTURE_MAG_FILTER, GL_NEAREST);
|
||||
glTextureParameteri(this.texture.id, GL_TEXTURE_COMPARE_MODE, GL_NONE);
|
||||
glTextureParameteri(this.texture.id, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_EDGE);
|
||||
glTextureParameteri(this.texture.id, GL_TEXTURE_WRAP_T, GL_CLAMP_TO_EDGE);
|
||||
this.width = width;
|
||||
this.height = height;
|
||||
}
|
||||
|
||||
public void buildMipChain(int srcDepthTex, int width, int height) {
|
||||
if (this.width != width || this.height != height) {
|
||||
if (this.texture != null) {
|
||||
this.texture.free();
|
||||
this.texture = null;
|
||||
}
|
||||
this.alloc(width, height);
|
||||
}
|
||||
glBindVertexArray(AbstractFarWorldRenderer.STATIC_VAO);
|
||||
int boundFB = GL11.glGetInteger(GL_DRAW_FRAMEBUFFER_BINDING);
|
||||
this.hiz.bind();
|
||||
this.fb.bind(GL_DEPTH_ATTACHMENT, this.texture, 0).verify();
|
||||
glBindFramebuffer(GL_FRAMEBUFFER, this.fb.id);
|
||||
|
||||
glDepthFunc(GL_ALWAYS);
|
||||
|
||||
glBindTextureUnit(0, srcDepthTex);
|
||||
glBindSampler(0, this.sampler);
|
||||
glUniform1i(0, 0);
|
||||
int cw = this.width /2;
|
||||
int ch = this.height/2;
|
||||
for (int i = 0; i < this.levels; i++) {
|
||||
this.fb.bind(GL_DEPTH_ATTACHMENT, this.texture, i);
|
||||
glViewport(0, 0, cw, ch); cw /= 2; ch /= 2;
|
||||
glDrawArrays(GL_TRIANGLE_FAN, 0, 4);
|
||||
if (i == 0) {
|
||||
glBindTextureUnit(0, this.texture.id);
|
||||
}
|
||||
glTextureParameteri(this.texture.id, GL_TEXTURE_BASE_LEVEL, i);
|
||||
glTextureParameteri(this.texture.id, GL_TEXTURE_MAX_LEVEL, i+1);
|
||||
}
|
||||
glTextureParameteri(this.texture.id, GL_TEXTURE_BASE_LEVEL, 0);
|
||||
glTextureParameteri(this.texture.id, GL_TEXTURE_MAX_LEVEL, this.levels-1);//TODO: CHECK IF ITS -1 or -0
|
||||
|
||||
glDepthFunc(GL_LEQUAL);
|
||||
glBindFramebuffer(GL_FRAMEBUFFER, boundFB);
|
||||
glViewport(0, 0, width, height);
|
||||
glBindVertexArray(0);
|
||||
}
|
||||
|
||||
public void free() {
|
||||
this.fb.free();
|
||||
this.texture.free();
|
||||
this.texture = null;
|
||||
glDeleteSamplers(this.sampler);
|
||||
}
|
||||
}
|
||||
@@ -53,7 +53,7 @@ public class RenderDataFactory {
|
||||
// can do funny stuff like double rendering
|
||||
|
||||
private static final boolean USE_UINT64 = false;//FIXME: replace with automatic detection of uint64 shader extension support
|
||||
private static final int QUADS_PER_MESHLET = 62;
|
||||
private static final int QUADS_PER_MESHLET = 30;
|
||||
private static void writePos(long ptr, long pos) {
|
||||
if (USE_UINT64) {
|
||||
MemoryUtil.memPutLong(ptr, pos);
|
||||
|
||||
9
src/main/resources/assets/voxy/shaders/hiz/blit.fsh
Normal file
9
src/main/resources/assets/voxy/shaders/hiz/blit.fsh
Normal file
@@ -0,0 +1,9 @@
|
||||
#version 450
|
||||
|
||||
|
||||
layout(location = 0) in vec2 uv;
|
||||
layout(binding = 0) uniform sampler2D depthTex;
|
||||
void main() {
|
||||
vec4 depths = textureGather(depthTex, uv, 0); // Get depth values from all surrounding texels.
|
||||
gl_FragDepth = max(max(depths.x, depths.y), max(depths.z, depths.w)); // Write conservative depth.
|
||||
}
|
||||
8
src/main/resources/assets/voxy/shaders/hiz/blit.vsh
Normal file
8
src/main/resources/assets/voxy/shaders/hiz/blit.vsh
Normal file
@@ -0,0 +1,8 @@
|
||||
#version 450
|
||||
|
||||
layout(location = 0) out vec2 uv;
|
||||
void main() {
|
||||
vec2 corner = vec2[](vec2(0,0), vec2(1,0), vec2(1,1),vec2(0,1))[gl_VertexID];
|
||||
uv = corner;
|
||||
gl_Position = vec4(corner*2-1, 0, 1);
|
||||
}
|
||||
@@ -7,7 +7,7 @@
|
||||
#import <voxy:lod/section.glsl>
|
||||
#define extractMeshletStart extractQuadStart
|
||||
layout(local_size_x = 64) in;
|
||||
#define QUADS_PER_MESHLET 62
|
||||
#define QUADS_PER_MESHLET 30
|
||||
|
||||
void emitMeshlets(inout uint mli, inout uint meshletPtr, uint mskedCnt, uint cnt) {
|
||||
for (;mskedCnt != 0; mskedCnt--,mli++) {
|
||||
|
||||
@@ -10,6 +10,7 @@ layout(location = 2) in flat vec4 tinting;
|
||||
layout(location = 3) in flat vec4 addin;
|
||||
layout(location = 4) in flat uint flags;
|
||||
layout(location = 5) in flat vec4 conditionalTinting;
|
||||
layout(location = 6) in flat uint meshlet;
|
||||
//layout(location = 6) in flat vec4 solidColour;
|
||||
|
||||
layout(location = 0) out vec4 outColour;
|
||||
@@ -29,4 +30,13 @@ void main() {
|
||||
outColour = (colour * tinting) + addin;
|
||||
|
||||
//outColour = vec4(uv + baseUV, 0, 1);
|
||||
|
||||
/*
|
||||
uint hash = meshlet*1231421+123141;
|
||||
hash ^= hash>>16;
|
||||
hash = hash*1231421+123141;
|
||||
hash ^= hash>>16;
|
||||
|
||||
outColour = vec4(float(hash&15u)/15, float((hash>>4)&15u)/15, float((hash>>8)&15u)/15, 1);
|
||||
*/
|
||||
}
|
||||
@@ -1,6 +1,6 @@
|
||||
#version 450
|
||||
#extension GL_ARB_gpu_shader_int64 : enable
|
||||
#define QUADS_PER_MESHLET 62
|
||||
#define QUADS_PER_MESHLET 30
|
||||
|
||||
#define MESHLET_ACCESS readonly
|
||||
//There are 16 bytes of metadata at the start of the meshlet
|
||||
@@ -36,6 +36,7 @@ uint extractDetail(PosHeader pos) {
|
||||
}
|
||||
#endif
|
||||
|
||||
layout(location = 6) out flat uint meshlet;
|
||||
PosHeader meshletPosition;
|
||||
Quad quad;
|
||||
bool setupMeshlet() {
|
||||
@@ -49,6 +50,7 @@ bool setupMeshlet() {
|
||||
return true;
|
||||
}
|
||||
|
||||
meshlet = data;
|
||||
uint baseId = (data*MESHLET_SIZE);
|
||||
uint quadIndex = baseId + (gl_VertexID>>2) + 2;
|
||||
meshletPosition = geometryPool[baseId];
|
||||
|
||||
Reference in New Issue
Block a user