From 8b877a5f1ae21f80250bdced30f227fe7dd5cdcb Mon Sep 17 00:00:00 2001 From: Morippi Date: Wed, 24 Aug 2022 21:54:56 +0200 Subject: [PATCH] Divided transparent from opaque in the rendering (transparent are not rendering for some reason) --- .../lod/core/a7/datatype/LodRenderSource.java | 5 +- .../a7/datatype/PlaceHolderRenderSource.java | 2 +- .../datatype/column/ColumnRenderSource.java | 24 +++++-- .../column/render/ColumnRenderBuffer.java | 69 ++++++++++++++----- .../core/a7/render/RenderBufferHandler.java | 28 ++++++-- 5 files changed, 97 insertions(+), 31 deletions(-) diff --git a/src/main/java/com/seibel/lod/core/a7/datatype/LodRenderSource.java b/src/main/java/com/seibel/lod/core/a7/datatype/LodRenderSource.java index 0ad7c46a7..968e98266 100644 --- a/src/main/java/com/seibel/lod/core/a7/datatype/LodRenderSource.java +++ b/src/main/java/com/seibel/lod/core/a7/datatype/LodRenderSource.java @@ -24,10 +24,11 @@ public interface LodRenderSource { /** * Try and swap in new render buffer for this section. Note that before this call, there should be no other * places storing or referencing the render buffer. - * @param referenceSlot The slot for swapping in the new buffer. + * @param referenceSlotsOpaque The opaque slot for swapping in the new buffer. + * @param referenceSlotsTransparent The transparent slot for swapping in the new buffer. * @return True if the swap was successful. False if swap is not needed or if it is in progress. */ - boolean trySwapRenderBuffer(LodQuadTree quadTree, AtomicReference referenceSlot); + boolean trySwapRenderBuffer(LodQuadTree quadTree, AtomicReference referenceSlotsOpaque, AtomicReference referenceSlotsTransparent); void saveRender(IClientLevel level, RenderMetaFile file, OutputStream dataStream) throws IOException; diff --git a/src/main/java/com/seibel/lod/core/a7/datatype/PlaceHolderRenderSource.java b/src/main/java/com/seibel/lod/core/a7/datatype/PlaceHolderRenderSource.java index 983ee9423..7f8dea0ed 100644 --- a/src/main/java/com/seibel/lod/core/a7/datatype/PlaceHolderRenderSource.java +++ b/src/main/java/com/seibel/lod/core/a7/datatype/PlaceHolderRenderSource.java @@ -41,7 +41,7 @@ public class PlaceHolderRenderSource implements LodRenderSource { return 0; } @Override - public boolean trySwapRenderBuffer(LodQuadTree quadTree, AtomicReference referenceSlot) { + public boolean trySwapRenderBuffer(LodQuadTree quadTree, AtomicReference referenceSlotsOpaque, AtomicReference referenceSlotsTransparent) { return false; } @Override diff --git a/src/main/java/com/seibel/lod/core/a7/datatype/column/ColumnRenderSource.java b/src/main/java/com/seibel/lod/core/a7/datatype/column/ColumnRenderSource.java index 5eda2de4a..2bae4f1c7 100644 --- a/src/main/java/com/seibel/lod/core/a7/datatype/column/ColumnRenderSource.java +++ b/src/main/java/com/seibel/lod/core/a7/datatype/column/ColumnRenderSource.java @@ -267,8 +267,9 @@ public class ColumnRenderSource implements LodRenderSource, IColumnDatatype { return SECTION_SIZE_OFFSET; } - private CompletableFuture inBuildRenderBuffer = null; - private Reference usedBuffer = new Reference<>(); + private CompletableFuture inBuildRenderBuffer = null; + private Reference usedBufferOpaque = new Reference<>(); + private Reference usedBufferTransparent = new Reference<>(); private void tryBuildBuffer(IClientLevel level, LodQuadTree quadTree) { @@ -280,7 +281,7 @@ public class ColumnRenderSource implements LodRenderSource, IColumnDatatype { data[direction.ordinal()-2] = ((ColumnRenderSource) section.getRenderContainer()); } } - inBuildRenderBuffer = ColumnRenderBuffer.build(level, usedBuffer, this, data); + inBuildRenderBuffer = ColumnRenderBuffer.build(level, usedBufferOpaque, usedBufferTransparent, this, data); } } private void cancelBuildBuffer() { @@ -319,7 +320,7 @@ public class ColumnRenderSource implements LodRenderSource, IColumnDatatype { private static final long SWAP_BUSY_COLLISION_TIMEOUT = /* 1 sec */ 1_000_000_000L; @Override - public boolean trySwapRenderBuffer(LodQuadTree quadTree, AtomicReference referenceSlot) { + public boolean trySwapRenderBuffer(LodQuadTree quadTree, AtomicReference referenceSlotsOpaque, AtomicReference referenceSlotsTransparent) { if (lastNs != -1 && System.nanoTime() - lastNs < SWAP_TIMEOUT) { return false; } @@ -327,11 +328,20 @@ public class ColumnRenderSource implements LodRenderSource, IColumnDatatype { if (inBuildRenderBuffer.isDone()) { lastNs = System.nanoTime(); //LOGGER.info("Swapping render buffer for {}", sectionPos); - RenderBuffer oldBuffer = referenceSlot.getAndSet(inBuildRenderBuffer.join()); - if (oldBuffer instanceof ColumnRenderBuffer) { - ColumnRenderBuffer swapped = usedBuffer.swap((ColumnRenderBuffer) oldBuffer); + RenderBuffer[] newBuffers = inBuildRenderBuffer.join(); + RenderBuffer oldBuffersOpaque = referenceSlotsOpaque.getAndSet(newBuffers[0]); + RenderBuffer oldBuffersTransparent = referenceSlotsOpaque.getAndSet(newBuffers[1]); + ColumnRenderBuffer swapped; + if (oldBuffersOpaque instanceof ColumnRenderBuffer) { + swapped = usedBufferOpaque.swap((ColumnRenderBuffer) oldBuffersOpaque); LodUtil.assertTrue(swapped == null); } + + if (oldBuffersTransparent instanceof ColumnRenderBuffer) { + swapped = usedBufferTransparent.swap((ColumnRenderBuffer) oldBuffersTransparent); + LodUtil.assertTrue(swapped == null); + } + inBuildRenderBuffer = null; return true; } diff --git a/src/main/java/com/seibel/lod/core/a7/datatype/column/render/ColumnRenderBuffer.java b/src/main/java/com/seibel/lod/core/a7/datatype/column/render/ColumnRenderBuffer.java index ce518b4b2..772205125 100644 --- a/src/main/java/com/seibel/lod/core/a7/datatype/column/render/ColumnRenderBuffer.java +++ b/src/main/java/com/seibel/lod/core/a7/datatype/column/render/ColumnRenderBuffer.java @@ -185,7 +185,7 @@ public class ColumnRenderBuffer extends RenderBuffer { return getCurrentJobsCount() > MAX_CONCURRENT_CALL; } - public static CompletableFuture build(IClientLevel clientLevel, Reference usedBufferSlot, ColumnRenderSource data, ColumnRenderSource[] adjData) { + public static CompletableFuture build(IClientLevel clientLevel, Reference usedBufferSlotOpaque, Reference usedBufferSlotTransparent, ColumnRenderSource data, ColumnRenderSource[] adjData) { if (isBusy()) return null; //LOGGER.info("RenderRegion startBuild @ {}", data.sectionPos); return CompletableFuture.supplyAsync(() -> { @@ -194,14 +194,22 @@ public class ColumnRenderBuffer extends RenderBuffer { int skyLightCullingBelow = Config.Client.Graphics.AdvancedGraphics.caveCullingHeight.get(); // FIXME: Clamp also to the max world height. skyLightCullingBelow = Math.max(skyLightCullingBelow, clientLevel.getMinY()); - LodQuadBuilder builder = new LodQuadBuilder(true, + LodQuadBuilder builderOpaque = new LodQuadBuilder(true, (short) (skyLightCullingBelow - clientLevel.getMinY())); - makeLodRenderData(builder, data, adjData); - if (builder.getCurrentQuadsCount() > 0) { + + LodQuadBuilder builderTransparent = new LodQuadBuilder(true, + (short) (skyLightCullingBelow - clientLevel.getMinY())); + + makeLodRenderData(builderOpaque, builderTransparent, data, adjData); + if (builderOpaque.getCurrentQuadsCount() > 0) { //LOGGER.info("her"); } EVENT_LOGGER.trace("RenderRegion end QuadBuild @ {}", data.sectionPos); - return builder; + LodQuadBuilder[] builders = new LodQuadBuilder[2]; + builders[0] = builderOpaque; + builders[1] = builderOpaque; + + return builders; } catch (UncheckedInterruptedException e) { throw e; } @@ -210,24 +218,35 @@ public class ColumnRenderBuffer extends RenderBuffer { throw e3; } }, BUFFER_BUILDERS) - .thenApplyAsync((builder) -> { + .thenApplyAsync((builders) -> { try { EVENT_LOGGER.trace("RenderRegion start Upload @ {}", data.sectionPos); GLProxy glProxy = GLProxy.getInstance(); EGpuUploadMethod method = GLProxy.getInstance().getGpuUploadMethod(); EGLProxyContext oldContext = glProxy.getGlContext(); glProxy.setGlContext(EGLProxyContext.LOD_BUILDER); - ColumnRenderBuffer buffer = usedBufferSlot.swap(null); - if (buffer == null) - buffer = new ColumnRenderBuffer( + ColumnRenderBuffer buffersSlotOpaque = usedBufferSlotOpaque.swap(null); + ColumnRenderBuffer buffersSlotTransparent = usedBufferSlotTransparent.swap(null); + + if (buffersSlotOpaque == null) + buffersSlotOpaque = new ColumnRenderBuffer( new DHBlockPos(data.sectionPos.getCorner().getCorner(), clientLevel.getMinY()) ); + if (buffersSlotTransparent == null) + buffersSlotTransparent = new ColumnRenderBuffer( + new DHBlockPos(data.sectionPos.getCorner().getCorner(), clientLevel.getMinY()) + ); try { - buffer.uploadBuffer(builder, method); + buffersSlotOpaque.uploadBuffer(builders[0], method); + buffersSlotTransparent.uploadBuffer(builders[1], method); EVENT_LOGGER.trace("RenderRegion end Upload @ {}", data.sectionPos); - return buffer; + ColumnRenderBuffer[] buffers = new ColumnRenderBuffer[2]; + buffers[0] = buffersSlotOpaque; + buffers[1] = buffersSlotTransparent; + return buffers; } catch (Exception e) { - buffer.close(); + buffersSlotOpaque.close(); + buffersSlotTransparent.close(); throw e; } finally { glProxy.setGlContext(oldContext); @@ -241,7 +260,14 @@ public class ColumnRenderBuffer extends RenderBuffer { }, BUFFER_UPLOADER).handle((v, e) -> { //LOGGER.info("RenderRegion endBuild @ {}", data.sectionPos); if (e != null) { - if (!usedBufferSlot.isEmpty()) usedBufferSlot.swap(null).close(); + if (!usedBufferSlotOpaque.isEmpty()) { + ColumnRenderBuffer buffersSlot = usedBufferSlotOpaque.swap(null); + buffersSlot.close(); + } + if (!usedBufferSlotTransparent.isEmpty()) { + ColumnRenderBuffer buffersSlot = usedBufferSlotTransparent.swap(null); + buffersSlot.close(); + } return null; } else { return v; @@ -251,7 +277,7 @@ public class ColumnRenderBuffer extends RenderBuffer { - private static void makeLodRenderData(LodQuadBuilder quadBuilder, ColumnRenderSource region, ColumnRenderSource[] adjRegions) { + private static void makeLodRenderData(LodQuadBuilder quadBuilderOpaque, LodQuadBuilder quadBuilderTransparent, ColumnRenderSource region, ColumnRenderSource[] adjRegions) { // Variable initialization EDebugMode debugMode = Config.Client.Advanced.Debugging.debugMode.get(); @@ -343,12 +369,21 @@ public class ColumnRenderBuffer extends RenderBuffer { long adjDataTop = i - 1 >= 0 ? posData.get(i - 1) : DataPointUtil.EMPTY_DATA; long adjDataBot = i + 1 < posData.size() ? posData.get(i + 1) : DataPointUtil.EMPTY_DATA; + // We send the call to create the vertices - CubicLodTemplate.addLodToBuffer(data, adjDataTop, adjDataBot, adjData, detailLevel, - x, z, quadBuilder, debugMode); + if(DataPointUtil.getAlpha(data) == 255) + { + CubicLodTemplate.addLodToBuffer(data, adjDataTop, adjDataBot, adjData, detailLevel, + x, z, quadBuilderOpaque, debugMode); + }else + { + CubicLodTemplate.addLodToBuffer(data, adjDataTop, adjDataBot, adjData, detailLevel, + x, z, quadBuilderTransparent, debugMode); + } } } } - quadBuilder.mergeQuads(); + quadBuilderOpaque.mergeQuads(); + quadBuilderTransparent.mergeQuads(); } } diff --git a/src/main/java/com/seibel/lod/core/a7/render/RenderBufferHandler.java b/src/main/java/com/seibel/lod/core/a7/render/RenderBufferHandler.java index df58b7fd3..b871ed466 100644 --- a/src/main/java/com/seibel/lod/core/a7/render/RenderBufferHandler.java +++ b/src/main/java/com/seibel/lod/core/a7/render/RenderBufferHandler.java @@ -17,14 +17,29 @@ public class RenderBufferHandler { class RenderBufferNode implements AutoCloseable { public final DhSectionPos pos; public volatile RenderBufferNode[] children = null; - public final AtomicReference renderBufferSlot = new AtomicReference<>(); + public final AtomicReference renderBufferSlotOpaque = new AtomicReference<>(); + public final AtomicReference renderBufferSlotTransparent = new AtomicReference<>(); public RenderBufferNode(DhSectionPos pos) { this.pos = pos; } public void render(a7LodRenderer renderContext) { - RenderBuffer buff = renderBufferSlot.get(); + RenderBuffer buff; + + buff = renderBufferSlotOpaque.get(); + if (buff != null) { + buff.render(renderContext); + } else { + RenderBufferNode[] childs = children; + if (childs != null) { + for (RenderBufferNode child : childs) { + child.render(renderContext); + } + } + } + + buff = renderBufferSlotTransparent.get(); if (buff != null) { buff.render(renderContext); } else { @@ -57,7 +72,7 @@ public class RenderBufferHandler { // } } else { LodUtil.assertTrue(container != null); // section.isLoaded() should have ensured this - container.trySwapRenderBuffer(target, renderBufferSlot); + container.trySwapRenderBuffer(target, renderBufferSlotOpaque, renderBufferSlotTransparent); } // Update children's render buffer state @@ -97,7 +112,12 @@ public class RenderBufferHandler { child.close(); } } - RenderBuffer buff = renderBufferSlot.getAndSet(null); + RenderBuffer buff; + buff = renderBufferSlotOpaque.getAndSet(null); + if (buff != null) { + buff.close(); + } + buff = renderBufferSlotTransparent.getAndSet(null); if (buff != null) { buff.close(); }