From 7408018f09efdfe702143bbe759e6ecbd6a539e1 Mon Sep 17 00:00:00 2001 From: Moritz Zwerger Date: Wed, 26 Jul 2023 01:57:54 +0200 Subject: [PATCH] register render layers properly --- .../de/bixilon/minosoft/gui/RenderLoop.kt | 2 +- .../gui/rendering/chunk/ChunkRenderer.kt | 3 ++- .../renderer/renderer/RendererManager.kt | 14 ++++++++++- .../renderer/pipeline/RendererPipeline.kt | 17 ++++++++++--- .../pipeline/world/PipelineElement.kt | 24 +++++++++++++++++-- .../pipeline/world/WorldRendererPipeline.kt | 15 ++++++++++-- .../renderer/renderer/world/LayerSettings.kt | 4 +++- 7 files changed, 68 insertions(+), 11 deletions(-) diff --git a/src/main/java/de/bixilon/minosoft/gui/RenderLoop.kt b/src/main/java/de/bixilon/minosoft/gui/RenderLoop.kt index 55b0f9782..f0018bc96 100644 --- a/src/main/java/de/bixilon/minosoft/gui/RenderLoop.kt +++ b/src/main/java/de/bixilon/minosoft/gui/RenderLoop.kt @@ -89,7 +89,7 @@ class RenderLoop( context.textures.staticTextures.animator.draw() - context.renderer.render() + context.renderer.draw() context.system.reset() // Reset to enable depth mask, etc again diff --git a/src/main/java/de/bixilon/minosoft/gui/rendering/chunk/ChunkRenderer.kt b/src/main/java/de/bixilon/minosoft/gui/rendering/chunk/ChunkRenderer.kt index dd473c360..ef63dc990 100644 --- a/src/main/java/de/bixilon/minosoft/gui/rendering/chunk/ChunkRenderer.kt +++ b/src/main/java/de/bixilon/minosoft/gui/rendering/chunk/ChunkRenderer.kt @@ -43,6 +43,7 @@ import de.bixilon.minosoft.gui.rendering.system.base.DepthFunctions import de.bixilon.minosoft.gui.rendering.system.base.RenderSystem import de.bixilon.minosoft.gui.rendering.system.base.layer.OpaqueLayer import de.bixilon.minosoft.gui.rendering.system.base.layer.RenderLayer +import de.bixilon.minosoft.gui.rendering.system.base.layer.TranslucentLayer import de.bixilon.minosoft.gui.rendering.system.base.layer.TransparentLayer import de.bixilon.minosoft.gui.rendering.system.base.settings.RenderSettings import de.bixilon.minosoft.gui.rendering.util.vec.vec2.Vec2iUtil.EMPTY @@ -93,7 +94,7 @@ class ChunkRenderer( override fun registerLayers() { layers.register(OpaqueLayer, shader, this::drawBlocksOpaque) { visible.opaque.isEmpty() } layers.register(TransparentLayer, transparentShader, this::drawBlocksTransparent) { visible.transparent.isEmpty() } - layers.register(TransparentLayer, transparentShader, this::drawBlocksTranslucent) { visible.translucent.isEmpty() } + layers.register(TranslucentLayer, shader, this::drawBlocksTranslucent) { visible.translucent.isEmpty() } layers.register(TextLayer, textShader, this::drawText) { visible.text.isEmpty() } layers.register(BlockEntitiesLayer, shader, this::drawBlockEntities) { visible.blockEntities.isEmpty() } } diff --git a/src/main/java/de/bixilon/minosoft/gui/rendering/renderer/renderer/RendererManager.kt b/src/main/java/de/bixilon/minosoft/gui/rendering/renderer/renderer/RendererManager.kt index a356ef6fb..8edd7a90c 100644 --- a/src/main/java/de/bixilon/minosoft/gui/rendering/renderer/renderer/RendererManager.kt +++ b/src/main/java/de/bixilon/minosoft/gui/rendering/renderer/renderer/RendererManager.kt @@ -23,13 +23,14 @@ import de.bixilon.kutil.latch.SimpleLatch import de.bixilon.minosoft.gui.rendering.RenderContext import de.bixilon.minosoft.gui.rendering.renderer.drawable.Drawable import de.bixilon.minosoft.gui.rendering.renderer.renderer.pipeline.RendererPipeline +import de.bixilon.minosoft.gui.rendering.renderer.renderer.world.WorldRenderer import de.bixilon.minosoft.util.logging.Log import de.bixilon.minosoft.util.logging.LogLevels import de.bixilon.minosoft.util.logging.LogMessageType class RendererManager( val context: RenderContext, -) : Drawable { +) : Drawable, Iterable { private val renderers: MutableMap, Renderer> = linkedMapOf() private val pipeline = RendererPipeline(this) private val connection = context.connection @@ -41,6 +42,7 @@ class RendererManager( if (previous != null) { Log.log(LogMessageType.RENDERING, LogLevels.WARN) { "Renderer $previous ($builder) got replaced by $renderer!" } } + pipeline += renderer return renderer } @@ -63,6 +65,12 @@ class RendererManager( } fun init(latch: AbstractLatch) { + for (renderer in renderers.values) { + if (renderer !is WorldRenderer) continue + renderer.registerLayers() + } + pipeline.world.rebuild() + runAsync(latch, Renderer::preAsyncInit) for (renderer in renderers.values) { @@ -101,4 +109,8 @@ class RendererManager( prepare() pipeline.draw() } + + override fun iterator(): Iterator { + return renderers.values.iterator() + } } diff --git a/src/main/java/de/bixilon/minosoft/gui/rendering/renderer/renderer/pipeline/RendererPipeline.kt b/src/main/java/de/bixilon/minosoft/gui/rendering/renderer/renderer/pipeline/RendererPipeline.kt index 04f71ba6c..dfbe0b48d 100644 --- a/src/main/java/de/bixilon/minosoft/gui/rendering/renderer/renderer/pipeline/RendererPipeline.kt +++ b/src/main/java/de/bixilon/minosoft/gui/rendering/renderer/renderer/pipeline/RendererPipeline.kt @@ -17,6 +17,7 @@ import de.bixilon.minosoft.gui.rendering.renderer.drawable.Drawable import de.bixilon.minosoft.gui.rendering.renderer.renderer.Renderer import de.bixilon.minosoft.gui.rendering.renderer.renderer.RendererManager import de.bixilon.minosoft.gui.rendering.renderer.renderer.pipeline.world.WorldRendererPipeline +import de.bixilon.minosoft.gui.rendering.renderer.renderer.world.WorldRenderer import de.bixilon.minosoft.gui.rendering.system.base.PolygonModes import de.bixilon.minosoft.gui.rendering.system.base.RenderSystem import de.bixilon.minosoft.gui.rendering.system.base.phases.PostDrawable @@ -24,9 +25,9 @@ import de.bixilon.minosoft.gui.rendering.system.base.phases.PreDrawable import de.bixilon.minosoft.gui.rendering.system.base.phases.SkipAll class RendererPipeline(private val renderer: RendererManager) : Drawable { - private val world = WorldRendererPipeline(renderer) + val world = WorldRendererPipeline(renderer) - private val rest: MutableList = mutableListOf() + private val rest: MutableList = mutableListOf() private val pre: MutableList = mutableListOf() private val post: MutableList = mutableListOf() @@ -43,7 +44,6 @@ class RendererPipeline(private val renderer: RendererManager) : Drawable { private fun drawRest() { for (renderer in rest) { - if (renderer !is Drawable) continue if (renderer.skipDraw) continue if (renderer is SkipAll && renderer.skipAll) continue @@ -79,4 +79,15 @@ class RendererPipeline(private val renderer: RendererManager) : Drawable { drawPost() } + operator fun plusAssign(renderer: Renderer) { + if (renderer is WorldRenderer) { + return world.rebuild() + } + if (renderer is Drawable) { + rest += renderer + // TODO: sort for framebuffer + } + if (renderer is PreDrawable) pre += renderer + if (renderer is PostDrawable) post += renderer + } } diff --git a/src/main/java/de/bixilon/minosoft/gui/rendering/renderer/renderer/pipeline/world/PipelineElement.kt b/src/main/java/de/bixilon/minosoft/gui/rendering/renderer/renderer/pipeline/world/PipelineElement.kt index c7cbed006..ff513161c 100644 --- a/src/main/java/de/bixilon/minosoft/gui/rendering/renderer/renderer/pipeline/world/PipelineElement.kt +++ b/src/main/java/de/bixilon/minosoft/gui/rendering/renderer/renderer/pipeline/world/PipelineElement.kt @@ -13,6 +13,26 @@ package de.bixilon.minosoft.gui.rendering.renderer.renderer.pipeline.world -import de.bixilon.minosoft.gui.rendering.renderer.drawable.Drawable +import de.bixilon.minosoft.gui.rendering.RenderContext +import de.bixilon.minosoft.gui.rendering.shader.Shader +import de.bixilon.minosoft.gui.rendering.system.base.layer.RenderLayer -class PipelineElement : Comparable, Drawable +class PipelineElement( + val layer: RenderLayer, + val shader: Shader?, + val renderer: () -> Unit, + val skip: (() -> Boolean)? +) : Comparable { + + fun draw(context: RenderContext) { + if (skip != null && skip.invoke()) return + + context.system.set(layer.settings) + shader?.use() + renderer.invoke() + } + + override fun compareTo(other: PipelineElement): Int { + return layer.priority.compareTo(other.layer.priority) + } +} diff --git a/src/main/java/de/bixilon/minosoft/gui/rendering/renderer/renderer/pipeline/world/WorldRendererPipeline.kt b/src/main/java/de/bixilon/minosoft/gui/rendering/renderer/renderer/pipeline/world/WorldRendererPipeline.kt index b82303b46..60a95fcf2 100644 --- a/src/main/java/de/bixilon/minosoft/gui/rendering/renderer/renderer/pipeline/world/WorldRendererPipeline.kt +++ b/src/main/java/de/bixilon/minosoft/gui/rendering/renderer/renderer/pipeline/world/WorldRendererPipeline.kt @@ -15,13 +15,21 @@ package de.bixilon.minosoft.gui.rendering.renderer.renderer.pipeline.world import de.bixilon.minosoft.gui.rendering.renderer.drawable.Drawable import de.bixilon.minosoft.gui.rendering.renderer.renderer.RendererManager +import de.bixilon.minosoft.gui.rendering.renderer.renderer.world.WorldRenderer class WorldRendererPipeline(val renderer: RendererManager) : Drawable { + private val framebuffer = renderer.context.framebuffer.world private var elements: Array = emptyArray() private fun build(): Array { - TODO() + val list: MutableList = mutableListOf() + for (renderer in renderer) { + if (renderer !is WorldRenderer) continue + list += renderer.layers.elements + } + + return list.sorted().toTypedArray() } fun rebuild() { @@ -30,8 +38,11 @@ class WorldRendererPipeline(val renderer: RendererManager) : Drawable { override fun draw() { + renderer.context.system.framebuffer = framebuffer.framebuffer + renderer.context.system.polygonMode = framebuffer.polygonMode + for (element in elements) { - element.draw() + element.draw(renderer.context) } } } diff --git a/src/main/java/de/bixilon/minosoft/gui/rendering/renderer/renderer/world/LayerSettings.kt b/src/main/java/de/bixilon/minosoft/gui/rendering/renderer/renderer/world/LayerSettings.kt index 507771572..a3cc076a5 100644 --- a/src/main/java/de/bixilon/minosoft/gui/rendering/renderer/renderer/world/LayerSettings.kt +++ b/src/main/java/de/bixilon/minosoft/gui/rendering/renderer/renderer/world/LayerSettings.kt @@ -13,12 +13,14 @@ package de.bixilon.minosoft.gui.rendering.renderer.renderer.world +import de.bixilon.minosoft.gui.rendering.renderer.renderer.pipeline.world.PipelineElement import de.bixilon.minosoft.gui.rendering.shader.Shader import de.bixilon.minosoft.gui.rendering.system.base.layer.RenderLayer class LayerSettings { + val elements: MutableList = mutableListOf() fun register(layer: RenderLayer, shader: Shader?, renderer: () -> Unit, skip: (() -> Boolean)? = null) { - TODO() + elements += PipelineElement(layer, shader, renderer, skip) } }