diff --git a/module.rendering/src/main/java/dev/anvilcraft/lib/v2/rendering/gui/GuiRenderExtras.java b/module.rendering/src/main/java/dev/anvilcraft/lib/v2/rendering/gui/GuiRenderExtras.java index 3461047b..02d4905e 100644 --- a/module.rendering/src/main/java/dev/anvilcraft/lib/v2/rendering/gui/GuiRenderExtras.java +++ b/module.rendering/src/main/java/dev/anvilcraft/lib/v2/rendering/gui/GuiRenderExtras.java @@ -11,14 +11,15 @@ import net.minecraft.client.gui.GuiGraphicsExtractor; import net.minecraft.client.gui.render.TextureSetup; import net.minecraft.client.renderer.RenderPipelines; +import net.minecraft.client.renderer.SubmitNodeCollector; import net.minecraft.client.renderer.block.BlockAndTintGetter; -import net.minecraft.client.renderer.state.gui.BlitRenderState; import net.minecraft.core.BlockPos; import net.minecraft.world.item.ItemStack; import net.minecraft.world.level.block.state.BlockState; import org.joml.Matrix3x2f; import org.jspecify.annotations.Nullable; +import java.util.function.BiConsumer; import java.util.function.Supplier; public class GuiRenderExtras { @@ -296,7 +297,8 @@ public static void submitStructure( glitched, poseStack.last().copy(), guiGraphicsExtractor.pose().get(new Matrix3x2f()), - guiGraphicsExtractor.peekScissorStack() + guiGraphicsExtractor.peekScissorStack(), + (BiConsumer) null ) ); } @@ -329,7 +331,8 @@ public static void submitStructure( glitched, pose3D, guiGraphicsExtractor.pose().get(new Matrix3x2f()), - guiGraphicsExtractor.peekScissorStack() + guiGraphicsExtractor.peekScissorStack(), + (BiConsumer)null ) ); } @@ -360,4 +363,103 @@ public static void submitStructure( pose3D ); } + + public static void submitStructure( + GuiGraphicsExtractor guiGraphicsExtractor, + BlockAndTintGetter structureAccess, + BlockPos startPos, + BlockPos endPos, + float x0, + float y0, + float x1, + float y1, + float scale, + boolean ambientOcclusion, + boolean glitched, + PoseStack poseStack, + BiConsumer drawAdditionalCallback + ) { + guiGraphicsExtractor.submitPictureInPictureRenderState( + new StructurePipRenderingState( + structureAccess, + startPos, + endPos, + (int) x0, + (int) y0, + (int) x1, + (int) y1, + scale, + ambientOcclusion, + glitched, + poseStack.last().copy(), + guiGraphicsExtractor.pose().get(new Matrix3x2f()), + guiGraphicsExtractor.peekScissorStack(), + drawAdditionalCallback + ) + ); + } + + public static void submitStructure( + GuiGraphicsExtractor guiGraphicsExtractor, + BlockAndTintGetter structureAccess, + BlockPos startPos, + BlockPos endPos, + float x0, + float y0, + float x1, + float y1, + float scale, + boolean ambientOcclusion, + boolean glitched, + PoseStack.Pose pose3D, + BiConsumer drawAdditionalCallback + ) { + guiGraphicsExtractor.submitPictureInPictureRenderState( + new StructurePipRenderingState( + structureAccess, + startPos, + endPos, + (int) x0, + (int) y0, + (int) x1, + (int) y1, + scale, + ambientOcclusion, + glitched, + pose3D, + guiGraphicsExtractor.pose().get(new Matrix3x2f()), + guiGraphicsExtractor.peekScissorStack(), + drawAdditionalCallback + ) + ); + } + + public static void submitStructure( + GuiGraphicsExtractor guiGraphicsExtractor, + BlockAndTintGetter structureAccess, + BlockPos startPos, + BlockPos endPos, + float x0, + float y0, + float x1, + float y1, + PoseStack.Pose pose3D, + BiConsumer drawAdditionalCallback + ) { + submitStructure( + guiGraphicsExtractor, + structureAccess, + startPos, + endPos, + x0, + y0, + x1, + y1, + 32.0f, + false, + false, + pose3D, + drawAdditionalCallback + ); + } } diff --git a/module.rendering/src/main/java/dev/anvilcraft/lib/v2/rendering/gui/renderer/StructurePipRenderer.java b/module.rendering/src/main/java/dev/anvilcraft/lib/v2/rendering/gui/renderer/StructurePipRenderer.java index 5268cbce..8da61253 100644 --- a/module.rendering/src/main/java/dev/anvilcraft/lib/v2/rendering/gui/renderer/StructurePipRenderer.java +++ b/module.rendering/src/main/java/dev/anvilcraft/lib/v2/rendering/gui/renderer/StructurePipRenderer.java @@ -147,25 +147,25 @@ protected void renderToTexture(StructurePipRenderingState renderState, PoseStack } bufferSource.endBatch(); + + RenderBuffers renderBuffers = minecraft.renderBuffers(); + SubmitNodeStorage submitNodeStorage = new SubmitNodeStorage(); + GameRenderer gameRenderer = minecraft.gameRenderer; + FeatureRenderDispatcher frd = new FeatureRenderDispatcher( + submitNodeStorage, + minecraft.getModelManager(), + renderBuffers.bufferSource(), + minecraft.getAtlasManager(), + renderBuffers.outlineBufferSource(), + renderBuffers.crumblingBufferSource(), + minecraft.font, + gameRenderer.getGameRenderState() + ); for (BlockPos blockPos : BlockPos.betweenClosed(renderState.startPos(), renderState.endPos())) { BlockEntity blockEntity = level.getBlockEntity(blockPos); if (blockEntity == null) continue; BlockEntityRenderer blockEntityRenderer = minecraft.getBlockEntityRenderDispatcher().getRenderer(blockEntity); if (blockEntityRenderer == null) continue; - - RenderBuffers renderBuffers = minecraft.renderBuffers(); - SubmitNodeStorage submitNodeStorage = new SubmitNodeStorage(); - GameRenderer gameRenderer = minecraft.gameRenderer; - FeatureRenderDispatcher frd = new FeatureRenderDispatcher( - submitNodeStorage, - minecraft.getModelManager(), - renderBuffers.bufferSource(), - minecraft.getAtlasManager(), - renderBuffers.outlineBufferSource(), - renderBuffers.crumblingBufferSource(), - minecraft.font, - gameRenderer.getGameRenderState() - ); poseStack.pushPose(); poseStack.translate(blockPos.getX(), blockPos.getY(), blockPos.getZ()); BlockEntityRenderState blockEntityRenderState = blockEntityRenderer.createRenderState(); @@ -182,12 +182,19 @@ protected void renderToTexture(StructurePipRenderingState renderState, PoseStack submitNodeStorage, gameRenderer.getGameRenderState().levelRenderState.cameraRenderState ); - frd.renderAllFeatures(); poseStack.popPose(); } + if (renderState.drawAdditionalCallback() != null) { + renderState.drawAdditionalCallback().accept(submitNodeStorage, poseStack); + } + frd.renderAllFeatures(); + bufferSource.endBatch(); poseStack.popPose(); poseStack.popPose(); + if (!poseStack.isEmpty()) { + throw new IllegalStateException("Pose stack not empty"); + } if (renderState.glitched()) { applyGlitchEffect(width, height); } diff --git a/module.rendering/src/main/java/dev/anvilcraft/lib/v2/rendering/gui/state/StructurePipRenderingState.java b/module.rendering/src/main/java/dev/anvilcraft/lib/v2/rendering/gui/state/StructurePipRenderingState.java index d7c6b38a..395d4ae3 100644 --- a/module.rendering/src/main/java/dev/anvilcraft/lib/v2/rendering/gui/state/StructurePipRenderingState.java +++ b/module.rendering/src/main/java/dev/anvilcraft/lib/v2/rendering/gui/state/StructurePipRenderingState.java @@ -2,13 +2,18 @@ import com.mojang.blaze3d.vertex.PoseStack; import net.minecraft.client.gui.navigation.ScreenRectangle; +import net.minecraft.client.renderer.SubmitNodeCollector; import net.minecraft.client.renderer.block.BlockAndTintGetter; import net.minecraft.client.renderer.state.gui.pip.PictureInPictureRenderState; import net.minecraft.core.BlockPos; import net.minecraft.util.Mth; +import org.jetbrains.annotations.ApiStatus; import org.joml.Matrix3x2f; import org.jspecify.annotations.Nullable; +import java.util.function.BiConsumer; + +@ApiStatus.Internal public record StructurePipRenderingState ( BlockAndTintGetter structureAccess, BlockPos startPos, @@ -23,9 +28,45 @@ public record StructurePipRenderingState ( PoseStack.Pose pose3D, Matrix3x2f pose, @Nullable ScreenRectangle scissorArea, - @Nullable ScreenRectangle bounds + @Nullable ScreenRectangle bounds, + @Nullable BiConsumer drawAdditionalCallback ) implements PictureInPictureRenderState { + public StructurePipRenderingState( + BlockAndTintGetter structureAccess, + BlockPos startPos, + BlockPos endPos, + int x0, + int y0, + int x1, + int y1, + float scale, + boolean ambientOcclusion, + boolean glitched, + PoseStack.Pose pose3D, + Matrix3x2f pose, + @Nullable ScreenRectangle scissorArea, + @Nullable BiConsumer drawAdditionalCallback + ) { + this( + structureAccess, + startPos, + endPos, + x0, + y0, + x1, + y1, + scale, + ambientOcclusion, + glitched, + pose3D, + pose, + scissorArea, + PictureInPictureRenderState.getBounds(Mth.floor(x0), Mth.floor(y0), Mth.floor(x1), Mth.floor(y1), scissorArea), + drawAdditionalCallback + ); + } + public StructurePipRenderingState( BlockAndTintGetter structureAccess, BlockPos startPos, @@ -40,7 +81,42 @@ public StructurePipRenderingState( PoseStack.Pose pose3D, Matrix3x2f pose, @Nullable ScreenRectangle scissorArea - ){ + ) { + this( + structureAccess, + startPos, + endPos, + x0, + y0, + x1, + y1, + scale, + ambientOcclusion, + glitched, + pose3D, + pose, + scissorArea, + PictureInPictureRenderState.getBounds(Mth.floor(x0), Mth.floor(y0), Mth.floor(x1), Mth.floor(y1), scissorArea), + null + ); + } + + public StructurePipRenderingState( + BlockAndTintGetter structureAccess, + BlockPos startPos, + BlockPos endPos, + int x0, + int y0, + int x1, + int y1, + float scale, + boolean ambientOcclusion, + boolean glitched, + PoseStack.Pose pose3D, + Matrix3x2f pose, + @Nullable ScreenRectangle scissorArea, + @Nullable ScreenRectangle bounds + ) { this( structureAccess, startPos, @@ -55,7 +131,8 @@ public StructurePipRenderingState( pose3D, pose, scissorArea, - PictureInPictureRenderState.getBounds(Mth.floor(x0), Mth.floor(y0), Mth.floor(x1), Mth.floor(y1), scissorArea) + bounds, + null ); } }