diff --git a/src/client/java/dev/turtywurty/industria/renderer/block/ArcFurnaceBlockEntityRenderer.java b/src/client/java/dev/turtywurty/industria/renderer/block/ArcFurnaceBlockEntityRenderer.java index 9f6a742..b0771da 100644 --- a/src/client/java/dev/turtywurty/industria/renderer/block/ArcFurnaceBlockEntityRenderer.java +++ b/src/client/java/dev/turtywurty/industria/renderer/block/ArcFurnaceBlockEntityRenderer.java @@ -10,6 +10,11 @@ public ArcFurnaceBlockEntityRenderer(BlockEntityRendererFactory.Context context) super(context); } + @Override + protected void renderModel(ArcFurnaceBlockEntity entity, float tickDelta, MatrixStack matrices, VertexConsumerProvider vertexConsumers, int light, int overlay) { + + } + @Override protected void onRender(ArcFurnaceBlockEntity entity, float tickDelta, MatrixStack matrices, VertexConsumerProvider vertexConsumers, int light, int overlay) { diff --git a/src/client/java/dev/turtywurty/industria/renderer/block/CentrifugalConcentratorBlockEntityRenderer.java b/src/client/java/dev/turtywurty/industria/renderer/block/CentrifugalConcentratorBlockEntityRenderer.java index c272d63..4bbd5e4 100644 --- a/src/client/java/dev/turtywurty/industria/renderer/block/CentrifugalConcentratorBlockEntityRenderer.java +++ b/src/client/java/dev/turtywurty/industria/renderer/block/CentrifugalConcentratorBlockEntityRenderer.java @@ -1,14 +1,10 @@ package dev.turtywurty.industria.renderer.block; -import com.mojang.blaze3d.vertex.VertexFormat; import dev.turtywurty.industria.blockentity.CentrifugalConcentratorBlockEntity; import dev.turtywurty.industria.blockentity.util.fluid.SyncingFluidStorage; import dev.turtywurty.industria.model.CentrifugalConcentratorModel; import net.fabricmc.fabric.api.transfer.v1.client.fluid.FluidVariantRendering; import net.fabricmc.fabric.api.transfer.v1.fluid.FluidVariant; -import net.minecraft.block.entity.BlockEntity; -import net.minecraft.client.MinecraftClient; -import net.minecraft.client.model.ModelPart; import net.minecraft.client.render.*; import net.minecraft.client.render.block.entity.BlockEntityRendererFactory; import net.minecraft.client.texture.Sprite; @@ -17,16 +13,9 @@ import net.minecraft.item.ItemStack; import net.minecraft.item.Items; import net.minecraft.particle.ParticleTypes; -import net.minecraft.util.TriState; -import net.minecraft.util.math.BlockPos; import net.minecraft.util.math.MathHelper; import net.minecraft.util.math.RotationAxis; -import net.minecraft.util.math.Vec3d; -import org.jbox2d.common.Vec3; -import org.joml.Matrix4f; -import org.joml.Vector3d; import org.joml.Vector3f; -import org.joml.Vector4f; // TODO: Finish OBJLoader and use that for rendering public class CentrifugalConcentratorBlockEntityRenderer extends IndustriaBlockEntityRenderer { @@ -40,7 +29,7 @@ public CentrifugalConcentratorBlockEntityRenderer(BlockEntityRendererFactory.Con } @Override - protected void onRender(CentrifugalConcentratorBlockEntity entity, float tickDelta, MatrixStack matrices, VertexConsumerProvider vertexConsumers, int light, int overlay) { + protected void renderModel(CentrifugalConcentratorBlockEntity entity, float tickDelta, MatrixStack matrices, VertexConsumerProvider vertexConsumers, int light, int overlay) { this.model.getCylinderTop().hidden = true; int rpm = entity.getRecipeRPM(); @@ -57,46 +46,76 @@ protected void onRender(CentrifugalConcentratorBlockEntity entity, float tickDel this.model.getBowl().yaw = prevBowlYRot; this.model.getCylinderTop().hidden = false; + } + + @Override + protected void onRender(CentrifugalConcentratorBlockEntity entity, float tickDelta, MatrixStack matrices, VertexConsumerProvider vertexConsumers, int light, int overlay) { + + float fluidYOffset = renderInputFluid(entity, tickDelta, matrices, vertexConsumers, light, overlay); - renderInputFluid(entity, tickDelta, matrices, vertexConsumers, light, overlay); + matrices.push(); + matrices.translate(0, fluidYOffset, 0); + renderInputItems(entity, tickDelta, matrices, vertexConsumers, light, overlay); + matrices.pop(); } - private void renderInputFluid(CentrifugalConcentratorBlockEntity entity, float tickDelta, MatrixStack matrices, VertexConsumerProvider vertexConsumers, int light, int overlay) { - SyncingFluidStorage fluidTank = entity.getInputFluidTank(); - if (fluidTank.isResourceBlank() || fluidTank.amount <= 0) return; + private void renderInputItems(CentrifugalConcentratorBlockEntity entity, float tickDelta, MatrixStack matrices, VertexConsumerProvider vertexConsumers, int light, int overlay) { + ItemStack stackInSlot = Items.DIAMOND.getDefaultStack(); //entity.getInputInventory().getStackInSlot(0); + if(stackInSlot.isEmpty()) return; + + float radius = 1.1f; + for (int i = 0; i < NUM_SPINNING_ITEMS; i++) { + float angle = -entity.bowlRotation + (float) Math.TAU / NUM_SPINNING_ITEMS * i; + + float x = (float) Math.cos(angle) * radius; + float y = (float) Math.sin(angle * 3) * 0.02f - 0.2f; + float z = (float) Math.sin(angle) * radius; + + matrices.push(); + matrices.translate(x, y, z); + matrices.multiply(RotationAxis.POSITIVE_Y.rotation(angle + (float) Math.PI / 2f)); + matrices.scale(0.5f, 0.5f, 0.5f); + this.context.getItemRenderer().renderItem(stackInSlot, ItemDisplayContext.NONE, light, overlay, matrices, vertexConsumers, entity.getWorld(), 0); + + Vector3f pos = matrixStackToWorldPosition(matrices); + entity.getWorld().addParticleClient(ParticleTypes.BUBBLE, pos.x, pos.y + 0.3f, pos.z, 0, 0, 0); + + matrices.pop(); + } + } + + + private float renderInputFluid(CentrifugalConcentratorBlockEntity entity, float tickDelta, MatrixStack matrices, VertexConsumerProvider vertexConsumers, int light, int overlay) { + SyncingFluidStorage fluidTank = entity.getInputFluidTank(); + if (fluidTank.isResourceBlank() || fluidTank.amount <= 0) return 0; FluidVariant fluidVariant = fluidTank.variant; Sprite fluidSprite = FluidVariantRendering.getSprite(fluidVariant); - if (fluidSprite == null) - return; + if (fluidSprite == null) return 0; RenderLayer renderLayer = RenderLayer.getItemEntityTranslucentCull(fluidSprite.getAtlasId()); VertexConsumer vertexConsumer = vertexConsumers.getBuffer(renderLayer); - int sides = 16; - float outerRadius = 19 / 16f; - float innerRadius = 4 / 16f; - int fluidColor = FluidVariantRendering.getColor(fluidVariant, entity.getWorld(), entity.getPos()); - float fillPercent = fluidTank.amount / (float) fluidTank.getCapacity(); - // fillPercent = (float) (Math.sin(entity.getWorld().getTime() / entity.getWorld().getTickManager().getTickRate()) * 0.5f + 0.5f); + int sides = 16; + float outerRadius = 19 / 16f; + float innerRadius = fillPercent <= 7 / 16f ? 0 : 4 / 16f; - if (fillPercent <= 7 / 16f) { - innerRadius = 0; - } + int fluidColor = FluidVariantRendering.getColor(fluidVariant, entity.getWorld(), entity.getPos()); float yMin = 1 / 16f; float yMax = 18 / 16f; float yOffset = MathHelper.lerp(fillPercent, yMin, yMax); + matrices.push(); - matrices.translate(0, -yOffset, 0); + matrices.translate(0, yOffset, 0); float angleOffset = (float) Math.PI / sides; for (int i = 0; i < sides; i += 1) { - float angle0 = angleOffset + (float) (2.0 * Math.PI * i / sides); - float angle1 = angleOffset + (float) (2.0 * Math.PI * (i + 1) / sides); + float angle0 = angleOffset - (float) (2.0 * Math.PI * i / sides); + float angle1 = angleOffset - (float) (2.0 * Math.PI * (i + 1) / sides); angledFluidVertex(vertexConsumer, matrices, fluidSprite, fluidColor, angle0, innerRadius, outerRadius, light, overlay); angledFluidVertex(vertexConsumer, matrices, fluidSprite, fluidColor, angle0, outerRadius, outerRadius, light, overlay); @@ -104,38 +123,9 @@ private void renderInputFluid(CentrifugalConcentratorBlockEntity entity, float t angledFluidVertex(vertexConsumer, matrices, fluidSprite, fluidColor, angle1, innerRadius, outerRadius, light, overlay); } - ItemStack stackInSlot = Items.DIAMOND.getDefaultStack(); //entity.getInputInventory().getStackInSlot(0); - float radius = 1.1f; - - for (int i = 0; i < NUM_SPINNING_ITEMS; i++) { - float angle = -entity.bowlRotation + (float) Math.TAU / NUM_SPINNING_ITEMS * i; - - float x = (float) Math.cos(angle) * radius; - float y = (float) Math.sin(angle * 3) * 0.02f + 0.225f; - float z = (float) Math.sin(angle) * radius; - - matrices.push(); - matrices.translate(x, y, z); - matrices.multiply(RotationAxis.POSITIVE_X.rotationDegrees(180)); - matrices.multiply(RotationAxis.POSITIVE_Y.rotation(angle + (float) Math.PI / 2f)); - matrices.scale(0.5f, 0.5f, 0.5f); - this.context.getItemRenderer().renderItem(stackInSlot, ItemDisplayContext.NONE, light, overlay, matrices, vertexConsumers, entity.getWorld(), 0); - - - Vector3f pos = localToWorldPosition(matrices); - entity.getWorld().addParticleClient(ParticleTypes.BUBBLE, pos.x, pos.y + 0.25, pos.z, 0, 0, 0); - - matrices.pop(); - } - matrices.pop(); - } - - private Vector3f localToWorldPosition(MatrixStack matrices) { - Vector3f pos = matrices.peek().getPositionMatrix().transformPosition(0, 0, 0, new Vector3f()); - Vec3d cameraPos = MinecraftClient.getInstance().gameRenderer.getCamera().getPos(); - return new Vector3f((float) (pos.x() + cameraPos.x), (float) (pos.y() + cameraPos.y), (float) (pos.z() + cameraPos.z)); + return yOffset; } private void angledFluidVertex(VertexConsumer vc, MatrixStack matrixStack, Sprite sprite, int fluidColor, float angle, float radius, float uvSize, int light, int overlay) { diff --git a/src/client/java/dev/turtywurty/industria/renderer/block/ClarifierBlockEntityRenderer.java b/src/client/java/dev/turtywurty/industria/renderer/block/ClarifierBlockEntityRenderer.java index a3160e3..5a975ba 100644 --- a/src/client/java/dev/turtywurty/industria/renderer/block/ClarifierBlockEntityRenderer.java +++ b/src/client/java/dev/turtywurty/industria/renderer/block/ClarifierBlockEntityRenderer.java @@ -9,13 +9,16 @@ import net.minecraft.client.render.VertexConsumerProvider; import net.minecraft.client.render.block.entity.BlockEntityRendererFactory; import net.minecraft.client.util.math.MatrixStack; +import net.minecraft.fluid.Fluids; import net.minecraft.item.ItemDisplayContext; import net.minecraft.item.ItemStack; +import net.minecraft.item.Items; import net.minecraft.util.math.MathHelper; import net.minecraft.util.math.RotationAxis; import net.minecraft.util.math.Vec3d; public class ClarifierBlockEntityRenderer extends IndustriaBlockEntityRenderer { + private final ClarifierModel model; private final InWorldFluidRenderingComponent fluidRenderer = new InWorldFluidRenderingComponent(); @@ -50,11 +53,13 @@ public ClarifierBlockEntityRenderer(BlockEntityRendererFactory.Context context) } @Override - protected void onRender(ClarifierBlockEntity entity, float tickDelta, MatrixStack matrices, VertexConsumerProvider vertexConsumers, int light, int overlay) { + protected void renderModel(ClarifierBlockEntity entity, float tickDelta, MatrixStack matrices, VertexConsumerProvider vertexConsumers, int light, int overlay) { this.model.getRootPart().render(matrices, vertexConsumers.getBuffer(this.model.getLayer(ClarifierModel.TEXTURE_LOCATION)), light, overlay); + } - if (entity.getWorld() == null) - return; + @Override + protected void onRender(ClarifierBlockEntity entity, float tickDelta, MatrixStack matrices, VertexConsumerProvider vertexConsumers, int light, int overlay) { + if (entity.getWorld() == null) return; renderInputFluid(entity, matrices, vertexConsumers, light, overlay); renderOutputFluid(entity, matrices, vertexConsumers, light, overlay); @@ -64,13 +69,13 @@ protected void onRender(ClarifierBlockEntity entity, float tickDelta, MatrixStac } private void renderOutputStack(ClarifierBlockEntity entity, MatrixStack matrices, VertexConsumerProvider vertexConsumers, int light, int overlay) { - ItemStack outputStack = entity.getOutputInventory().getStack(0); + ItemStack outputStack = new ItemStack(Items.DIAMOND_BLOCK, 64); // Items.DIAMOND.getDefaultStack(); //entity.getOutputInventory().getStack(0); if (outputStack.isEmpty()) return; float scale = 0.05f; - float zOffset = 11f / 16f + 10f / 16f + 2f / 16f; - float startY = 0.75f - scale / 2 + 9f / 16f; + float zOffset = -(11f / 16f + 10f / 16f + 2f / 16f); + float startY = -1.1f + scale / 2; for (int i = 0; i < MathHelper.clamp(outputStack.getCount(), 1, 64); i++) { matrices.push(); @@ -78,6 +83,7 @@ private void renderOutputStack(ClarifierBlockEntity entity, MatrixStack matrices GridPosition position = OUTPUT_ITEM_POSITIONS[i]; float xOff = position.x * (scale + (0.0625f * scale)) - 0.345f; float yOff = position.y * (scale + (0.0625f * scale)); + matrices.translate(xOff, startY - yOff, zOffset); matrices.scale(scale, scale, scale); this.context.getItemRenderer().renderItem(outputStack, ItemDisplayContext.NONE, light, overlay, matrices, vertexConsumers, entity.getWorld(), 0); @@ -87,12 +93,12 @@ private void renderOutputStack(ClarifierBlockEntity entity, MatrixStack matrices // Thanks to Basti for the item rendering math private void renderCurrentOutputItem(ClarifierBlockEntity blockEntity, MatrixStack matrices, VertexConsumerProvider vertexConsumers, int light, int overlay) { - ItemStack nextOutput = blockEntity.getNextOutputItemStack(); + ItemStack nextOutput = Items.DIAMOND_BLOCK.getDefaultStack(); //blockEntity.getNextOutputItemStack(); if (nextOutput.isEmpty()) return; - float itemProgress = (float) blockEntity.getProgress() / blockEntity.getMaxProgress(); + float itemProgress = (blockEntity.getWorld().getTime() / 100f) % 1; // (float) blockEntity.getProgress() / blockEntity.getMaxProgress(); float scale = 0.15f; float firstStretch = 11f / 16f; @@ -123,7 +129,7 @@ private void renderCurrentOutputItem(ClarifierBlockEntity blockEntity, MatrixSta } matrices.push(); - matrices.translate(0, 0.75 - scale / 2 - dy, 0 + dz); + matrices.translate(0, -0.75 + scale / 2 + dy, -dz); matrices.scale(scale, scale, scale); matrices.multiply(RotationAxis.POSITIVE_X.rotation(rotation)); this.context.getItemRenderer().renderItem(nextOutput, ItemDisplayContext.NONE, light, overlay, matrices, vertexConsumers, blockEntity.getWorld(), 0); @@ -131,58 +137,60 @@ private void renderCurrentOutputItem(ClarifierBlockEntity blockEntity, MatrixSta } private void renderInputFluid(ClarifierBlockEntity entity, MatrixStack matrices, VertexConsumerProvider vertexConsumers, int light, int overlay) { - SyncingFluidStorage fluidStorage = entity.getInputFluidTank(); - if (fluidStorage == null || fluidStorage.isResourceBlank() || fluidStorage.amount <= 0) - return; +// SyncingFluidStorage fluidStorage = entity.getInputFluidTank(); +// if (fluidStorage == null || fluidStorage.isResourceBlank() || fluidStorage.amount <= 0) +// return; - FluidVariant fluidVariant = fluidStorage.getResource(); + FluidVariant fluidVariant = FluidVariant.of(Fluids.WATER); // fluidStorage.getResource(); - long amount = fluidStorage.amount; + long amount = 10000; //fluidStorage.amount; float fluidProgress = (float) amount / (FluidConstants.BUCKET * 5); - // fluidProgress = (float) (Math.sin(entity.getWorld().getTime() / 64.0) * 0.5 + 0.5); - float fluidHeight = -0.625f + (fluidProgress * 1 + 1.999f/16f); + fluidProgress = (float) (Math.sin(entity.getWorld().getTime() / 64.0) * 0.5 + 0.5); + + float fluidHeight = 0.625f - (fluidProgress * 1 + 1.999f / 16f); float size = 1.25f; - if (fluidHeight < 0f) + if (fluidHeight > 0f) size = 0.5f; - this.fluidRenderer.renderTopFaceOnly(fluidVariant, - vertexConsumers, matrices, - light, overlay, - entity.getWorld(), entity.getPos(), - -size, fluidHeight, -size, - size, size); +// this.fluidRenderer.renderTopFaceOnly(fluidVariant, +// vertexConsumers, matrices, +// light, overlay, +// entity.getWorld(), entity.getPos(), +// -size, fluidHeight, -size, +// size, size); } private void renderOutputFluid(ClarifierBlockEntity entity, MatrixStack matrices, VertexConsumerProvider vertexConsumers, int light, int overlay) { - SyncingFluidStorage fluidStorage = entity.getOutputFluidTank(); - if (fluidStorage == null || fluidStorage.isResourceBlank() || fluidStorage.amount <= 0) - return; - - FluidVariant fluidVariant = fluidStorage.getResource(); - - long amount = fluidStorage.amount; - float fluidProgress = (float) amount / (FluidConstants.BUCKET * 5); - // fluidProgress = (float) (Math.sin(entity.getWorld().getTime() / 64.0) * 0.5 + 0.5); - float fluidHeight = -1.375f + (fluidProgress * 0.5f); +// SyncingFluidStorage fluidStorage = entity.getOutputFluidTank(); +// if (fluidStorage == null || fluidStorage.isResourceBlank() || fluidStorage.amount <= 0) +// return; +// +// FluidVariant fluidVariant = fluidStorage.getResource(); +// +// long amount = fluidStorage.amount; - this.fluidRenderer.renderTopFaceOnly(fluidVariant, - vertexConsumers, matrices, - light, overlay, - entity.getWorld(), entity.getPos(), - -0.375f, fluidHeight, -0.5f, - 0.375f, 1.4375f); - matrices.push(); - matrices.multiply(RotationAxis.POSITIVE_Y.rotationDegrees(180)); - this.fluidRenderer.drawTiledXYQuadOnly(fluidVariant, - vertexConsumers, matrices, - light, overlay, - entity.getWorld(), entity.getPos(), - -0.375f, -1.375f, -1.4375f, - 0.375f, fluidHeight, -1.4375f); + FluidVariant fluidVariant = FluidVariant.of(Fluids.WATER); + long amount = 10000; - matrices.pop(); + float fluidProgress = (float) amount / (FluidConstants.BUCKET * 5); + fluidProgress = (float) (Math.sin(entity.getWorld().getTime() / 64.0) * 0.5 + 0.5); + float fluidHeight = 1.375f - (fluidProgress * 0.5f); + +// this.fluidRenderer.renderTopFaceOnly(fluidVariant, +// vertexConsumers, matrices, +// light, overlay, +// entity.getWorld(), entity.getPos(), +// 0.375f, fluidHeight, 0.5f, +// -0.375f, -1.4375f); +// +// this.fluidRenderer.drawTiledXYQuadOnly(fluidVariant, +// vertexConsumers, matrices, +// light, overlay, +// entity.getWorld(), entity.getPos(), +// -0.375f, 1.375f, -1.4375f, +// 0.375f, fluidHeight, -1.4375f); } private record GridPosition(int x, int y) { diff --git a/src/client/java/dev/turtywurty/industria/renderer/block/CrusherBlockEntityRenderer.java b/src/client/java/dev/turtywurty/industria/renderer/block/CrusherBlockEntityRenderer.java index 664480c..0046f83 100644 --- a/src/client/java/dev/turtywurty/industria/renderer/block/CrusherBlockEntityRenderer.java +++ b/src/client/java/dev/turtywurty/industria/renderer/block/CrusherBlockEntityRenderer.java @@ -13,28 +13,18 @@ import net.minecraft.util.math.RotationAxis; import net.minecraft.util.math.Vec3d; -public class CrusherBlockEntityRenderer implements BlockEntityRenderer { +public class CrusherBlockEntityRenderer extends IndustriaBlockEntityRenderer { private static final Identifier TEXTURE = Industria.id("textures/block/crusher.png"); private final CrusherModel model; public CrusherBlockEntityRenderer(BlockEntityRendererFactory.Context context) { + super(context); this.model = new CrusherModel(context.getLayerModelPart(CrusherModel.LAYER_LOCATION)); } @Override - public void render(CrusherBlockEntity entity, float tickDelta, MatrixStack matrices, VertexConsumerProvider vertexConsumers, int light, int overlay, Vec3d cameraPos) { - matrices.push(); - matrices.translate(0.5f, 1.5f, 0.5f); - matrices.multiply(RotationAxis.POSITIVE_X.rotationDegrees(180)); - - matrices.multiply(RotationAxis.POSITIVE_Y.rotationDegrees(180 + switch (entity.getCachedState().get(Properties.HORIZONTAL_FACING)) { - case EAST -> 90; - case SOUTH -> 180; - case WEST -> 270; - default -> 0; - })); - + protected void renderModel(CrusherBlockEntity entity, float tickDelta, MatrixStack matrices, VertexConsumerProvider vertexConsumers, int light, int overlay) { float prevBottomLeftRoll = this.model.getCrusherParts().bottomLeft().roll; float prevBottomRightRoll = this.model.getCrusherParts().bottomRight().roll; float prevTopLeftRoll = this.model.getCrusherParts().topLeft().roll; @@ -54,7 +44,10 @@ public void render(CrusherBlockEntity entity, float tickDelta, MatrixStack matri this.model.getCrusherParts().bottomRight().roll = prevBottomRightRoll; this.model.getCrusherParts().topLeft().roll = prevTopLeftRoll; this.model.getCrusherParts().topRight().roll = prevTopRightRoll; + } + + @Override + protected void onRender(CrusherBlockEntity entity, float tickDelta, MatrixStack matrices, VertexConsumerProvider vertexConsumers, int light, int overlay) { - matrices.pop(); } } diff --git a/src/client/java/dev/turtywurty/industria/renderer/block/CrystallizerBlockEntityRenderer.java b/src/client/java/dev/turtywurty/industria/renderer/block/CrystallizerBlockEntityRenderer.java index ba9ac7b..e6c2514 100644 --- a/src/client/java/dev/turtywurty/industria/renderer/block/CrystallizerBlockEntityRenderer.java +++ b/src/client/java/dev/turtywurty/industria/renderer/block/CrystallizerBlockEntityRenderer.java @@ -66,9 +66,12 @@ public CrystallizerBlockEntityRenderer(BlockEntityRendererFactory.Context contex } @Override - protected void onRender(CrystallizerBlockEntity entity, float tickDelta, MatrixStack matrices, VertexConsumerProvider vertexConsumers, int light, int overlay) { + protected void renderModel(CrystallizerBlockEntity entity, float tickDelta, MatrixStack matrices, VertexConsumerProvider vertexConsumers, int light, int overlay) { this.model.render(matrices, vertexConsumers.getBuffer(this.model.getLayer(CrystallizerModel.TEXTURE_LOCATION)), light, overlay); + } + @Override + protected void onRender(CrystallizerBlockEntity entity, float tickDelta, MatrixStack matrices, VertexConsumerProvider vertexConsumers, int light, int overlay) { renderNextOutputItem(entity, matrices, vertexConsumers, light, overlay); renderFluids(entity, matrices, vertexConsumers, light, overlay); } @@ -99,14 +102,14 @@ private void renderNextOutputItem(CrystallizerBlockEntity entity, MatrixStack ma } private void renderFluids(CrystallizerBlockEntity entity, MatrixStack matrices, VertexConsumerProvider vertexConsumers, int light, int overlay) { - this.fluidRenderer.render(entity.getCrystalFluidStorage(), + this.fluidRenderer.renderFluidTank(entity.getCrystalFluidStorage(), vertexConsumers, matrices, light, overlay, entity.getWorld(), entity.getPos(), -18f/16f, -0.5001f, -18f/16f, 18f/16f, 46f, 18f/16f - 0.001f, 0x40000000, ColorMode.SUBTRACTION); - this.fluidRenderer.render(entity.getWaterFluidStorage(), + this.fluidRenderer.renderFluidTank(entity.getWaterFluidStorage(), vertexConsumers, matrices, light, overlay, entity.getWorld(), entity.getPos(), diff --git a/src/client/java/dev/turtywurty/industria/renderer/block/DigesterBlockEntityRenderer.java b/src/client/java/dev/turtywurty/industria/renderer/block/DigesterBlockEntityRenderer.java index 033acf3..ff50d03 100644 --- a/src/client/java/dev/turtywurty/industria/renderer/block/DigesterBlockEntityRenderer.java +++ b/src/client/java/dev/turtywurty/industria/renderer/block/DigesterBlockEntityRenderer.java @@ -16,7 +16,11 @@ public DigesterBlockEntityRenderer(BlockEntityRendererFactory.Context context) { } @Override - protected void onRender(DigesterBlockEntity entity, float tickDelta, MatrixStack matrices, VertexConsumerProvider vertexConsumers, int light, int overlay) { + protected void renderModel(DigesterBlockEntity entity, float tickDelta, MatrixStack matrices, VertexConsumerProvider vertexConsumers, int light, int overlay) { this.model.getRootPart().render(matrices, vertexConsumers.getBuffer(this.model.getLayer(DigesterModel.TEXTURE_LOCATION)), light, overlay); } + + @Override + protected void onRender(DigesterBlockEntity entity, float tickDelta, MatrixStack matrices, VertexConsumerProvider vertexConsumers, int light, int overlay) { + } } diff --git a/src/client/java/dev/turtywurty/industria/renderer/block/DrillBlockEntityRenderer.java b/src/client/java/dev/turtywurty/industria/renderer/block/DrillBlockEntityRenderer.java index 47949f6..8ab3d34 100644 --- a/src/client/java/dev/turtywurty/industria/renderer/block/DrillBlockEntityRenderer.java +++ b/src/client/java/dev/turtywurty/industria/renderer/block/DrillBlockEntityRenderer.java @@ -42,68 +42,74 @@ public DrillBlockEntityRenderer(BlockEntityRendererFactory.Context context) { } @Override - public void onRender(DrillBlockEntity entity, float tickDelta, MatrixStack matrices, VertexConsumerProvider vertexConsumers, int light, int overlay) { - World world = entity.getWorld(); - - { // Render motor - if (!entity.getMotorInventory().isEmpty()) { - DrillMotorModel.DrillMotorParts parts = this.motorModel.getDrillMotorParts(); - float prevRodGear = parts.rodGear().pitch; - float connectingGear = parts.connectingGear().pitch; + protected void renderModel(DrillBlockEntity entity, float tickDelta, MatrixStack matrices, VertexConsumerProvider vertexConsumers, int light, int overlay) { + renderMotor(entity, tickDelta, matrices, vertexConsumers, light, overlay); + renderFrame(entity, tickDelta, matrices, vertexConsumers, light, overlay); - if (!entity.isDrilling() && !entity.isRetracting()) { - entity.clientMotorRotation = 0; - } - parts.rodGear().pitch += entity.clientMotorRotation += (entity.isDrilling() ? 0.03f : entity.isRetracting() ? -0.03f : 0); - parts.connectingGear().pitch = -entity.clientMotorRotation; + World world = entity.getWorld(); - this.motorModel.render(matrices, vertexConsumers.getBuffer(this.motorModel.getLayer(DrillMotorModel.TEXTURE_LOCATION)), light, overlay); + int worldBottom = world == null ? 0 : world.getBottomY(); + int startY = entity.getPos().getY() + 2; + float currentY = entity.getDrillYOffset() - 1 + startY; - parts.rodGear().pitch = prevRodGear; - parts.connectingGear().pitch = connectingGear; - } - } + float progress = 1 - (startY - currentY) / (startY - worldBottom); - { // Render frame - float prevCableWheelPitch = this.model.getCableWheel().pitch; - float prevCableWheelRodPitch = this.model.getCableWheelRod().pitch; + renderCableWheel(entity, tickDelta, matrices, vertexConsumers, light, overlay, progress); + renderDrill(entity, tickDelta, matrices, vertexConsumers, light, overlay, progress); + } - this.model.getCableWheel().pitch = entity.clientMotorRotation; - this.model.getCableWheelRod().pitch = entity.clientMotorRotation; + private void renderMotor(DrillBlockEntity entity, float tickDelta, MatrixStack matrices, VertexConsumerProvider vertexConsumers, int light, int overlay) { + if (entity.getMotorInventory().isEmpty()) return; - this.model.render(matrices, vertexConsumers.getBuffer(this.model.getLayer(DrillFrameModel.TEXTURE_LOCATION)), light, overlay); + DrillMotorModel.DrillMotorParts parts = this.motorModel.getDrillMotorParts(); + float prevRodGear = parts.rodGear().pitch; + float connectingGear = parts.connectingGear().pitch; - this.model.getCableWheel().pitch = prevCableWheelPitch; - this.model.getCableWheelRod().pitch = prevCableWheelRodPitch; + if (!entity.isDrilling() && !entity.isRetracting()) { + entity.clientMotorRotation = 0; } - int worldBottom = world == null ? 0 : world.getBottomY(); - int startY = entity.getPos().getY() + 2; - float currentY = entity.getDrillYOffset() - 1 + startY; + parts.rodGear().pitch += entity.clientMotorRotation += (entity.isDrilling() ? 0.03f : entity.isRetracting() ? -0.03f : 0); + parts.connectingGear().pitch = -entity.clientMotorRotation; - float progress = 1 - (startY - currentY) / (startY - worldBottom); + this.motorModel.render(matrices, vertexConsumers.getBuffer(this.motorModel.getLayer(DrillMotorModel.TEXTURE_LOCATION)), light, overlay); - { // Render cable wheel - ModelPart cableMain = this.cableModel.getMain(); + parts.rodGear().pitch = prevRodGear; + parts.connectingGear().pitch = connectingGear; + } - float prevCableMainPitch = cableMain.pitch; + private void renderFrame(DrillBlockEntity entity, float tickDelta, MatrixStack matrices, VertexConsumerProvider vertexConsumers, int light, int overlay) { + float prevCableWheelPitch = this.model.getCableWheel().pitch; + float prevCableWheelRodPitch = this.model.getCableWheelRod().pitch; - cableMain.pitch = entity.clientMotorRotation; + this.model.getCableWheel().pitch = entity.clientMotorRotation; + this.model.getCableWheelRod().pitch = entity.clientMotorRotation; - float cableScaleFactor = 0.5f - (progress / 2f); + this.model.render(matrices, vertexConsumers.getBuffer(this.model.getLayer(DrillFrameModel.TEXTURE_LOCATION)), light, overlay); - cableMain.xScale -= cableScaleFactor; - cableMain.yScale -= cableScaleFactor; - cableMain.zScale -= cableScaleFactor; - this.cableModel.render(matrices, vertexConsumers.getBuffer(this.cableModel.getLayer(DrillCableModel.TEXTURE_LOCATION)), light, overlay); - cableMain.xScale += cableScaleFactor; - cableMain.yScale += cableScaleFactor; - cableMain.zScale += cableScaleFactor; + this.model.getCableWheel().pitch = prevCableWheelPitch; + this.model.getCableWheelRod().pitch = prevCableWheelRodPitch; + } - cableMain.pitch = prevCableMainPitch; - } + private void renderCableWheel(DrillBlockEntity entity, float tickDelta, MatrixStack matrices, VertexConsumerProvider vertexConsumers, int light, int overlay, float progress) { + ModelPart cableMain = this.cableModel.getMain(); + + float prevCableMainPitch = cableMain.pitch; + cableMain.pitch = entity.clientMotorRotation; + float cableScaleFactor = 0.5f - (progress / 2f); + + cableMain.xScale -= cableScaleFactor; + cableMain.yScale -= cableScaleFactor; + cableMain.zScale -= cableScaleFactor; + this.cableModel.render(matrices, vertexConsumers.getBuffer(this.cableModel.getLayer(DrillCableModel.TEXTURE_LOCATION)), light, overlay); + cableMain.xScale += cableScaleFactor; + cableMain.yScale += cableScaleFactor; + cableMain.zScale += cableScaleFactor; + cableMain.pitch = prevCableMainPitch; + } + private void renderDrill(DrillBlockEntity entity, float tickDelta, MatrixStack matrices, VertexConsumerProvider vertexConsumers, int light, int overlay, float progress) { ItemStack drillHeadStack = entity.getDrillStack(); if (drillHeadStack.isEmpty() || !(drillHeadStack.getItem() instanceof DrillHeadable drillHeadable)) return; @@ -112,51 +118,44 @@ public void onRender(DrillBlockEntity entity, float tickDelta, MatrixStack matri if (drillHeadData == null) return; - { // Render drill cable - matrices.push(); - MatrixStack.Entry entry = matrices.peek(); - VertexConsumer linesVertexConsumer = vertexConsumers.getBuffer(RenderLayer.getLines()); + matrices.push(); + MatrixStack.Entry entry = matrices.peek(); + VertexConsumer linesVertexConsumer = vertexConsumers.getBuffer(RenderLayer.getLines()); - float angleOffset = (float) (entity.isRetracting() ? - -entity.clientMotorRotation < 0 ? -Math.PI / 4 : -Math.PI / 4 - Math.PI / 2 : - -entity.clientMotorRotation < 0 ? -3 * Math.PI / 4 + Math.PI / 2 : -3 * Math.PI / 4); + float angleOffset = (float) (entity.isRetracting() ? + -entity.clientMotorRotation < 0 ? -Math.PI / 4 : -Math.PI / 4 - Math.PI / 2 : + -entity.clientMotorRotation < 0 ? -3 * Math.PI / 4 + Math.PI / 2 : -3 * Math.PI / 4); - float angle = (float) (-entity.clientMotorRotation % (Math.PI / 2f)) + angleOffset; + float angle = (float) (-entity.clientMotorRotation % (Math.PI / 2f)) + angleOffset; - float wheelRadius = (progress / 2f + 0.5f) * 3.5f / 16f; + float wheelRadius = (progress / 2f + 0.5f) * 3.5f / 16f; - float wheelZ = 0.5f; - float wheelY = -1.5f + 1.5f / 16f; + float wheelZ = 0.5f; + float wheelY = -1.5f + 1.5f / 16f; - double r = Math.sqrt(2) * wheelRadius; - float cableZ = wheelZ + (float) (Math.cos(angle) * r); - float cableY = wheelY + (float) (Math.sin(angle) * r); + double r = Math.sqrt(2) * wheelRadius; + float cableZ = wheelZ + (float) (Math.cos(angle) * r); + float cableY = wheelY + (float) (Math.sin(angle) * r); - linesVertexConsumer.vertex(entry, 0f, cableY, cableZ) - .color(70, 70, 70, 255) - .normal(1, 0, 0); + linesVertexConsumer.vertex(entry, 0f, cableY, cableZ).color(70, 70, 70, 255).normal(1, 0, 0); + linesVertexConsumer.vertex(entry, 0, -1.54f, 0).color(70, 70, 70, 255).normal(1, 0, 0); + linesVertexConsumer.vertex(entry, 0, -1.54f, 0).color(70, 70, 70, 255).normal(0, 1, 0); - linesVertexConsumer.vertex(entry, 0, -1.54f, 0) - .color(70, 70, 70, 255) - .normal(1, 0, 0); + matrices.translate(0, -entity.getDrillYOffset(), 0); + linesVertexConsumer.vertex(matrices.peek(), 0, 0.5f, 0).color(70, 70, 70, 255).normal(0, 1, 0); - linesVertexConsumer.vertex(entry, 0, -1.54f, 0) - .color(70, 70, 70, 255) - .normal(0, 1, 0); + //drill head + Model drillHeadModel = this.drillHeadModels.computeIfAbsent(drillHeadable, ignored -> drillHeadData.modelResolver().apply(Either.left(this.context))); + Identifier drillHeadTexture = this.drillHeadTextures.computeIfAbsent(drillHeadable, ignored -> drillHeadData.textureLocation()); - matrices.translate(0, -entity.getDrillYOffset(), 0); - linesVertexConsumer.vertex(matrices.peek(), 0, 0.5f, 0) - .color(70, 70, 70, 255) - .normal(0, 1, 0); - } + drillHeadData.onRender().render(entity, drillHeadStack, tickDelta, matrices, vertexConsumers, drillHeadModel, vertexConsumers.getBuffer(drillHeadModel.getLayer(drillHeadTexture)), light, overlay); + matrices.pop(); + } - { // Render drill head - Model drillHeadModel = this.drillHeadModels.computeIfAbsent(drillHeadable, ignored -> drillHeadData.modelResolver().apply(Either.left(this.context))); - Identifier drillHeadTexture = this.drillHeadTextures.computeIfAbsent(drillHeadable, ignored -> drillHeadData.textureLocation()); - drillHeadData.onRender().render(entity, drillHeadStack, tickDelta, matrices, vertexConsumers, drillHeadModel, vertexConsumers.getBuffer(drillHeadModel.getLayer(drillHeadTexture)), light, overlay); - matrices.pop(); - } + @Override + public void onRender(DrillBlockEntity entity, float tickDelta, MatrixStack matrices, VertexConsumerProvider vertexConsumers, int light, int overlay) { + } @Override diff --git a/src/client/java/dev/turtywurty/industria/renderer/block/ElectrolyzerBlockEntityRenderer.java b/src/client/java/dev/turtywurty/industria/renderer/block/ElectrolyzerBlockEntityRenderer.java index 3092452..05a3983 100644 --- a/src/client/java/dev/turtywurty/industria/renderer/block/ElectrolyzerBlockEntityRenderer.java +++ b/src/client/java/dev/turtywurty/industria/renderer/block/ElectrolyzerBlockEntityRenderer.java @@ -15,7 +15,11 @@ public ElectrolyzerBlockEntityRenderer(BlockEntityRendererFactory.Context contex } @Override - protected void onRender(ElectrolyzerBlockEntity entity, float tickDelta, MatrixStack matrices, VertexConsumerProvider vertexConsumers, int light, int overlay) { + protected void renderModel(ElectrolyzerBlockEntity entity, float tickDelta, MatrixStack matrices, VertexConsumerProvider vertexConsumers, int light, int overlay) { this.model.render(matrices, vertexConsumers.getBuffer(this.model.getLayer(ElectrolyzerModel.TEXTURE_LOCATION)), light, overlay); } + + @Override + protected void onRender(ElectrolyzerBlockEntity entity, float tickDelta, MatrixStack matrices, VertexConsumerProvider vertexConsumers, int light, int overlay) { + } } diff --git a/src/client/java/dev/turtywurty/industria/renderer/block/FluidTankBlockEntityRenderer.java b/src/client/java/dev/turtywurty/industria/renderer/block/FluidTankBlockEntityRenderer.java index 4ff2f87..fbf9395 100644 --- a/src/client/java/dev/turtywurty/industria/renderer/block/FluidTankBlockEntityRenderer.java +++ b/src/client/java/dev/turtywurty/industria/renderer/block/FluidTankBlockEntityRenderer.java @@ -5,6 +5,9 @@ import net.minecraft.client.render.VertexConsumerProvider; import net.minecraft.client.render.block.entity.BlockEntityRendererFactory; import net.minecraft.client.util.math.MatrixStack; +import net.minecraft.item.Item; +import net.minecraft.item.ItemDisplayContext; +import net.minecraft.item.Items; public class FluidTankBlockEntityRenderer extends IndustriaBlockEntityRenderer { private final InWorldFluidRenderingComponent fluidRenderingComponent = new InWorldFluidRenderingComponent(); @@ -13,11 +16,16 @@ public FluidTankBlockEntityRenderer(BlockEntityRendererFactory.Context context) super(context); } + @Override + protected void renderModel(FluidTankBlockEntity entity, float tickDelta, MatrixStack matrices, VertexConsumerProvider vertexConsumers, int light, int overlay) { + + } + @Override protected void onRender(FluidTankBlockEntity entity, float tickDelta, MatrixStack matrices, VertexConsumerProvider vertexConsumers, int light, int overlay) { matrices.push(); - matrices.translate(-0.5, 1.5, 0.5); - this.fluidRenderingComponent.render(entity.getFluidTank(), + matrices.translate(-0.5, -1.5, -0.5); + this.fluidRenderingComponent.renderFluidTank(entity.getFluidTank(), vertexConsumers, matrices, light, overlay, entity.getWorld(), entity.getPos(), diff --git a/src/client/java/dev/turtywurty/industria/renderer/block/IndustriaBlockEntityRenderer.java b/src/client/java/dev/turtywurty/industria/renderer/block/IndustriaBlockEntityRenderer.java index 3e8a7ec..f31e574 100644 --- a/src/client/java/dev/turtywurty/industria/renderer/block/IndustriaBlockEntityRenderer.java +++ b/src/client/java/dev/turtywurty/industria/renderer/block/IndustriaBlockEntityRenderer.java @@ -56,6 +56,33 @@ public IndustriaBlockEntityRenderer(BlockEntityRendererFactory.Context context) this.context = context; } + + @Override + public final void render(T entity, float tickDelta, MatrixStack matrices, VertexConsumerProvider vertexConsumers, int light, int overlay, Vec3d cameraPos) { + matrices.push(); + setupBlockEntityTransformations(matrices, entity); + + matrices.push(); + matrices.multiply(RotationAxis.POSITIVE_X.rotationDegrees(180)); + renderModel(entity, tickDelta, matrices, vertexConsumers, light, overlay); + matrices.pop(); + + onRender(entity, tickDelta, matrices, vertexConsumers, light, overlay); + + if (isPlayerLookingAt(entity.getPos())) { + List wireframe = getModelParts(); + if (!wireframe.isEmpty()) { + boolean isHighContrast = isHighContrast(); + renderWireframe(wireframe, matrices, vertexConsumers, isHighContrast); + } + } + + matrices.pop(); + postRender(entity, tickDelta, matrices, vertexConsumers, light, overlay); + } + + protected abstract void renderModel(T entity, float tickDelta, MatrixStack matrices, VertexConsumerProvider vertexConsumers, int light, int overlay); + /** * Called to render the block entity. * @@ -80,22 +107,17 @@ public IndustriaBlockEntityRenderer(BlockEntityRendererFactory.Context context) */ protected void postRender(T entity, float tickDelta, MatrixStack matrices, VertexConsumerProvider vertexConsumers, int light, int overlay) {} - @Override - public final void render(T entity, float tickDelta, MatrixStack matrices, VertexConsumerProvider vertexConsumers, int light, int overlay, Vec3d cameraPos) { - setupBlockEntityTransformations(matrices, entity); - onRender(entity, tickDelta, matrices, vertexConsumers, light, overlay); - - if (isPlayerLookingAt(entity.getPos())) { - List wireframe = getModelParts(); - if (!wireframe.isEmpty()) { - boolean isHighContrast = isHighContrast(); - renderWireframe(wireframe, matrices, vertexConsumers, isHighContrast); - } - } - - matrices.pop(); + /** + * Converts a MatrixStack to a world Position + * + * @param matrices The current MatrixStack + * @return The world Position stored in a {@link Vector3f} + */ + protected Vector3f matrixStackToWorldPosition(MatrixStack matrices) { + Vector3f pos = matrices.peek().getPositionMatrix().transformPosition(0, 0, 0, new Vector3f()); + Vec3d cameraPos = MinecraftClient.getInstance().gameRenderer.getCamera().getPos(); - postRender(entity, tickDelta, matrices, vertexConsumers, light, overlay); + return new Vector3f((float) (pos.x() + cameraPos.x), (float) (pos.y() + cameraPos.y), (float) (pos.z() + cameraPos.z)); } private static boolean isHighContrast() { @@ -161,16 +183,16 @@ public static void renderWireframe(List modelParts, MatrixStack matri /** * Visits a model part and renders its wireframe. * - * @param modelPart The model part to visit - * @param matrices The matrix stack - * @param vertexConsumer The vertex consumer - * @param color The color of the wireframe - * @param v0 The first vertex - * @param v1 The second vertex - * @param v2 The third vertex - * @param v3 The fourth vertex - * @param pos The position of the vertex - * @param normal The normal of the vertex + * @param modelPart The model part to visit + * @param matrices The matrix stack + * @param vertexConsumer The vertex consumer + * @param color The color of the wireframe + * @param v0 The first vertex + * @param v1 The second vertex + * @param v2 The third vertex + * @param v3 The fourth vertex + * @param pos The position of the vertex + * @param normal The normal of the vertex */ private static void visitPart(ModelPart modelPart, MatrixStack matrices, VertexConsumer vertexConsumer, int color, Vector3f v0, Vector3f v1, Vector3f v2, Vector3f v3, Vector4f pos, Vector3f normal) { if (!modelPart.visible || (modelPart.isEmpty() && modelPart.children.isEmpty())) @@ -276,9 +298,7 @@ public final void renderForItem(T entity, float tickDelta, MatrixStack matrices, } protected void setupBlockEntityTransformations(MatrixStack matrices, T entity) { - matrices.push(); matrices.translate(0.5f, 1.5f, 0.5f); - matrices.multiply(RotationAxis.POSITIVE_X.rotationDegrees(180)); BlockState state = entity.getCachedState(); if (!state.getProperties().contains(Properties.HORIZONTAL_FACING)) diff --git a/src/client/java/dev/turtywurty/industria/renderer/block/MixerBlockEntityRenderer.java b/src/client/java/dev/turtywurty/industria/renderer/block/MixerBlockEntityRenderer.java index 377c8b1..2c8d8ce 100644 --- a/src/client/java/dev/turtywurty/industria/renderer/block/MixerBlockEntityRenderer.java +++ b/src/client/java/dev/turtywurty/industria/renderer/block/MixerBlockEntityRenderer.java @@ -25,10 +25,14 @@ public MixerBlockEntityRenderer(BlockEntityRendererFactory.Context context) { } @Override - protected void onRender(MixerBlockEntity entity, float tickDelta, MatrixStack matrices, VertexConsumerProvider vertexConsumers, int light, int overlay) { + protected void renderModel(MixerBlockEntity entity, float tickDelta, MatrixStack matrices, VertexConsumerProvider vertexConsumers, int light, int overlay) { this.model.getMixerParts().stirring_rods().yaw = entity.stirringRotation; this.model.getMixerParts().main().render(matrices, vertexConsumers.getBuffer(this.model.getLayer(MixerModel.TEXTURE_LOCATION)), light, overlay); this.model.getMixerParts().stirring_rods().yaw = 0.0F; + } + + @Override + protected void onRender(MixerBlockEntity entity, float tickDelta, MatrixStack matrices, VertexConsumerProvider vertexConsumers, int light, int overlay) { boolean isMixing = entity.isMixing(); if (isMixing) { @@ -51,46 +55,46 @@ protected void onRender(MixerBlockEntity entity, float tickDelta, MatrixStack ma SyncingSimpleInventory inputInventory = entity.getInputInventory(); for (int index = 0; index < inputInventory.heldStacks.size(); index++) { ItemStack stack = inputInventory.heldStacks.get(index); - if (!stack.isEmpty()) { - matrices.push(); + if (stack.isEmpty()) continue; - Vec3d position = entity.mixingItemPositions.get(index); + matrices.push(); - if(isMixing) { - // Calculate angle for each item - float angle = (float) (2 * Math.PI * index / inputInventory.heldStacks.size()); // Evenly space items around circle - // Add rotation over time using world time - float rotationSpeed = 0.1f; // Adjust this value to change rotation speed - float timeAngle = (float) entity.getWorld().getTime() * rotationSpeed; + Vec3d position = entity.mixingItemPositions.get(index); - // Define radius of the circle (you can adjust this value) - float radius = Math.max(width, depth) * 0.5f - 0.375f; + if (isMixing) { + // Calculate angle for each item + float angle = (float) (2 * Math.PI * index / inputInventory.heldStacks.size()); // Evenly space items around circle + // Add rotation over time using world time + float rotationSpeed = 0.1f; // Adjust this value to change rotation speed + float timeAngle = (float) entity.getWorld().getTime() * rotationSpeed; - // Calculate offsets using sine and cosine - double xOffset = radius * Math.sin(angle + timeAngle); - double yOffset = Math.sin(angle + index + timeAngle * 0.2f) - 1f; - double zOffset = radius * Math.cos(angle + timeAngle); + // Define radius of the circle (you can adjust this value) + float radius = Math.max(width, depth) * 0.5f - 0.375f; - position = position.add(xOffset, yOffset, zOffset); - } + // Calculate offsets using sine and cosine + double xOffset = radius * Math.sin(angle + timeAngle); + double yOffset = Math.sin(angle + index + timeAngle * 0.2f) - 1f; + double zOffset = radius * Math.cos(angle + timeAngle); - matrices.translate(position.x, position.y, position.z); - matrices.scale(0.5f, 0.5f, 0.5f); + position = position.add(xOffset, yOffset, zOffset); + } - if(isMixing) { - matrices.scale(1f - progress, 1f - progress, 1f - progress); // TODO: Make them fade away instead (maybe? :3) - matrices.multiply(RotationAxis.POSITIVE_Y.rotation(entity.getWorld().getTime() * 0.25f)); - matrices.multiply(RotationAxis.POSITIVE_X.rotation(entity.getWorld().getTime() * 0.25f)); - matrices.multiply(RotationAxis.POSITIVE_Z.rotation(entity.getWorld().getTime() * 0.25f)); - } + matrices.translate(position.x, position.y, position.z); + matrices.scale(0.5f, 0.5f, 0.5f); - this.context.getItemRenderer().renderItem(stack, ItemDisplayContext.FIXED, light, overlay, matrices, vertexConsumers, entity.getWorld(), 0); - matrices.pop(); + if (isMixing) { + matrices.scale(1f - progress, 1f - progress, 1f - progress); // TODO: Make them fade away instead (maybe? :3) + matrices.multiply(RotationAxis.POSITIVE_Y.rotation(entity.getWorld().getTime() * 0.25f)); + matrices.multiply(RotationAxis.POSITIVE_X.rotation(entity.getWorld().getTime() * 0.25f)); + matrices.multiply(RotationAxis.POSITIVE_Z.rotation(entity.getWorld().getTime() * 0.25f)); } + + this.context.getItemRenderer().renderItem(stack, ItemDisplayContext.FIXED, light, overlay, matrices, vertexConsumers, entity.getWorld(), 0); + matrices.pop(); } // TODO: Temperature-based color - this.fluidRenderer.render(entity.getInputFluidTank(), + this.fluidRenderer.renderFluidTank(entity.getInputFluidTank(), vertexConsumers, matrices, light, overlay, entity.getWorld(), entity.getPos(), diff --git a/src/client/java/dev/turtywurty/industria/renderer/block/MotorBlockEntityRenderer.java b/src/client/java/dev/turtywurty/industria/renderer/block/MotorBlockEntityRenderer.java index ce271bb..593eb28 100644 --- a/src/client/java/dev/turtywurty/industria/renderer/block/MotorBlockEntityRenderer.java +++ b/src/client/java/dev/turtywurty/industria/renderer/block/MotorBlockEntityRenderer.java @@ -10,36 +10,27 @@ import net.minecraft.util.math.RotationAxis; import net.minecraft.util.math.Vec3d; -public class MotorBlockEntityRenderer implements BlockEntityRenderer { - private final BlockEntityRendererFactory.Context context; +public class MotorBlockEntityRenderer extends IndustriaBlockEntityRenderer { + private final MotorModel model; public MotorBlockEntityRenderer(BlockEntityRendererFactory.Context context) { - this.context = context; - + super(context); this.model = new MotorModel(context.getLayerModelPart(MotorModel.LAYER_LOCATION)); } @Override - public void render(MotorBlockEntity entity, float tickDelta, MatrixStack matrices, VertexConsumerProvider vertexConsumers, int light, int overlay, Vec3d cameraPos) { - matrices.push(); - matrices.translate(0.5, 1.5, 0.5); - matrices.multiply(RotationAxis.POSITIVE_X.rotationDegrees(180)); - - matrices.multiply(RotationAxis.POSITIVE_Y.rotationDegrees(180 + switch (entity.getCachedState().get(Properties.HORIZONTAL_FACING)) { - case EAST -> 90; - case SOUTH -> 180; - case WEST -> 270; - default -> 0; - })); - + protected void renderModel(MotorBlockEntity entity, float tickDelta, MatrixStack matrices, VertexConsumerProvider vertexConsumers, int light, int overlay) { float rotationSpeed = entity.getRotationSpeed(); entity.rodRotation += rotationSpeed * tickDelta; this.model.getMotorParts().spinRod().pitch = entity.rodRotation; model.render(matrices, vertexConsumers.getBuffer(model.getLayer(MotorModel.TEXTURE_LOCATION)), light, overlay); this.model.getMotorParts().spinRod().pitch = 0; + } + + @Override + protected void onRender(MotorBlockEntity entity, float tickDelta, MatrixStack matrices, VertexConsumerProvider vertexConsumers, int light, int overlay) { - matrices.pop(); } } diff --git a/src/client/java/dev/turtywurty/industria/renderer/block/MultiblockIOBlockEntityRenderer.java b/src/client/java/dev/turtywurty/industria/renderer/block/MultiblockIOBlockEntityRenderer.java index ecd427c..ff483ea 100644 --- a/src/client/java/dev/turtywurty/industria/renderer/block/MultiblockIOBlockEntityRenderer.java +++ b/src/client/java/dev/turtywurty/industria/renderer/block/MultiblockIOBlockEntityRenderer.java @@ -14,14 +14,20 @@ import java.util.Map; public class MultiblockIOBlockEntityRenderer extends IndustriaBlockEntityRenderer { + + public MultiblockIOBlockEntityRenderer(BlockEntityRendererFactory.Context context) { super(context); } + @Override + protected void renderModel(MultiblockIOBlockEntity entity, float tickDelta, MatrixStack matrices, VertexConsumerProvider vertexConsumers, int light, int overlay) { + + } + @Override protected void onRender(MultiblockIOBlockEntity entity, float tickDelta, MatrixStack matrices, VertexConsumerProvider vertexConsumers, int light, int overlay) { - if(!this.context.getEntityRenderDispatcher().shouldRenderHitboxes()) - return; + if (!this.context.getEntityRenderDispatcher().shouldRenderHitboxes()) return; matrices.push(); matrices.translate(0, 1, 0); @@ -33,23 +39,15 @@ protected void onRender(MultiblockIOBlockEntity entity, float tickDelta, MatrixS continue; for (MultiblockIOPort port : ports.values()) { + double size = 0.5; for (TransferType transferType : port.getTransferTypes()) { float[] color = getColor(transferType); - VertexRendering.drawBox( - matrices, - vertexConsumer, - -size, - -size, - -size, - size, - size, - size, - color[0], - color[1], - color[2], - 0.5F); + VertexRendering.drawBox(matrices, vertexConsumer, + -size, -size, -size, + size, size, size, + color[0], color[1], color[2], 0.5F); size += 0.1F; } @@ -61,19 +59,10 @@ protected void onRender(MultiblockIOBlockEntity entity, float tickDelta, MatrixS float zOffset = opposite.getOffsetZ() * 0.75F; float alpha = (float) (Math.sin(entity.getWorld().getTime() % 20) * 0.5 + 0.5F); - VertexRendering.drawBox( - matrices, - vertexConsumer, - -0.1F + xOffset, - -0.1F + yOffset, - -0.1F + zOffset, - 0.1F + xOffset, - 0.1F + yOffset, - 0.1F + zOffset, - 1.0F, - 1.0F, - 1.0F, - alpha); + VertexRendering.drawBox(matrices, vertexConsumer, + -0.1F + xOffset, -0.1F + yOffset, -0.1F + zOffset, + 0.1F + xOffset, 0.1F + yOffset, 0.1F + zOffset, + 1.0F, 1.0F, 1.0F, alpha); } } @@ -81,18 +70,18 @@ protected void onRender(MultiblockIOBlockEntity entity, float tickDelta, MatrixS } private static float[] getColor(TransferType type) { - if(type == TransferType.ITEM) { + if (type == TransferType.ITEM) { return new float[]{0.0F, 0.0F, 0.0F}; } else if (type == TransferType.ENERGY) { - return new float[]{1.0F, 1.0F, 51/255F}; + return new float[]{1.0F, 1.0F, 51 / 255F}; } else if (type == TransferType.FLUID) { - return new float[]{135/255F, 206/255F, 250/255F}; + return new float[]{135 / 255F, 206 / 255F, 250 / 255F}; } else if (type == TransferType.SLURRY) { - return new float[]{139/255F, 69/255F, 19/255F}; + return new float[]{139 / 255F, 69 / 255F, 19 / 255F}; } else if (type == TransferType.HEAT) { - return new float[]{1.0F, 127/255F, 80/255F}; + return new float[]{1.0F, 127 / 255F, 80 / 255F}; } else if (type == TransferType.GAS) { - return new float[]{58/255F, 159/255F, 2/255F}; + return new float[]{58 / 255F, 159 / 255F, 2 / 255F}; } throw new IllegalStateException("Unexpected value: " + type); diff --git a/src/client/java/dev/turtywurty/industria/renderer/block/OilPumpJackBlockEntityRenderer.java b/src/client/java/dev/turtywurty/industria/renderer/block/OilPumpJackBlockEntityRenderer.java index 16d8384..eed280d 100644 --- a/src/client/java/dev/turtywurty/industria/renderer/block/OilPumpJackBlockEntityRenderer.java +++ b/src/client/java/dev/turtywurty/industria/renderer/block/OilPumpJackBlockEntityRenderer.java @@ -14,31 +14,21 @@ import net.minecraft.util.math.Vec3d; import org.joml.Vector3f; -public class OilPumpJackBlockEntityRenderer implements BlockEntityRenderer { - private final BlockEntityRendererFactory.Context context; +public class OilPumpJackBlockEntityRenderer extends IndustriaBlockEntityRenderer { + private final OilPumpJackModel model; private final OilPumpJackModel.OilPumpJackParts parts; public OilPumpJackBlockEntityRenderer(BlockEntityRendererFactory.Context context) { - this.context = context; + super(context); this.model = new OilPumpJackModel(context.getLayerModelPart(OilPumpJackModel.LAYER_LOCATION)); this.parts = this.model.getOilPumpJackParts(); } - @Override - public void render(OilPumpJackBlockEntity entity, float tickDelta, MatrixStack matrices, VertexConsumerProvider vertexConsumers, int light, int overlay, Vec3d cameraPos) { - matrices.push(); - matrices.translate(0.5f, 1.5f, 0.5f); - matrices.multiply(RotationAxis.POSITIVE_X.rotationDegrees(180)); - - matrices.multiply(RotationAxis.POSITIVE_Y.rotationDegrees(180 + switch (entity.getCachedState().get(Properties.HORIZONTAL_FACING)) { - case EAST -> 90; - case SOUTH -> 180; - case WEST -> 270; - default -> 0; - })); + @Override + protected void renderModel(OilPumpJackBlockEntity entity, float tickDelta, MatrixStack matrices, VertexConsumerProvider vertexConsumers, int light, int overlay) { float clientRotation = entity.clientRotation; if (entity.isRunning()) { clientRotation = clientRotation + 0.1f * tickDelta; @@ -80,10 +70,9 @@ public void render(OilPumpJackBlockEntity entity, float tickDelta, MatrixStack m // Draw bridle drawBridle(matrices, vertexConsumers, attachmentBPosition, attachmentCPosition, attachmentDPosition); - VertexConsumer vertexConsumer = vertexConsumers.getBuffer(this.model.getLayer(OilPumpJackModel.TEXTURE_LOCATION)); this.model.render(matrices, vertexConsumer, light, overlay); - matrices.pop(); + // Reset values parts.wheel().pitch = previousWheelPitch; @@ -92,6 +81,11 @@ public void render(OilPumpJackBlockEntity entity, float tickDelta, MatrixStack m parts.arm().pitch = previousArmPitch; } + @Override + protected void onRender(OilPumpJackBlockEntity entity, float tickDelta, MatrixStack matrices, VertexConsumerProvider vertexConsumers, int light, int overlay) { + + } + private void drawBridle(MatrixStack matrices, VertexConsumerProvider vertexConsumers, Vector3f attachmentBPosition, Vector3f attachmentCPosition, Vector3f attachmentDPosition) { matrices.push(); matrices.translate(0, 1.5f, 0); diff --git a/src/client/java/dev/turtywurty/industria/renderer/block/RotaryKilnBlockEntityRenderer.java b/src/client/java/dev/turtywurty/industria/renderer/block/RotaryKilnBlockEntityRenderer.java index 6234cb8..341d412 100644 --- a/src/client/java/dev/turtywurty/industria/renderer/block/RotaryKilnBlockEntityRenderer.java +++ b/src/client/java/dev/turtywurty/industria/renderer/block/RotaryKilnBlockEntityRenderer.java @@ -11,18 +11,23 @@ import net.minecraft.item.BlockItem; import net.minecraft.item.ItemDisplayContext; import net.minecraft.item.ItemStack; +import net.minecraft.particle.ParticleEffect; +import net.minecraft.particle.ParticleTypes; import net.minecraft.util.math.BlockPos; import net.minecraft.util.math.Direction; import net.minecraft.util.math.MathHelper; import net.minecraft.util.math.RotationAxis; +import org.jbox2d.callbacks.ContactImpulse; +import org.jbox2d.callbacks.ContactListener; +import org.jbox2d.collision.Manifold; import org.jbox2d.collision.shapes.ChainShape; import org.jbox2d.collision.shapes.PolygonShape; import org.jbox2d.common.Vec2; import org.jbox2d.dynamics.*; +import org.jbox2d.dynamics.contacts.Contact; +import org.joml.Vector3f; -import java.util.HashMap; -import java.util.Iterator; -import java.util.Map; +import java.util.*; import java.util.concurrent.ConcurrentHashMap; public class RotaryKilnBlockEntityRenderer extends IndustriaBlockEntityRenderer { @@ -45,7 +50,7 @@ public RotaryKilnBlockEntityRenderer(BlockEntityRendererFactory.Context context) } @Override - protected void onRender(RotaryKilnControllerBlockEntity entity, float tickDelta, MatrixStack matrices, VertexConsumerProvider vertexConsumers, int light, int overlay) { + protected void renderModel(RotaryKilnControllerBlockEntity entity, float tickDelta, MatrixStack matrices, VertexConsumerProvider vertexConsumers, int light, int overlay) { VertexConsumer vertexConsumer = vertexConsumers.getBuffer(this.model.getLayer(RotaryKilnModel.TEXTURE_LOCATION)); this.model.renderSegment(0, matrices, vertexConsumer, light, overlay); @@ -65,18 +70,21 @@ protected void onRender(RotaryKilnControllerBlockEntity entity, float tickDelta, this.model.renderSegment(segmentIndex, matrices, vertexConsumer, light, overlay); rotatingSegment.roll = 0; } - - matrices.translate(0, -1, 0); - renderItems(rendererData, entity, tickDelta, matrices, vertexConsumers, light, overlay); } - private void renderItems(RendererData rendererData, RotaryKilnControllerBlockEntity entity, float tickDelta, MatrixStack matrices, VertexConsumerProvider vertexConsumers, int light, int overlay) { + @Override + protected void onRender(RotaryKilnControllerBlockEntity entity, float tickDelta, MatrixStack matrices, VertexConsumerProvider vertexConsumers, int light, int overlay) { + RendererData rendererData = BLOCK_POS_RENDERER_DATA_MAP.computeIfAbsent(entity.getPos(), pos -> new RendererData()); + Map recipeToBodyMap = rendererData.recipeToBodyMap; World box2dWorld = rendererData.box2dWorld; long now = System.nanoTime(); float deltaTime = (now - rendererData.lastRenderTime) / 1_000_000_000f; // seconds + + deltaTime = MathHelper.clamp(deltaTime, 0.01f, 0.1f); + rendererData.lastRenderTime = now; box2dWorld.step(deltaTime, 6, 2); @@ -86,6 +94,7 @@ private void renderItems(RendererData rendererData, RotaryKilnControllerBlockEnt if (!entity.getRecipes().contains(entry.getKey())) { box2dWorld.destroyBody(entry.getValue()); + rendererData.collidedBodies.remove(entry.getValue()); iterator.remove(); } } @@ -102,12 +111,16 @@ private void renderItems(RendererData rendererData, RotaryKilnControllerBlockEnt matrices.push(); matrices.translate(body.getPosition().x, body.getPosition().y, z); - - matrices.push(); matrices.scale(0.5f, 0.5f, 0.5f); matrices.multiply(Direction.WEST.getRotationQuaternion()); matrices.multiply(RotationAxis.POSITIVE_X.rotation(body.getAngle())); this.context.getItemRenderer().renderItem(itemStack, ItemDisplayContext.NONE, light, overlay, matrices, vertexConsumers, entity.getWorld(), 0); + + if (rendererData.collidedBodies.remove(body)) { + Vector3f position = matrixStackToWorldPosition(matrices); + entity.getWorld().addParticleClient(ParticleTypes.SMOKE, position.x, position.y, position.z, 0, 0, 0); + } + matrices.pop(); } } @@ -122,6 +135,7 @@ private Body createNewItemBody(World box2dWorld, ItemStack itemStack) { Body box = box2dWorld.createBody(squareDef); box.setGravityScale(1f); box.setLinearVelocity(new Vec2(((float) Math.random() - 0.5f) * 2f, ((float) Math.random() - 0.5f) * 2f)); + box.setUserData("item"); var squareShape = new PolygonShape(); if (blockItem) { @@ -154,9 +168,32 @@ public static final class RendererData { private final Body barrelBody; private long lastRenderTime = System.nanoTime(); + private final Set collidedBodies = Collections.synchronizedSet(new HashSet<>()); public RendererData() { box2dWorld = new World(new Vec2(0, GRAVITY)); + box2dWorld.setContactListener(new ContactListener() { + @Override + public void beginContact(Contact contact) { + Body a = contact.getFixtureA().getBody(); + Body b = contact.getFixtureB().getBody(); + + if (a.getUserData() != null && a.getUserData().equals("item")) + collidedBodies.add(a); + + if (b.getUserData() != null && b.getUserData().equals("item")) + collidedBodies.add(b); + } + + @Override + public void endContact(Contact contact) {} + + @Override + public void preSolve(Contact contact, Manifold oldManifold) {} + + @Override + public void postSolve(Contact contact, ContactImpulse impulse) {} + }); var barrelDef = new BodyDef(); barrelDef.type = BodyType.KINEMATIC; diff --git a/src/client/java/dev/turtywurty/industria/renderer/block/ShakingTableBlockEntityRenderer.java b/src/client/java/dev/turtywurty/industria/renderer/block/ShakingTableBlockEntityRenderer.java index 41b2549..6e91857 100644 --- a/src/client/java/dev/turtywurty/industria/renderer/block/ShakingTableBlockEntityRenderer.java +++ b/src/client/java/dev/turtywurty/industria/renderer/block/ShakingTableBlockEntityRenderer.java @@ -9,11 +9,8 @@ import net.minecraft.client.render.*; import net.minecraft.client.render.block.entity.BlockEntityRendererFactory; import net.minecraft.client.util.math.MatrixStack; -import net.minecraft.item.Item; import net.minecraft.item.ItemDisplayContext; import net.minecraft.item.ItemStack; -import net.minecraft.item.Items; -import net.minecraft.util.Pair; import net.minecraft.util.math.Box; import net.minecraft.util.math.MathHelper; import net.minecraft.util.math.RotationAxis; @@ -29,26 +26,34 @@ public ShakingTableBlockEntityRenderer(BlockEntityRendererFactory.Context contex this.model = new ShakingTableModel(context.getLayerModelPart(ShakingTableModel.LAYER_LOCATION)); } - @Override - protected void onRender(ShakingTableBlockEntity entity, float tickDelta, MatrixStack matrices, VertexConsumerProvider vertexConsumers, int light, int overlay) { + private float getShakeOffset(ShakingTableBlockEntity entity) { float shakesPerSecond = entity.getRecipeFrequency(); + + float time = entity.getWorld().getTime(); + float frequency = shakesPerSecond * (float) Math.PI; + float shakeAmount = 2f; + + return (float) Math.sin(time * frequency) * shakeAmount; + } + + @Override + protected void renderModel(ShakingTableBlockEntity entity, float tickDelta, MatrixStack matrices, VertexConsumerProvider vertexConsumers, int light, int overlay) { int progress = entity.getProgress(); int maxProgress = entity.getMaxProgress(); - float shakeOffset = 0.0f; float previousOriginZ = this.model.getModelParts().table().originZ; - if (progress > 0 && progress < maxProgress) { - float time = tickDelta + entity.getWorld().getTime(); - float frequency = shakesPerSecond * (float) Math.PI; - float shakeAmount = 2f; - shakeOffset = (float) Math.sin(time * frequency) * shakeAmount; - this.model.getModelParts().table().originZ += shakeOffset; + if (progress > 0 && progress < maxProgress) { + this.model.getModelParts().table().originZ += getShakeOffset(entity); } this.model.render(matrices, vertexConsumers.getBuffer(this.model.getLayer(ShakingTableModel.TEXTURE_LOCATION)), light, overlay); this.model.getModelParts().table().originZ = previousOriginZ; + } + @Override + protected void onRender(ShakingTableBlockEntity entity, float tickDelta, MatrixStack matrices, VertexConsumerProvider vertexConsumers, int light, int overlay) { + float shakeOffset = getShakeOffset(entity); renderGutterFluids(entity, matrices, vertexConsumers, light, overlay, shakeOffset); @@ -65,12 +70,7 @@ protected void postRender(ShakingTableBlockEntity entity, float tickDelta, Matri shakeBox = shakeBox.offset(-entity.getPos().getX(), -entity.getPos().getY(), -entity.getPos().getZ()); if (shakeBox != null) { VertexConsumer vertexConsumer = vertexConsumers.getBuffer(RenderLayer.getLines()); - VertexRendering.drawBox( - matrices, - vertexConsumer, - shakeBox, - 1.0f, 1.0f, 1.0f, 1.0f - ); + VertexRendering.drawBox(matrices, vertexConsumer, shakeBox, 1.0f, 1.0f, 1.0f, 1.0f); } } } @@ -96,16 +96,7 @@ private void renderItemStacks(ShakingTableBlockEntity entity, MatrixStack matric matrices.translate(x, y, z); matrices.scale(0.5f, 0.5f, 0.5f); matrices.multiply(RotationAxis.POSITIVE_X.rotationDegrees(90)); - this.context.getItemRenderer().renderItem( - processingStack, - ItemDisplayContext.GROUND, - light, - overlay, - matrices, - vertexConsumers, - entity.getWorld(), - 0 - ); + this.context.getItemRenderer().renderItem(processingStack, ItemDisplayContext.GROUND, light, overlay, matrices, vertexConsumers, entity.getWorld(), 0); matrices.pop(); } @@ -120,9 +111,9 @@ private Vec2f renderSurfaceFluid(ShakingTableBlockEntity entity, MatrixStack mat float totalVolume = 3f; float width = 3f; - float minX = 1 + 1/16f; + float minX = 1 + 1 / 16f; float startX = minX - 0.4f; - float endX = -(1 + 2/16f); + float endX = -(1 + 2 / 16f); float fluidX = MathHelper.lerp(progress, startX, endX); @@ -131,7 +122,7 @@ private Vec2f renderSurfaceFluid(ShakingTableBlockEntity entity, MatrixStack mat matrices.push(); matrices.translate(0, 0.0f, shakeOffset / 16f); - this.fluidRenderer.render(entity.getInputFluidTank(), + this.fluidRenderer.renderFluidTank(entity.getInputFluidTank(), vertexConsumers, matrices, light, overlay, entity.getWorld(), entity.getPos(), @@ -155,7 +146,7 @@ private void renderGutterFluids(ShakingTableBlockEntity entity, MatrixStack matr float z1 = -1f - 1f / 16f; float x2 = 1f + 1f / 16f; float z2 = -5f / 16f; - this.fluidRenderer.render(entity.getInputFluidTank(), + this.fluidRenderer.renderFluidTank(entity.getInputFluidTank(), vertexConsumers, matrices, light, overlay, entity.getWorld(), entity.getPos(), @@ -170,7 +161,7 @@ private void renderGutterFluids(ShakingTableBlockEntity entity, MatrixStack matr float z1 = -1f / 16f; float x2 = 1f + 1f / 16f; float z2 = 1 + 2f / 16f; - this.fluidRenderer.render(entity.getInputFluidTank(), + this.fluidRenderer.renderFluidTank(entity.getInputFluidTank(), vertexConsumers, matrices, light, overlay, entity.getWorld(), entity.getPos(), diff --git a/src/client/java/dev/turtywurty/industria/renderer/block/UpgradeStationBlockEntityRenderer.java b/src/client/java/dev/turtywurty/industria/renderer/block/UpgradeStationBlockEntityRenderer.java index 4299ddf..bb56f24 100644 --- a/src/client/java/dev/turtywurty/industria/renderer/block/UpgradeStationBlockEntityRenderer.java +++ b/src/client/java/dev/turtywurty/industria/renderer/block/UpgradeStationBlockEntityRenderer.java @@ -10,30 +10,23 @@ import net.minecraft.util.math.RotationAxis; import net.minecraft.util.math.Vec3d; -public class UpgradeStationBlockEntityRenderer implements BlockEntityRenderer { - private final BlockEntityRendererFactory.Context context; +public class UpgradeStationBlockEntityRenderer extends IndustriaBlockEntityRenderer { + private final UpgradeStationModel model; public UpgradeStationBlockEntityRenderer(BlockEntityRendererFactory.Context context) { - this.context = context; + super(context); this.model = new UpgradeStationModel(context.getLayerModelPart(UpgradeStationModel.LAYER_LOCATION)); } @Override - public void render(UpgradeStationBlockEntity entity, float tickDelta, MatrixStack matrices, VertexConsumerProvider vertexConsumers, int light, int overlay, Vec3d cameraPos) { - matrices.push(); - matrices.translate(0.5f, 1.5f, 0.5f); - matrices.multiply(RotationAxis.POSITIVE_X.rotationDegrees(180)); - - matrices.multiply(RotationAxis.POSITIVE_Y.rotationDegrees(180 + switch (entity.getCachedState().get(Properties.HORIZONTAL_FACING)) { - case EAST -> 90; - case SOUTH -> 180; - case WEST -> 270; - default -> 0; - })); - + protected void renderModel(UpgradeStationBlockEntity entity, float tickDelta, MatrixStack matrices, VertexConsumerProvider vertexConsumers, int light, int overlay) { this.model.render(matrices, vertexConsumers.getBuffer(this.model.getLayer(UpgradeStationModel.TEXTURE_LOCATION)), light, overlay); - matrices.pop(); + } + + @Override + protected void onRender(UpgradeStationBlockEntity entity, float tickDelta, MatrixStack matrices, VertexConsumerProvider vertexConsumers, int light, int overlay) { + } } diff --git a/src/client/java/dev/turtywurty/industria/renderer/block/WindTurbineBlockEntityRenderer.java b/src/client/java/dev/turtywurty/industria/renderer/block/WindTurbineBlockEntityRenderer.java index b121e37..a3c1479 100644 --- a/src/client/java/dev/turtywurty/industria/renderer/block/WindTurbineBlockEntityRenderer.java +++ b/src/client/java/dev/turtywurty/industria/renderer/block/WindTurbineBlockEntityRenderer.java @@ -12,29 +12,18 @@ import net.minecraft.util.math.RotationAxis; import net.minecraft.util.math.Vec3d; -public class WindTurbineBlockEntityRenderer implements BlockEntityRenderer { - private final BlockEntityRendererFactory.Context context; +public class WindTurbineBlockEntityRenderer extends IndustriaBlockEntityRenderer { + private final WindTurbineModel model; public WindTurbineBlockEntityRenderer(BlockEntityRendererFactory.Context context) { - this.context = context; + super(context); this.model = new WindTurbineModel(context.getLayerModelPart(WindTurbineModel.LAYER_LOCATION)); } @Override - public void render(WindTurbineBlockEntity entity, float tickDelta, MatrixStack matrices, VertexConsumerProvider vertexConsumers, int light, int overlay, Vec3d cameraPos) { - matrices.push(); - matrices.translate(0.5f, 1.5f, 0.5f); - matrices.multiply(RotationAxis.POSITIVE_X.rotationDegrees(180)); - - matrices.multiply(RotationAxis.POSITIVE_Y.rotationDegrees(180 + switch (entity.getCachedState().get(Properties.HORIZONTAL_FACING)) { - case EAST -> 90; - case SOUTH -> 180; - case WEST -> 270; - default -> 0; - })); - + protected void renderModel(WindTurbineBlockEntity entity, float tickDelta, MatrixStack matrices, VertexConsumerProvider vertexConsumers, int light, int overlay) { float outputPercentage = getEnergyPerTickPercent(entity); entity.setPropellerRotation(entity.getPropellerRotation() + (outputPercentage * 0.25f)); model.getWindTurbineParts().propellers().roll = entity.getPropellerRotation(); @@ -42,7 +31,11 @@ public void render(WindTurbineBlockEntity entity, float tickDelta, MatrixStack m VertexConsumer consumer = vertexConsumers.getBuffer(this.model.getLayer(WindTurbineModel.TEXTURE_LOCATION)); this.model.render(matrices, consumer, light, overlay); this.model.getWindTurbineParts().propellers().roll = 0.0F; - matrices.pop(); + } + + @Override + protected void onRender(WindTurbineBlockEntity entity, float tickDelta, MatrixStack matrices, VertexConsumerProvider vertexConsumers, int light, int overlay) { + } public int getEnergyPerTick(WindTurbineBlockEntity blockEntity) { diff --git a/src/client/java/dev/turtywurty/industria/util/InWorldFluidRenderingComponent.java b/src/client/java/dev/turtywurty/industria/util/InWorldFluidRenderingComponent.java index 4a96761..f4a9721 100644 --- a/src/client/java/dev/turtywurty/industria/util/InWorldFluidRenderingComponent.java +++ b/src/client/java/dev/turtywurty/industria/util/InWorldFluidRenderingComponent.java @@ -9,52 +9,56 @@ import net.minecraft.client.render.VertexConsumerProvider; import net.minecraft.client.texture.Sprite; import net.minecraft.client.util.math.MatrixStack; +import net.minecraft.fluid.Fluids; import net.minecraft.util.math.BlockPos; +import net.minecraft.util.math.Direction; import net.minecraft.util.math.MathHelper; import net.minecraft.util.math.RotationAxis; import net.minecraft.world.World; import org.jetbrains.annotations.Nullable; +import org.joml.Vector3f; import java.util.function.UnaryOperator; public class InWorldFluidRenderingComponent { + private boolean shouldDebugAmount = false; public void setShouldDebugAmount(boolean shouldDebugAmount) { this.shouldDebugAmount = shouldDebugAmount; } - public void render(@Nullable SingleFluidStorage fluidTank, VertexConsumerProvider vertexConsumers, MatrixStack matrices, int light, int overlay, World world, BlockPos pos, float x1, float y1, float z1, float x2, float maxHeightPixels, float z2) { - render(fluidTank, vertexConsumers, matrices, light, overlay, world, pos, x1, y1, z1, x2, maxHeightPixels, z2, IndeterminateBoolean.INDETERMINATE); + public void renderFluidTank(@Nullable SingleFluidStorage fluidTank, VertexConsumerProvider vertexConsumers, MatrixStack matrices, int light, int overlay, World world, BlockPos pos, float x1, float y1, float z1, float x2, float maxHeightPixels, float z2) { + renderFluidTank(fluidTank, vertexConsumers, matrices, light, overlay, world, pos, x1, y1, z1, x2, maxHeightPixels, z2, IndeterminateBoolean.INDETERMINATE); } - public void render(@Nullable SingleFluidStorage fluidTank, VertexConsumerProvider vertexConsumers, MatrixStack matrices, int light, int overlay, World world, BlockPos pos, float x1, float y1, float z1, float x2, float maxHeightPixels, float z2, IndeterminateBoolean drawTopFace) { - render(fluidTank, vertexConsumers, matrices, light, overlay, world, pos, x1, y1, z1, x2, maxHeightPixels, z2, 0xFFFFFFFF, ColorMode.MULTIPLICATION, drawTopFace); + public void renderFluidTank(@Nullable SingleFluidStorage fluidTank, VertexConsumerProvider vertexConsumers, MatrixStack matrices, int light, int overlay, World world, BlockPos pos, float x1, float y1, float z1, float x2, float maxHeightPixels, float z2, IndeterminateBoolean drawTopFace) { + renderFluidTank(fluidTank, vertexConsumers, matrices, light, overlay, world, pos, x1, y1, z1, x2, maxHeightPixels, z2, 0xFFFFFFFF, ColorMode.MULTIPLICATION, drawTopFace); } - public void render(@Nullable SingleFluidStorage fluidTank, VertexConsumerProvider vertexConsumers, MatrixStack matrices, int light, int overlay, World world, BlockPos pos, float x1, float y1, float z1, float x2, float maxHeightPixels, float z2, int color, ColorMode colorMode) { - render(fluidTank, vertexConsumers, matrices, light, overlay, world, pos, x1, y1, z1, x2, maxHeightPixels, z2, color, colorMode, IndeterminateBoolean.INDETERMINATE); + public void renderFluidTank(@Nullable SingleFluidStorage fluidTank, VertexConsumerProvider vertexConsumers, MatrixStack matrices, int light, int overlay, World world, BlockPos pos, float x1, float y1, float z1, float x2, float maxHeightPixels, float z2, int color, ColorMode colorMode) { + renderFluidTank(fluidTank, vertexConsumers, matrices, light, overlay, world, pos, x1, y1, z1, x2, maxHeightPixels, z2, color, colorMode, IndeterminateBoolean.INDETERMINATE); } - public void render(@Nullable SingleFluidStorage fluidTank, VertexConsumerProvider vertexConsumers, MatrixStack matrices, int light, int overlay, World world, BlockPos pos, float x1, float y1, float z1, float x2, float maxHeightPixels, float z2, int color, ColorMode colorMode, IndeterminateBoolean drawTopFace) { - if (fluidTank == null || fluidTank.isResourceBlank() || fluidTank.amount <= 0) - return; + public void renderFluidTank(@Nullable SingleFluidStorage fluidTank, VertexConsumerProvider vertexConsumers, MatrixStack matrices, int light, int overlay, World world, BlockPos pos, float x1, float y1, float z1, float x2, float maxHeightPixels, float z2, int color, ColorMode colorMode, IndeterminateBoolean drawTopFace) { + // if (fluidTank == null || fluidTank.isResourceBlank() || fluidTank.amount <= 0) return; - FluidVariant fluidVariant = fluidTank.getResource(); + FluidVariant fluidVariant = FluidVariant.of(Fluids.WATER); //fluidTank.getResource(); long amount = fluidTank.amount; long capacity = fluidTank.getCapacity(); - float fillPercentage = (float) amount / capacity; + float fillPercentage = (float) (Math.sin(world.getTime() / 20.0) * 0.5 + 0.5); + ; //(float) amount / capacity; fillPercentage = MathHelper.clamp(fillPercentage, 0.0F, 1.0F); - if(this.shouldDebugAmount) { - fillPercentage = (float) (Math.sin(world.getTime() / 64.0) * 0.5 + 0.5); + if (this.shouldDebugAmount) { + fillPercentage = (float) (Math.sin(world.getTime() / 64f) * 0.5 + 0.5); } int fluidColor = FluidVariantRendering.getColor(fluidVariant, world, pos); fluidColor = ColorMode.modifyColor(fluidColor, color, colorMode); Sprite stillSprite = FluidVariantRendering.getSprite(fluidVariant); - if(stillSprite == null) + if (stillSprite == null) return; RenderLayer renderLayer = RenderLayer.getItemEntityTranslucentCull(stillSprite.getAtlasId()); @@ -63,541 +67,305 @@ public void render(@Nullable SingleFluidStorage fluidTank, VertexConsumerProvide float y2 = ((fillPercentage * maxHeightPixels) / 16f) + y1; matrices.push(); - matrices.multiply(RotationAxis.POSITIVE_X.rotationDegrees(180)); if (FluidVariantAttributes.isLighterThanAir(fluidVariant)) { matrices.multiply(RotationAxis.POSITIVE_X.rotationDegrees(180)); } - MatrixStack.Entry entry = matrices.peek(); - int blockLight = (light >> 4) & 0xF; int luminosity = Math.max(blockLight, FluidVariantAttributes.getLuminance(fluidVariant)); light = (light & 0xF00000) | (luminosity << 4); - // Front (XY plane, z constant) - drawTiledXYQuad(vertexConsumer, entry, - x1, y1, z1 + 0.001F, - x2, y2, z1 + 0.001F, - stillSprite, fluidColor, light, overlay, 0.0F, 1.0F, -1.0F); - - // Back (XY plane, z constant) - drawReversedTiledXYQuad(vertexConsumer, entry, - x1, y1, z2 - 0.001F, - x2, y2, z2 - 0.001F, - stillSprite, fluidColor, light, overlay, 0.0F, 1.0F, 1.0F); - - // Left (YZ plane, x constant) - drawReversedTiledYZQuad(vertexConsumer, entry, - x1 + 0.001F, y1, z1, - y2, z2, - stillSprite, fluidColor, light, overlay, 1.0F, 1.0F, 0.0F); - - // Right (YZ plane, x constant) - drawTiledYZQuad(vertexConsumer, entry, - x2 - 0.001F, y1, z1, - y2, z2, - stillSprite, fluidColor, light, overlay, -1.0F, 1.0F, 0.0F); - - if (drawTopFace.evaluate(fillPercentage < 1.0F)) { - drawTiledTopQuad(vertexConsumer, entry, x1, y2, z1 + 0.001F, x2, z2 - 0.001F, stillSprite, fluidColor, light, overlay); - } - - matrices.pop(); - } - - public void renderTopFaceOnly(@Nullable FluidVariant fluidVariant, VertexConsumerProvider vertexConsumers, MatrixStack matrices, int light, int overlay, World world, BlockPos pos, float x1, float y, float z1, float x2, float z2, UnaryOperator wrapRenderLayer) { - renderTopFaceOnly(fluidVariant, vertexConsumers, matrices, light, overlay, world, pos, x1, y, z1, x2, z2, 0xFFFFFFFF, ColorMode.MULTIPLICATION, wrapRenderLayer); - } - - public void renderTopFaceOnly(@Nullable FluidVariant fluidVariant, VertexConsumerProvider vertexConsumers, MatrixStack matrices, int light, int overlay, World world, BlockPos pos, float x1, float y, float z1, float x2, float z2) { - renderTopFaceOnly(fluidVariant, vertexConsumers, matrices, light, overlay, world, pos, x1, y, z1, x2, z2, 0xFFFFFFFF, ColorMode.MULTIPLICATION); - } - - public void renderTopFaceOnly(@Nullable FluidVariant fluidVariant, VertexConsumerProvider vertexConsumers, MatrixStack matrices, int light, int overlay, World world, BlockPos pos, float x1, float y, float z1, float x2, float z2, int color, ColorMode colorMode) { - renderTopFaceOnly(fluidVariant, vertexConsumers, matrices, light, overlay, world, pos, x1, y, z1, x2, z2, color, colorMode, renderLayer -> renderLayer); - } + renderDirectionalTiledQuad(Direction.NORTH, vertexConsumer, matrices, + x1, x2, y1, y2, z1 + 0.01f, + stillSprite, fluidColor, light, overlay); - public void renderTopFaceOnly(@Nullable FluidVariant fluidVariant, VertexConsumerProvider vertexConsumers, MatrixStack matrices, int light, int overlay, World world, BlockPos pos, float x1, float y, float z1, float x2, float z2, int color, ColorMode colorMode, UnaryOperator wrapRenderLayer) { - if (fluidVariant == null) - return; + renderDirectionalTiledQuad(Direction.SOUTH, vertexConsumer, matrices, + x1, x2, y1, y2, z2 - 0.01f, + stillSprite, fluidColor, light, overlay); - int fluidColor = FluidVariantRendering.getColor(fluidVariant, world, pos); - fluidColor = ColorMode.modifyColor(fluidColor, color, colorMode); - - Sprite stillSprite = FluidVariantRendering.getSprite(fluidVariant); - if(stillSprite == null) - return; - - RenderLayer renderLayer = RenderLayer.getItemEntityTranslucentCull(stillSprite.getAtlasId()); - renderLayer = wrapRenderLayer.apply(renderLayer); - VertexConsumer vertexConsumer = vertexConsumers.getBuffer(renderLayer); + renderDirectionalTiledQuad(Direction.WEST, vertexConsumer, matrices, + z1, z2, y1, y2, x1 + 0.01f, + stillSprite, fluidColor, light, overlay); - matrices.push(); - matrices.multiply(RotationAxis.POSITIVE_X.rotationDegrees(180)); + renderDirectionalTiledQuad(Direction.EAST, vertexConsumer, matrices, + z1, z2, y1, y2, x2 - 0.01f, + stillSprite, fluidColor, light, overlay); - if (FluidVariantAttributes.isLighterThanAir(fluidVariant)) { - matrices.multiply(RotationAxis.POSITIVE_X.rotationDegrees(180)); - } + if (drawTopFace.evaluate(fillPercentage < 1.0F)) + renderDirectionalTiledQuad(Direction.UP, vertexConsumer, matrices, + x1, x2, z1, z2, y2, stillSprite, fluidColor, light, overlay); - MatrixStack.Entry entry = matrices.peek(); - int blockLight = (light >> 4) & 0xF; - int luminosity = Math.max(blockLight, FluidVariantAttributes.getLuminance(fluidVariant)); - light = (light & 0xF00000) | (luminosity << 4); + matrices.pop(); + } - drawTiledTopQuad(vertexConsumer, entry, x1, y, z1 + 0.001F, x2, z2 - 0.001F, stillSprite, fluidColor, light, overlay); + // Calls the full renderFace with default color and color mode + public void renderFace(Direction direction, @Nullable FluidVariant fluidVariant, VertexConsumerProvider vertexConsumers, MatrixStack matrices, + int light, int overlay, World world, BlockPos pos, + float left, float right, float up, float down, float depth, + UnaryOperator wrapRenderLayer) { - matrices.pop(); + renderFace(direction, fluidVariant, vertexConsumers, matrices, light, overlay, world, pos, + left, right, up, down, depth, + 0xFFFFFFFF, ColorMode.MULTIPLICATION, wrapRenderLayer); } - public static void drawTiledTopQuad(VertexConsumer vertexConsumer, - MatrixStack.Entry entry, - float x1, float y, float z1, - float x2, float z2, - Sprite sprite, - int color, - int light, int overlay) { - float tileSize = 1.0f; // Maximum tile size in world space - int tileCountX = Math.max(1, Math.round((x2 - x1) / tileSize)); - int tileCountZ = Math.max(1, Math.round((z2 - z1) / tileSize)); + // Calls the full renderFace with default color, color mode, and identity render layer + public void renderFace(Direction direction, @Nullable FluidVariant fluidVariant, VertexConsumerProvider vertexConsumers, MatrixStack matrices, + int light, int overlay, World world, BlockPos pos, + float left, float right, float up, float down, float depth) { - float tileWidth = (x2 - x1) / tileCountX; - float tileDepth = (z2 - z1) / tileCountZ; + renderFace(direction, fluidVariant, vertexConsumers, matrices, light, overlay, world, pos, + left, right, up, down, depth, + 0xFFFFFFFF, ColorMode.MULTIPLICATION); + } - float u0 = sprite.getMinU(); - float v0 = sprite.getMinV(); - float u1 = sprite.getMaxU(); - float v1 = sprite.getMaxV(); - float tileUSize = (u1 - u0); - float tileVSize = (v1 - v0); + public void renderFace(Direction direction, @Nullable FluidVariant fluidVariant, VertexConsumerProvider vertexConsumers, MatrixStack matrices, + int light, int overlay, World world, BlockPos pos, + float left, float right, float up, float down, float depth, + int color, ColorMode colorMode) { - for (int i = 0; i < tileCountX; i++) { - for (int j = 0; j < tileCountZ; j++) { - float xStart = x1 + i * tileWidth; - float xEnd = xStart + tileWidth; - float zStart = z1 + j * tileDepth; - float zEnd = zStart + tileDepth; - - float uEnd = u0 + tileUSize; - float vEnd = v0 + tileVSize; - - vertexConsumer.vertex(entry, xStart, y, zStart) - .color(color) - .texture(u0, v0) - .light(light) - .overlay(overlay) - .normal(0.0F, 1.0F, 0.0F); - - vertexConsumer.vertex(entry, xStart, y, zEnd) - .color(color) - .texture(u0, vEnd) - .light(light) - .overlay(overlay) - .normal(0.0F, 1.0F, 0.0F); - - vertexConsumer.vertex(entry, xEnd, y, zEnd) - .color(color) - .texture(uEnd, vEnd) - .light(light) - .overlay(overlay) - .normal(0.0F, 1.0F, 0.0F); - - vertexConsumer.vertex(entry, xEnd, y, zStart) - .color(color) - .texture(uEnd, v0) - .light(light) - .overlay(overlay) - .normal(entry, 0.0F, 1.0F, 0.0F); - } - } + renderFace(direction, fluidVariant, vertexConsumers, matrices, light, overlay, world, pos, + left, right, up, down, depth, + color, colorMode, renderLayer -> renderLayer); } - public void drawTiledXYQuadOnly(@Nullable FluidVariant fluidVariant, VertexConsumerProvider vertexConsumers, MatrixStack matrices, int light, int overlay, World world, BlockPos pos, float x1, float y1, float z1, float x2, float y2, float z2) { - drawTiledXYQuadOnly(fluidVariant, vertexConsumers, matrices, light, overlay, world, pos, x1, y1, z1, x2, y2, z2, 0xFFFFFFFF, ColorMode.MULTIPLICATION); - } - public void drawTiledXYQuadOnly(@Nullable FluidVariant fluidVariant, VertexConsumerProvider vertexConsumers, MatrixStack matrices, int light, int overlay, World world, BlockPos pos, float x1, float y1, float z1, float x2, float y2, float z2, int color, ColorMode colorMode) { - if (fluidVariant == null) - return; + public void renderFace(Direction direction, @Nullable FluidVariant fluidVariant, VertexConsumerProvider vertexConsumers, MatrixStack matrices, int light, int overlay, World world, BlockPos pos, float left, float right, float up, float down, float depth, int color, ColorMode colorMode, UnaryOperator wrapRenderLayer) { + if (fluidVariant == null) return; + + Sprite stillSprite = FluidVariantRendering.getSprite(fluidVariant); + if (stillSprite == null) return; int fluidColor = FluidVariantRendering.getColor(fluidVariant, world, pos); fluidColor = ColorMode.modifyColor(fluidColor, color, colorMode); - Sprite stillSprite = FluidVariantRendering.getSprite(fluidVariant); - if(stillSprite == null) - return; - RenderLayer renderLayer = RenderLayer.getItemEntityTranslucentCull(stillSprite.getAtlasId()); + renderLayer = wrapRenderLayer.apply(renderLayer); VertexConsumer vertexConsumer = vertexConsumers.getBuffer(renderLayer); matrices.push(); - matrices.multiply(RotationAxis.POSITIVE_X.rotationDegrees(180)); if (FluidVariantAttributes.isLighterThanAir(fluidVariant)) { matrices.multiply(RotationAxis.POSITIVE_X.rotationDegrees(180)); } - MatrixStack.Entry entry = matrices.peek(); - int blockLight = (light >> 4) & 0xF; int luminosity = Math.max(blockLight, FluidVariantAttributes.getLuminance(fluidVariant)); light = (light & 0xF00000) | (luminosity << 4); - drawTiledXYQuad(vertexConsumer, entry, x1, y1, z1, x2, y2, z2, stillSprite, fluidColor, light, overlay, 0.0F, 1.0F, -1.0F); + renderDirectionalTiledQuad(direction, vertexConsumer, matrices, left, depth, up, right, down, stillSprite, fluidColor, light, overlay); matrices.pop(); } - // For front and back (XY plane) - public static void drawTiledXYQuad(VertexConsumer vertexConsumer, - MatrixStack.Entry entry, - float x1, float y1, float z1, - float x2, float y2, float z2, - Sprite sprite, - int color, - int light, int overlay, - float nx, float ny, float nz) { - float tileSize = 1.0f; - int fullTilesX = (int) ((x2 - x1) / tileSize); - int fullTilesY = (int) ((y2 - y1) / tileSize); - float leftoverX = (x2 - x1) - (fullTilesX * tileSize); - float leftoverY = (y2 - y1) - (fullTilesY * tileSize); - - // Draw full tiles - for (int i = 0; i < fullTilesX; i++) { - for (int j = 0; j < fullTilesY; j++) { - float xStart = x1 + i * tileSize; - float xEnd = xStart + tileSize; - float yStart = y1 + j * tileSize; - float yEnd = yStart + tileSize; - float u0 = sprite.getMinU(); - float v0 = sprite.getMinV(); - float u1 = sprite.getMaxU(); - float v1 = sprite.getMaxV(); - drawQuad(vertexConsumer, entry, xStart, yStart, z1, xEnd, yEnd, z2, u0, v0, u1, v1, color, light, overlay, nx, ny, nz); - } - } + private static void renderDirectionalTiledQuad(Direction direction, VertexConsumer vertexConsumer, MatrixStack matrices, + float left, float right, float up, float down, float depth, + Sprite sprite, int color, int light, int overlay) { - // Draw leftover tiles in x - if (leftoverX > 0) { - for (int j = 0; j < fullTilesY; j++) { - float xStart = x1 + fullTilesX * tileSize; - float xEnd = xStart + leftoverX; - float yStart = y1 + j * tileSize; - float yEnd = yStart + tileSize; - float u0 = sprite.getMinU(); - float v0 = sprite.getMinV(); - float u1 = sprite.getFrameU(leftoverX); - float v1 = sprite.getFrameV(tileSize); - drawQuad(vertexConsumer, entry, xStart, yStart, z1, xEnd, yEnd, z2, u0, v0, u1, v1, color, light, overlay, nx, ny, nz); - } + // Swap if left > right or up > down + if (left > right) { + float temp = left; + left = right; + right = temp; } - - // Draw leftover tiles in y - if (leftoverY > 0) { - for (int i = 0; i < fullTilesX; i++) { - float xStart = x1 + i * tileSize; - float xEnd = xStart + tileSize; - float yStart = y1 + fullTilesY * tileSize; - float yEnd = yStart + leftoverY; - float u0 = sprite.getMinU(); - float v0 = sprite.getMinV(); - float u1 = sprite.getFrameU(tileSize); - float v1 = sprite.getFrameV(leftoverY); - drawQuad(vertexConsumer, entry, xStart, yStart, z1, xEnd, yEnd, z2, u0, v0, u1, v1, color, light, overlay, nx, ny, nz); - } - - // Draw the corner leftover tile if both leftoverX and leftoverY > 0 - if (leftoverX > 0) { - float xStart = x1 + fullTilesX * tileSize; - float xEnd = xStart + leftoverX; - float yStart = y1 + fullTilesY * tileSize; - float yEnd = yStart + leftoverY; - float u0 = sprite.getMinU(); - float v0 = sprite.getMinV(); - float u1 = sprite.getFrameU(leftoverX); - float v1 = sprite.getFrameV(leftoverY); - drawQuad(vertexConsumer, entry, xStart, yStart, z1, xEnd, yEnd, z2, u0, v0, u1, v1, color, light, overlay, nx, ny, nz); - } + if (up > down) { + float temp = up; + up = down; + down = temp; } - } - // For left and right (YZ plane) - public static void drawTiledYZQuad(VertexConsumer vertexConsumer, - MatrixStack.Entry entry, - float x, float y1, float z1, - float y2, float z2, - Sprite sprite, - int color, - int light, int overlay, - float nx, float ny, float nz) { float tileSize = 1.0f; - int fullTilesZ = (int) ((z2 - z1) / tileSize); - int fullTilesY = (int) ((y2 - y1) / tileSize); - float leftoverZ = (z2 - z1) - (fullTilesZ * tileSize); - float leftoverY = (y2 - y1) - (fullTilesY * tileSize); - - // Draw full tiles - for (int i = 0; i < fullTilesZ; i++) { - for (int j = 0; j < fullTilesY; j++) { - float zStart = z1 + i * tileSize; - float zEnd = zStart + tileSize; - float yStart = y1 + j * tileSize; - float yEnd = yStart + tileSize; - float u0 = sprite.getMinU(); - float v0 = sprite.getMinV(); - float u1 = sprite.getMaxU(); - float v1 = sprite.getMaxV(); - drawQuad(vertexConsumer, entry, x, yStart, zStart, x, yEnd, zEnd, u0, v0, u1, v1, color, light, overlay, nx, ny, nz); - } + float uMin = sprite.getMinU(), uMax = sprite.getMaxU(); + float vMin = sprite.getMinV(), vMax = sprite.getMaxV(); + + float x1, x2, y1, y2, z1, z2; + float uStart = uMin, uEnd = uMax, vStart = vMin, vEnd = vMax; + Vector3f normal; + + // Coordinate and UV setup + switch (direction) { + case UP: + x1 = left; + x2 = right; + y1 = y2 = depth; + z1 = up; + z2 = down; + normal = new Vector3f(0, 1, 0); + break; + case DOWN: + x1 = left; + x2 = right; + y1 = y2 = depth; + z1 = down; + z2 = up; + normal = new Vector3f(0, -1, 0); + uStart = uMax; + uEnd = uMin; + break; + case NORTH: + x1 = right; + x2 = left; + y1 = down; + y2 = up; + z1 = z2 = depth; + normal = new Vector3f(0, 0, -1); + vStart = vMax; + vEnd = vMin; + break; + case SOUTH: + x1 = left; + x2 = right; + y1 = down; + y2 = up; + z1 = z2 = depth; + normal = new Vector3f(0, 0, 1); + uStart = uMax; + uEnd = uMin; + vStart = vMax; + vEnd = vMin; + break; + case WEST: + x1 = x2 = depth; + y1 = down; + y2 = up; + z1 = left; + z2 = right; + normal = new Vector3f(-1, 0, 0); + vStart = vMax; + vEnd = vMin; + break; + case EAST: + x1 = x2 = depth; + y1 = down; + y2 = up; + z1 = right; + z2 = left; + normal = new Vector3f(1, 0, 0); + uStart = uMax; + uEnd = uMin; + vStart = vMax; + vEnd = vMin; + break; + default: + throw new IllegalArgumentException("Invalid direction"); } - // Draw leftover tiles in z - if (leftoverZ > 0) { - for (int j = 0; j < fullTilesY; j++) { - float zStart = z1 + fullTilesZ * tileSize; - float zEnd = zStart + leftoverZ; - float yStart = y1 + j * tileSize; - float yEnd = yStart + tileSize; - float u0 = sprite.getMinU(); - float v0 = sprite.getMinV(); - float u1 = sprite.getFrameU(leftoverZ); - float v1 = sprite.getFrameV(tileSize); - drawQuad(vertexConsumer, entry, x, yStart, zStart, x, yEnd, zEnd, u0, v0, u1, v1, color, light, overlay, nx, ny, nz); - } - } + // Calculate tiling + float tileCountX = Math.max(1, Math.round(Math.abs(x2 - x1) / tileSize)); + float tileCountY = Math.max(1, Math.round(Math.abs(y2 - y1) / tileSize)); + float tileCountZ = Math.max(1, Math.round(Math.abs(z2 - z1) / tileSize)); + float tileWidthX = (x2 - x1) / tileCountX; + float tileWidthY = (y2 - y1) / tileCountY; + float tileWidthZ = (z2 - z1) / tileCountZ; - // Draw leftover tiles in y - if (leftoverY > 0) { - for (int i = 0; i < fullTilesZ; i++) { - float zStart = z1 + i * tileSize; - float zEnd = zStart + tileSize; - float yStart = y1 + fullTilesY * tileSize; - float yEnd = yStart + leftoverY; - float u0 = sprite.getMinU(); - float v0 = sprite.getMinV(); - float u1 = sprite.getFrameU(tileSize); - float v1 = sprite.getFrameV(leftoverY); - drawQuad(vertexConsumer, entry, x, yStart, zStart, x, yEnd, zEnd, u0, v0, u1, v1, color, light, overlay, nx, ny, nz); - } + MatrixStack.Entry entry = matrices.peek(); - // Draw the corner leftover tile if both leftoverZ and leftoverY > 0 - if (leftoverZ > 0) { - float zStart = z1 + fullTilesZ * tileSize; - float zEnd = zStart + leftoverZ; - float yStart = y1 + fullTilesY * tileSize; - float yEnd = yStart + leftoverY; - float u0 = sprite.getMinU(); - float v0 = sprite.getMinV(); - float u1 = sprite.getFrameU(leftoverZ); - float v1 = sprite.getFrameV(leftoverY); - drawQuad(vertexConsumer, entry, x, yStart, zStart, x, yEnd, zEnd, u0, v0, u1, v1, color, light, overlay, nx, ny, nz); - } - } - } - private static void drawQuad(VertexConsumer vertexConsumer, - MatrixStack.Entry entry, - float x1, float y1, float z1, - float x2, float y2, float z2, - float minU, float minV, - float maxU, float maxV, - int color, - int light, int overlay, - float normalX, float normalY, float normalZ) { - vertexConsumer.vertex(entry, x1, y1, z1) - .color(color) - .texture(minU, minV) - .light(light) - .overlay(overlay) - .normal(normalX, normalY, normalZ); - - vertexConsumer.vertex(entry, x1, y2, z1) - .color(color) - .texture(minU, maxV) - .light(light) - .overlay(overlay) - .normal(normalX, normalY, normalZ); - - vertexConsumer.vertex(entry, x2, y2, z2) - .color(color) - .texture(maxU, maxV) - .light(light) - .overlay(overlay) - .normal(normalX, normalY, normalZ); - - vertexConsumer.vertex(entry, x2, y1, z2) - .color(color) - .texture(maxU, minV) - .light(light) - .overlay(overlay) - .normal(normalX, normalY, normalZ); - } - private static void drawReversedQuad(VertexConsumer vertexConsumer, - MatrixStack.Entry entry, - float x1, float y1, float z1, - float x2, float y2, float z2, - float minU, float minV, - float maxU, float maxV, - int color, - int light, int overlay, - float normalX, float normalY, float normalZ) { - // Vertex 4: (x2, y1, z2) with (maxU, minV) - vertexConsumer.vertex(entry, x2, y1, z2).color(color).texture(maxU, minV).light(light).overlay(overlay).normal(normalX, normalY, normalZ); - // Vertex 3: (x2, y2, z2) with (maxU, maxV) - vertexConsumer.vertex(entry, x2, y2, z2).color(color).texture(maxU, maxV).light(light).overlay(overlay).normal(normalX, normalY, normalZ); - // Vertex 2: (x1, y2, z1) with (minU, maxV) - vertexConsumer.vertex(entry, x1, y2, z1).color(color).texture(minU, maxV).light(light).overlay(overlay).normal(normalX, normalY, normalZ); - // Vertex 1: (x1, y1, z1) with (minU, minV) - vertexConsumer.vertex(entry, x1, y1, z1).color(color).texture(minU, minV).light(light).overlay(overlay).normal(normalX, normalY, normalZ); - } - private static void drawReversedTiledXYQuad(VertexConsumer vertexConsumer, - MatrixStack.Entry entry, - float x1, float y1, float z1, - float x2, float y2, float z2, - Sprite sprite, - int color, - int light, int overlay, - float nx, float ny, float nz) { - float tileSize = 1.0f; - int fullTilesX = (int) ((x2 - x1) / tileSize); - int fullTilesY = (int) ((y2 - y1) / tileSize); - float leftoverX = (x2 - x1) - (fullTilesX * tileSize); - float leftoverY = (y2 - y1) - (fullTilesY * tileSize); - - // Draw full tiles - for (int i = 0; i < fullTilesX; i++) { - for (int j = 0; j < fullTilesY; j++) { - float xStart = x1 + i * tileSize; - float xEnd = xStart + tileSize; - float yStart = y1 + j * tileSize; - float yEnd = yStart + tileSize; - float u0 = sprite.getMinU(); - float v0 = sprite.getMinV(); - float u1 = sprite.getMaxU(); - float v1 = sprite.getMaxV(); - drawReversedQuad(vertexConsumer, entry, xStart, yStart, z1, xEnd, yEnd, z2, u0, v0, u1, v1, color, light, overlay, nx, ny, nz); - } - } + // Draw tiles + for (int i = 0; i < tileCountX; i++) { + for (int j = 0; j < (int) (direction.getAxis() == Direction.Axis.Y ? tileCountZ : tileCountY); j++) { - // Draw leftover tiles in x - if (leftoverX > 0) { - for (int j = 0; j < fullTilesY; j++) { - float xStart = x1 + fullTilesX * tileSize; - float xEnd = xStart + leftoverX; - float yStart = y1 + j * tileSize; - float yEnd = yStart + tileSize; - float u0 = sprite.getMinU(); - float v0 = sprite.getMinV(); - float u1 = sprite.getFrameU(leftoverX); - float v1 = sprite.getFrameV(tileSize); - drawReversedQuad(vertexConsumer, entry, xStart, yStart, z1, xEnd, yEnd, z2, u0, v0, u1, v1, color, light, overlay, nx, ny, nz); - } - } + float xStart = x1 + i * tileWidthX, xEnd = xStart + tileWidthX; + float yStart = y1 + j * tileWidthY, yEnd = yStart + tileWidthY; + float zStart = z1 + j * tileWidthZ, zEnd = zStart + tileWidthZ; - // Draw leftover tiles in y - if (leftoverY > 0) { - for (int i = 0; i < fullTilesX; i++) { - float xStart = x1 + i * tileSize; - float xEnd = xStart + tileSize; - float yStart = y1 + fullTilesY * tileSize; - float yEnd = yStart + leftoverY; - float u0 = sprite.getMinU(); - float v0 = sprite.getMinV(); - float u1 = sprite.getFrameU(tileSize); - float v1 = sprite.getFrameV(leftoverY); - drawReversedQuad(vertexConsumer, entry, xStart, yStart, z1, xEnd, yEnd, z2, u0, v0, u1, v1, color, light, overlay, nx, ny, nz); - } - // Draw the corner leftover tile if both leftoverX and leftoverY > 0 - if (leftoverX > 0) { - float xStart = x1 + fullTilesX * tileSize; - float xEnd = xStart + leftoverX; - float yStart = y1 + fullTilesY * tileSize; - float yEnd = yStart + leftoverY; - float u0 = sprite.getMinU(); - float v0 = sprite.getMinV(); - float u1 = sprite.getFrameU(leftoverX); - float v1 = sprite.getFrameV(leftoverY); - drawReversedQuad(vertexConsumer, entry, xStart, yStart, z1, xEnd, yEnd, z2, u0, v0, u1, v1, color, light, overlay, nx, ny, nz); - } - } - } + float[][] vertices; + if (direction.getAxis() == Direction.Axis.Y) { + vertices = new float[][]{{xStart, y1, zStart}, {xStart, y1, zEnd}, {xEnd, y1, zEnd}, {xEnd, y1, zStart}}; + } else if (direction.getAxis() == Direction.Axis.Z) { + vertices = new float[][]{{xStart, yStart, z1}, {xStart, yEnd, z1}, {xEnd, yEnd, z1}, {xEnd, yStart, z1}}; + } else { + vertices = new float[][]{{x1, yStart, zStart}, {x1, yEnd, zStart}, {x1, yEnd, zEnd}, {x1, yStart, zEnd}}; + } - private static void drawReversedTiledYZQuad(VertexConsumer vertexConsumer, - MatrixStack.Entry entry, - float x, float y1, float z1, - float y2, float z2, - Sprite sprite, - int color, - int light, int overlay, - float nx, float ny, float nz) { - float tileSize = 1.0f; - int fullTilesZ = (int) ((z2 - z1) / tileSize); - int fullTilesY = (int) ((y2 - y1) / tileSize); - float leftoverZ = (z2 - z1) - (fullTilesZ * tileSize); - float leftoverY = (y2 - y1) - (fullTilesY * tileSize); - - // Draw full tiles - for (int i = 0; i < fullTilesZ; i++) { - for (int j = 0; j < fullTilesY; j++) { - float zStart = z1 + i * tileSize; - float zEnd = zStart + tileSize; - float yStart = y1 + j * tileSize; - float yEnd = yStart + tileSize; - float u0 = sprite.getMinU(); - float v0 = sprite.getMinV(); - float u1 = sprite.getMaxU(); - float v1 = sprite.getMaxV(); - drawReversedQuad(vertexConsumer, entry, x, yStart, zStart, x, yEnd, zEnd, u0, v0, u1, v1, color, light, overlay, nx, ny, nz); - } - } + float[][] uvs = {{uStart, vStart}, {uStart, vEnd}, {uEnd, vEnd}, {uEnd, vStart}}; - // Draw leftover tiles in z - if (leftoverZ > 0) { - for (int j = 0; j < fullTilesY; j++) { - float zStart = z1 + fullTilesZ * tileSize; - float zEnd = zStart + leftoverZ; - float yStart = y1 + j * tileSize; - float yEnd = yStart + tileSize; - float u0 = sprite.getMinU(); - float v0 = sprite.getMinV(); - float u1 = sprite.getFrameU(leftoverZ); - float v1 = sprite.getFrameV(tileSize); - drawReversedQuad(vertexConsumer, entry, x, yStart, zStart, x, yEnd, zEnd, u0, v0, u1, v1, color, light, overlay, nx, ny, nz); + for (int k = 0; k < 4; k++) { + vertexConsumer.vertex(entry, vertices[k][0], vertices[k][1], vertices[k][2]) + .color(color).texture(uvs[k][0], uvs[k][1]).light(light).overlay(overlay).normal(entry, normal); + } } } + } - // Draw leftover tiles in y - if (leftoverY > 0) { - for (int i = 0; i < fullTilesZ; i++) { - float zStart = z1 + i * tileSize; - float zEnd = zStart + tileSize; - float yStart = y1 + fullTilesY * tileSize; - float yEnd = yStart + leftoverY; - float u0 = sprite.getMinU(); - float v0 = sprite.getMinV(); - float u1 = sprite.getFrameU(tileSize); - float v1 = sprite.getFrameV(leftoverY); - drawReversedQuad(vertexConsumer, entry, x, yStart, zStart, x, yEnd, zEnd, u0, v0, u1, v1, color, light, overlay, nx, ny, nz); - } - // Draw the corner leftover tile if both leftoverZ and leftoverY > 0 - if (leftoverZ > 0) { - float zStart = z1 + fullTilesZ * tileSize; - float zEnd = zStart + leftoverZ; - float yStart = y1 + fullTilesY * tileSize; - float yEnd = yStart + leftoverY; - float u0 = sprite.getMinU(); - float v0 = sprite.getMinV(); - float u1 = sprite.getFrameU(leftoverZ); - float v1 = sprite.getFrameV(leftoverY); - drawReversedQuad(vertexConsumer, entry, x, yStart, zStart, x, yEnd, zEnd, u0, v0, u1, v1, color, light, overlay, nx, ny, nz); - } - } - } + // For front and back (XY plane) +// public static void drawTiledXYQuad(VertexConsumer vertexConsumer, +// MatrixStack.Entry entry, +// float x1, float y1, float z1, +// float x2, float y2, float z2, +// Sprite sprite, +// int color, +// int light, int overlay, +// float nx, float ny, float nz) { +// float tileSize = 1.0f; +// int fullTilesX = (int) ((x2 - x1) / tileSize); +// int fullTilesY = (int) ((y2 - y1) / tileSize); +// float leftoverX = (x2 - x1) - (fullTilesX * tileSize); +// float leftoverY = (y2 - y1) - (fullTilesY * tileSize); +// +// // Draw full tiles +// for (int i = 0; i < fullTilesX; i++) { +// for (int j = 0; j < fullTilesY; j++) { +// float xStart = x1 + i * tileSize; +// float xEnd = xStart + tileSize; +// float yStart = y1 + j * tileSize; +// float yEnd = yStart + tileSize; +// float u0 = sprite.getMinU(); +// float v0 = sprite.getMinV(); +// float u1 = sprite.getMaxU(); +// float v1 = sprite.getMaxV(); +// drawQuad(vertexConsumer, entry, xStart, yStart, z1, xEnd, yEnd, z2, u0, v0, u1, v1, color, light, overlay, nx, ny, nz); +// } +// } +// +// // Draw leftover tiles in x +// if (leftoverX > 0) { +// for (int j = 0; j < fullTilesY; j++) { +// float xStart = x1 + fullTilesX * tileSize; +// float xEnd = xStart + leftoverX; +// float yStart = y1 + j * tileSize; +// float yEnd = yStart + tileSize; +// float u0 = sprite.getMinU(); +// float v0 = sprite.getMinV(); +// float u1 = sprite.getFrameU(leftoverX); +// float v1 = sprite.getFrameV(tileSize); +// drawQuad(vertexConsumer, entry, xStart, yStart, z1, xEnd, yEnd, z2, u0, v0, u1, v1, color, light, overlay, nx, ny, nz); +// } +// } +// +// // Draw leftover tiles in y +// if (leftoverY > 0) { +// for (int i = 0; i < fullTilesX; i++) { +// float xStart = x1 + i * tileSize; +// float xEnd = xStart + tileSize; +// float yStart = y1 + fullTilesY * tileSize; +// float yEnd = yStart + leftoverY; +// float u0 = sprite.getMinU(); +// float v0 = sprite.getMinV(); +// float u1 = sprite.getFrameU(tileSize); +// float v1 = sprite.getFrameV(leftoverY); +// drawQuad(vertexConsumer, entry, xStart, yStart, z1, xEnd, yEnd, z2, u0, v0, u1, v1, color, light, overlay, nx, ny, nz); +// } +// +// // Draw the corner leftover tile if both leftoverX and leftoverY > 0 +// if (leftoverX > 0) { +// float xStart = x1 + fullTilesX * tileSize; +// float xEnd = xStart + leftoverX; +// float yStart = y1 + fullTilesY * tileSize; +// float yEnd = yStart + leftoverY; +// float u0 = sprite.getMinU(); +// float v0 = sprite.getMinV(); +// float u1 = sprite.getFrameU(leftoverX); +// float v1 = sprite.getFrameV(leftoverY); +// drawQuad(vertexConsumer, entry, xStart, yStart, z1, xEnd, yEnd, z2, u0, v0, u1, v1, color, light, overlay, nx, ny, nz); +// } +// } +// } } diff --git a/src/main/java/dev/turtywurty/industria/blockentity/util/fluid/WrappedFluidStorage.java b/src/main/java/dev/turtywurty/industria/blockentity/util/fluid/WrappedFluidStorage.java index 28b89ca..709f0af 100644 --- a/src/main/java/dev/turtywurty/industria/blockentity/util/fluid/WrappedFluidStorage.java +++ b/src/main/java/dev/turtywurty/industria/blockentity/util/fluid/WrappedFluidStorage.java @@ -53,7 +53,7 @@ public void readData(ReadView view) { if (storage instanceof SingleFluidStorage singleFluidStorage) { singleFluidStorage.amount = view.getLong("Amount", 0L); - singleFluidStorage.variant = view.read("Fluid", FluidVariant.CODEC).orElseThrow(); + singleFluidStorage.variant = view.read("Fluid", FluidVariant.CODEC).orElse(FluidVariant.blank()); } else { throw new UnsupportedOperationException("Cannot read fluid storage of type: " + storage.getClass().getName()); }