From 0f004b494e4e67006e960b6d142327ac066fbb41 Mon Sep 17 00:00:00 2001 From: Atsuihsio <842960157@qq.com> Date: Tue, 11 Mar 2025 17:16:35 +0800 Subject: [PATCH] =?UTF-8?q?=E4=BC=98=E5=8C=96=E7=81=AB=E7=82=AEHUD?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../client/overlay/CannonHudOverlay.java | 183 +++++++++++------- .../entity/vehicle/AnnihilatorEntity.java | 2 +- .../entity/vehicle/Mk42Entity.java | 7 +- .../entity/vehicle/Mle1934Entity.java | 7 +- .../superbwarfare/mixins/CameraMixin.java | 7 + .../animations/mk_42.animation.json | 6 +- 6 files changed, 132 insertions(+), 80 deletions(-) diff --git a/src/main/java/com/atsuishio/superbwarfare/client/overlay/CannonHudOverlay.java b/src/main/java/com/atsuishio/superbwarfare/client/overlay/CannonHudOverlay.java index 2914d5726..6d2eb41a0 100644 --- a/src/main/java/com/atsuishio/superbwarfare/client/overlay/CannonHudOverlay.java +++ b/src/main/java/com/atsuishio/superbwarfare/client/overlay/CannonHudOverlay.java @@ -1,14 +1,21 @@ package com.atsuishio.superbwarfare.client.overlay; import com.atsuishio.superbwarfare.ModUtils; +import com.atsuishio.superbwarfare.client.RenderHelper; import com.atsuishio.superbwarfare.entity.vehicle.AnnihilatorEntity; +import com.atsuishio.superbwarfare.entity.vehicle.Mk42Entity; +import com.atsuishio.superbwarfare.entity.vehicle.Mle1934Entity; import com.atsuishio.superbwarfare.entity.vehicle.base.CannonEntity; +import com.atsuishio.superbwarfare.entity.vehicle.base.VehicleEntity; import com.atsuishio.superbwarfare.event.ClientEventHandler; import com.atsuishio.superbwarfare.tools.FormatTool; +import com.atsuishio.superbwarfare.tools.InventoryTool; import com.atsuishio.superbwarfare.tools.TraceTool; import com.mojang.blaze3d.platform.GlStateManager; import com.mojang.blaze3d.systems.RenderSystem; import com.mojang.blaze3d.vertex.PoseStack; +import net.minecraft.client.Camera; +import net.minecraft.client.CameraType; import net.minecraft.client.Minecraft; import net.minecraft.client.gui.GuiGraphics; import net.minecraft.client.renderer.GameRenderer; @@ -29,6 +36,7 @@ import org.joml.Math; import static com.atsuishio.superbwarfare.client.RenderHelper.preciseBlit; import static com.atsuishio.superbwarfare.client.overlay.VehicleHudOverlay.renderKillIndicator; +import static com.atsuishio.superbwarfare.client.overlay.VehicleHudOverlay.renderKillIndicator3P; @Mod.EventBusSubscriber(value = Dist.CLIENT) public class CannonHudOverlay { @@ -41,91 +49,134 @@ public class CannonHudOverlay { Player player = mc.player; GuiGraphics guiGraphics = event.getGuiGraphics(); PoseStack poseStack = guiGraphics.pose(); + Camera camera = mc.gameRenderer.getMainCamera(); + Vec3 cameraPos = camera.getPosition(); if (!shouldRenderCrossHair(player)) return; - Entity cannon = player.getVehicle(); - if (cannon == null) return; + Entity vehicle = player.getVehicle(); + if (vehicle instanceof CannonEntity cannonEntity && cannonEntity instanceof VehicleEntity cannon) { + poseStack.pushPose(); + RenderSystem.disableDepthTest(); + RenderSystem.depthMask(false); + RenderSystem.enableBlend(); + RenderSystem.setShader(GameRenderer::getPositionTexShader); + RenderSystem.blendFuncSeparate(GlStateManager.SourceFactor.SRC_ALPHA, GlStateManager.DestFactor.ONE_MINUS_SRC_ALPHA, GlStateManager.SourceFactor.ONE, GlStateManager.DestFactor.ZERO); + RenderSystem.setShaderColor(1, 1, 1, 1); - poseStack.pushPose(); - RenderSystem.disableDepthTest(); - RenderSystem.depthMask(false); - RenderSystem.enableBlend(); - RenderSystem.setShader(GameRenderer::getPositionTexShader); - RenderSystem.blendFuncSeparate(GlStateManager.SourceFactor.SRC_ALPHA, GlStateManager.DestFactor.ONE_MINUS_SRC_ALPHA, GlStateManager.SourceFactor.ONE, GlStateManager.DestFactor.ZERO); - RenderSystem.setShaderColor(1, 1, 1, 1); + preciseBlit(event.getGuiGraphics(), ModUtils.loc("textures/screens/compass_white.png"), (float) w / 2 - 128, (float) 10, 128 + ((float) 64 / 45 * (Mth.lerp(event.getPartialTick(), cannon.yRotO, cannon.getYRot()))), 0, 256, 16, 512, 16); + preciseBlit(event.getGuiGraphics(), ModUtils.loc("textures/screens/roll_ind_white.png"), w / 2 - 4, 27, 0, 0.0F, 8, 8, 8, 8); - preciseBlit(event.getGuiGraphics(), ModUtils.loc("textures/screens/compass_white.png"), (float) w / 2 - 128, (float) 10, 128 + ((float) 64 / 45 * (Mth.lerp(event.getPartialTick(), cannon.yRotO, cannon.getYRot()))), 0, 256, 16, 512, 16); - preciseBlit(event.getGuiGraphics(), ModUtils.loc("textures/screens/roll_ind_white.png"), w / 2 - 4, 27, 0, 0.0F, 8, 8, 8, 8); + String angle = FormatTool.DECIMAL_FORMAT_1ZZ.format(Mth.lerp(event.getPartialTick(), cannon.yRotO, cannon.getYRot())); + int width = Minecraft.getInstance().font.width(angle); + event.getGuiGraphics().drawString(Minecraft.getInstance().font, Component.literal(angle), w / 2 - width / 2, 40, -1, false); - String angle = FormatTool.DECIMAL_FORMAT_1ZZ.format(Mth.lerp(event.getPartialTick(), cannon.yRotO, cannon.getYRot())); - int width = Minecraft.getInstance().font.width(angle); - event.getGuiGraphics().drawString(Minecraft.getInstance().font, Component.literal(angle), w / 2 - width / 2, 40, -1, false); + preciseBlit(event.getGuiGraphics(), ModUtils.loc("textures/screens/cannon/cannon_pitch.png"), w / 2 + 166, h / 2 - 64, 0, 0.0F, 8, 128, 8, 128); - preciseBlit(event.getGuiGraphics(), ModUtils.loc("textures/screens/cannon/cannon_pitch.png"), w / 2 + 166, h / 2 - 64, 0, 0.0F, 8, 128, 8, 128); + String pitch = FormatTool.DECIMAL_FORMAT_1ZZ.format(-Mth.lerp(event.getPartialTick(), cannon.xRotO, cannon.getXRot())); + int widthP = Minecraft.getInstance().font.width(pitch); - String pitch = FormatTool.DECIMAL_FORMAT_1ZZ.format(-Mth.lerp(event.getPartialTick(), cannon.xRotO, cannon.getXRot())); - int widthP = Minecraft.getInstance().font.width(pitch); + poseStack.pushPose(); - poseStack.pushPose(); + event.getGuiGraphics().pose().translate(0, Mth.lerp(event.getPartialTick(), cannon.xRotO, cannon.getXRot()) * 0.7, 0); + preciseBlit(event.getGuiGraphics(), ModUtils.loc("textures/screens/cannon/cannon_pitch_ind.png"), w / 2 + 158, h / 2 - 4, 0, 0.0F, 8, 8, 8, 8); + event.getGuiGraphics().drawString(Minecraft.getInstance().font, Component.literal(pitch), w / 2 + 157 - widthP, h / 2 - 4, -1, false); + poseStack.popPose(); - event.getGuiGraphics().pose().translate(0, Mth.lerp(event.getPartialTick(), cannon.xRotO, cannon.getXRot()) * 0.7, 0); - preciseBlit(event.getGuiGraphics(), ModUtils.loc("textures/screens/cannon/cannon_pitch_ind.png"), w / 2 + 158, h / 2 - 4, 0, 0.0F, 8, 8, 8, 8); - event.getGuiGraphics().drawString(Minecraft.getInstance().font, Component.literal(pitch), w / 2 + 157 - widthP, h / 2 - 4, -1, false); - poseStack.popPose(); + if (Minecraft.getInstance().options.getCameraType() == CameraType.FIRST_PERSON || ClientEventHandler.zoomVehicle) { + float fovAdjust = (float) 70 / Minecraft.getInstance().options.fov().get(); - float fovAdjust = (float) 70 / Minecraft.getInstance().options.fov().get(); + float f = (float) Math.min(w, h); + float f1 = Math.min((float) w / f, (float) h / f) * fovAdjust; + int i = Mth.floor(f * f1); + int j = Mth.floor(f * f1); + int k = (w - i) / 2; + int l = (h - j) / 2; + if (ClientEventHandler.zoomVehicle) { + Entity lookingEntity = TraceTool.findLookingEntity(player, 512); + boolean lookAtEntity = false; - float f = (float) Math.min(w, h); - float f1 = Math.min((float) w / f, (float) h / f) * fovAdjust; - int i = Mth.floor(f * f1); - int j = Mth.floor(f * f1); - int k = (w - i) / 2; - int l = (h - j) / 2; - if (ClientEventHandler.zoomVehicle) { - Entity lookingEntity = TraceTool.findLookingEntity(player, 512); - boolean lookAtEntity = false; + BlockHitResult result = player.level().clip(new ClipContext(player.getEyePosition(), player.getEyePosition().add(player.getViewVector(1).scale(512)), + ClipContext.Block.OUTLINE, ClipContext.Fluid.NONE, player)); + Vec3 hitPos = result.getLocation(); - BlockHitResult result = player.level().clip(new ClipContext(player.getEyePosition(), player.getEyePosition().add(player.getViewVector(1).scale(512)), - ClipContext.Block.OUTLINE, ClipContext.Fluid.NONE, player)); - Vec3 hitPos = result.getLocation(); + double blockRange = player.getEyePosition(1).distanceTo(hitPos); - double blockRange = player.getEyePosition(1).distanceTo(hitPos); + double entityRange = 0; + if (lookingEntity instanceof LivingEntity living) { + lookAtEntity = true; + entityRange = player.distanceTo(living); + } + if (lookAtEntity) { + event.getGuiGraphics().drawString(Minecraft.getInstance().font, Component.translatable("tips.superbwarfare.drone.range") + .append(Component.literal(FormatTool.format1D(entityRange, "m ") + lookingEntity.getDisplayName().getString())), + w / 2 + 14, h / 2 - 20, -1, false); + } else { + if (blockRange > 511) { + event.getGuiGraphics().drawString(Minecraft.getInstance().font, Component.translatable("tips.superbwarfare.drone.range") + .append(Component.literal("---m")), w / 2 + 14, h / 2 - 20, -1, false); + } else { + event.getGuiGraphics().drawString(Minecraft.getInstance().font, Component.translatable("tips.superbwarfare.drone.range") + .append(Component.literal(FormatTool.format1D(blockRange, "m"))), + w / 2 + 14, h / 2 - 20, -1, false); + } + } + if (cannon instanceof AnnihilatorEntity) { + preciseBlit(event.getGuiGraphics(), ModUtils.loc("textures/screens/cannon/laser_cannon_crosshair.png"), k, l, 0, 0.0F, i, j, i, j); + } else { + preciseBlit(event.getGuiGraphics(), ModUtils.loc("textures/screens/cannon/cannon_crosshair.png"), k, l, 0, 0.0F, i, j, i, j); + } + float diffY = -Mth.wrapDegrees(Mth.lerp(event.getPartialTick(), player.yHeadRotO, player.getYHeadRot()) - Mth.lerp(event.getPartialTick(), cannon.yRotO, cannon.getYRot())); - double entityRange = 0; - if (lookingEntity instanceof LivingEntity living) { - lookAtEntity = true; - entityRange = player.distanceTo(living); - } - if (lookAtEntity) { - event.getGuiGraphics().drawString(Minecraft.getInstance().font, Component.translatable("tips.superbwarfare.drone.range") - .append(Component.literal(FormatTool.format1D(entityRange, "m ") + lookingEntity.getDisplayName().getString())), - w / 2 + 14, h / 2 - 20, -1, false); - } else { - if (blockRange > 511) { - event.getGuiGraphics().drawString(Minecraft.getInstance().font, Component.translatable("tips.superbwarfare.drone.range") - .append(Component.literal("---m")), w / 2 + 14, h / 2 - 20, -1, false); + preciseBlit(event.getGuiGraphics(), ModUtils.loc("textures/screens/cannon/indicator.png"), w / 2 - 4.3f + 0.45f * diffY, h / 2 - 10, 0, 0.0F, 8, 8, 8, 8); } else { - event.getGuiGraphics().drawString(Minecraft.getInstance().font, Component.translatable("tips.superbwarfare.drone.range") - .append(Component.literal(FormatTool.format1D(blockRange, "m"))), - w / 2 + 14, h / 2 - 20, -1, false); + preciseBlit(event.getGuiGraphics(), ModUtils.loc("textures/screens/cannon/cannon_crosshair_notzoom.png"), k, l, 0, 0.0F, i, j, i, j); + } + renderKillIndicator(guiGraphics, w, h); + } else if (Minecraft.getInstance().options.getCameraType() == CameraType.THIRD_PERSON_BACK && !ClientEventHandler.zoomVehicle) { + Vec3 p = RenderHelper.worldToScreen(new Vec3(Mth.lerp(event.getPartialTick(), player.xo, player.getX()), Mth.lerp(event.getPartialTick(), player.yo, player.getY()), + Mth.lerp(event.getPartialTick(), player.zo, player.getZ())).add(cannon.getViewVector(event.getPartialTick()).scale(128)), cameraPos); + + // 第三人称准星 + if (p != null) { + poseStack.pushPose(); + float x = (float) p.x; + float y = (float) p.y; + + poseStack.pushPose(); + preciseBlit(guiGraphics, ModUtils.loc("textures/screens/drone.png"), x - 12, y - 12, 0, 0, 24, 24, 24, 24); + renderKillIndicator3P(guiGraphics, x - 7.5f + (float) (2 * (Math.random() - 0.5f)), y - 7.5f + (float) (2 * (Math.random() - 0.5f))); + + poseStack.pushPose(); + + poseStack.translate(x, y, 0); + poseStack.scale(0.75f, 0.75f, 1); + + if (player.getVehicle() instanceof Mk42Entity || player.getVehicle() instanceof Mle1934Entity) { + if (cannonEntity.getWeaponIndex(0) == 0) { + guiGraphics.drawString(Minecraft.getInstance().font, Component.literal("AP SHELL " + (InventoryTool.hasCreativeAmmoBox(player) ? "∞" : cannonEntity.getAmmoCount(player))), 30, -9, -1, false); + } else { + guiGraphics.drawString(Minecraft.getInstance().font, Component.literal("HE SHELL " + (InventoryTool.hasCreativeAmmoBox(player) ? "∞" : cannonEntity.getAmmoCount(player))), 30, -9, -1, false); + } + } + + // 歼灭者 + if (player.getVehicle() instanceof AnnihilatorEntity annihilatorEntity) { + guiGraphics.drawString(mc.font, Component.literal("LASER " + (FormatTool.format0D((double) (100 * annihilatorEntity.getEnergy()) / annihilatorEntity.getMaxEnergy()) + "%")), 30, -9, -1, false); + } + + double heal = 1 - cannon.getHealth() / cannon.getMaxHealth(); + + guiGraphics.drawString(Minecraft.getInstance().font, Component.literal("HP " + + FormatTool.format0D(100 * cannon.getHealth() / cannon.getMaxHealth())), 30, 1, Mth.hsvToRgb(0F, (float) heal, 1.0F), false); + + poseStack.popPose(); + poseStack.popPose(); + poseStack.popPose(); } } - if (cannon instanceof AnnihilatorEntity) { - preciseBlit(event.getGuiGraphics(), ModUtils.loc("textures/screens/cannon/laser_cannon_crosshair.png"), k, l, 0, 0.0F, i, j, i, j); - } else { - preciseBlit(event.getGuiGraphics(), ModUtils.loc("textures/screens/cannon/cannon_crosshair.png"), k, l, 0, 0.0F, i, j, i, j); - } - float diffY = -Mth.wrapDegrees(Mth.lerp(event.getPartialTick(), player.yHeadRotO, player.getYHeadRot()) - Mth.lerp(event.getPartialTick(), cannon.yRotO, cannon.getYRot())); - - preciseBlit(event.getGuiGraphics(), ModUtils.loc("textures/screens/cannon/indicator.png"), w / 2 - 4.3f + 0.45f * diffY, h / 2 - 10, 0, 0.0F, 8, 8, 8, 8); - } else { - preciseBlit(event.getGuiGraphics(), ModUtils.loc("textures/screens/cannon/cannon_crosshair_notzoom.png"), k, l, 0, 0.0F, i, j, i, j); + poseStack.popPose(); } - - renderKillIndicator(guiGraphics, w, h); - - poseStack.popPose(); } private static boolean shouldRenderCrossHair(Player player) { diff --git a/src/main/java/com/atsuishio/superbwarfare/entity/vehicle/AnnihilatorEntity.java b/src/main/java/com/atsuishio/superbwarfare/entity/vehicle/AnnihilatorEntity.java index 983aec5f4..7759687cd 100644 --- a/src/main/java/com/atsuishio/superbwarfare/entity/vehicle/AnnihilatorEntity.java +++ b/src/main/java/com/atsuishio/superbwarfare/entity/vehicle/AnnihilatorEntity.java @@ -507,7 +507,7 @@ public class AnnihilatorEntity extends EnergyVehicleEntity implements GeoEntity, turretTurnSound(diffX, diffY, 0.8f); this.setYRot(this.getYRot() + Mth.clamp(0.5f * diffY, -0.6f, 0.6f)); - this.setXRot(Mth.clamp(this.getXRot() + Mth.clamp(diffX, -2f, 2f), -45, 5f)); + this.setXRot(Mth.clamp(this.getXRot() + Mth.clamp(diffX, -0.8f, 0.8f), -45, 5f)); } public void autoAim() { diff --git a/src/main/java/com/atsuishio/superbwarfare/entity/vehicle/Mk42Entity.java b/src/main/java/com/atsuishio/superbwarfare/entity/vehicle/Mk42Entity.java index c9d696deb..790c3b6a5 100644 --- a/src/main/java/com/atsuishio/superbwarfare/entity/vehicle/Mk42Entity.java +++ b/src/main/java/com/atsuishio/superbwarfare/entity/vehicle/Mk42Entity.java @@ -388,11 +388,8 @@ public class Mk42Entity extends VehicleEntity implements GeoEntity, CannonEntity @Override public int getAmmoCount(Player player) { - if (player.getMainHandItem().getItem() instanceof CannonShellItem) { - return player.getMainHandItem().getCount(); - } else { - return -1; - } + var ammo = getWeaponIndex(0) == 0 ? ModItems.AP_5_INCHES.get() : ModItems.HE_5_INCHES.get(); + return InventoryTool.countItem(player.getInventory().items, ammo); } @Override diff --git a/src/main/java/com/atsuishio/superbwarfare/entity/vehicle/Mle1934Entity.java b/src/main/java/com/atsuishio/superbwarfare/entity/vehicle/Mle1934Entity.java index e1b5ad518..583809579 100644 --- a/src/main/java/com/atsuishio/superbwarfare/entity/vehicle/Mle1934Entity.java +++ b/src/main/java/com/atsuishio/superbwarfare/entity/vehicle/Mle1934Entity.java @@ -510,11 +510,8 @@ public class Mle1934Entity extends VehicleEntity implements GeoEntity, CannonEnt @Override public int getAmmoCount(Player player) { - if (player.getMainHandItem().getItem() instanceof CannonShellItem) { - return player.getMainHandItem().getCount(); - } else { - return -1; - } + var ammo = getWeaponIndex(0) == 0 ? ModItems.AP_5_INCHES.get() : ModItems.HE_5_INCHES.get(); + return InventoryTool.countItem(player.getInventory().items, ammo); } @Override diff --git a/src/main/java/com/atsuishio/superbwarfare/mixins/CameraMixin.java b/src/main/java/com/atsuishio/superbwarfare/mixins/CameraMixin.java index f0c35ecf7..9ce40df94 100644 --- a/src/main/java/com/atsuishio/superbwarfare/mixins/CameraMixin.java +++ b/src/main/java/com/atsuishio/superbwarfare/mixins/CameraMixin.java @@ -1,6 +1,7 @@ package com.atsuishio.superbwarfare.mixins; import com.atsuishio.superbwarfare.entity.vehicle.*; +import com.atsuishio.superbwarfare.entity.vehicle.base.CannonEntity; import com.atsuishio.superbwarfare.event.ClientEventHandler; import com.atsuishio.superbwarfare.init.ModItems; import com.atsuishio.superbwarfare.init.ModTags; @@ -118,6 +119,12 @@ public abstract class CameraMixin { } return; } + + if (player.getVehicle() instanceof CannonEntity && (Minecraft.getInstance().options.getCameraType() == CameraType.FIRST_PERSON || ClientEventHandler.zoomVehicle)) { + setRotation(Mth.lerp(partialTicks, player.yRotO, player.getYRot()), Mth.lerp(partialTicks, player.xRotO, player.getXRot())); + setPosition(Mth.lerp(partialTicks, player.xo, player.getX()), Mth.lerp(partialTicks, player.yo + player.getEyeHeight(), player.getEyeY()), Mth.lerp(partialTicks, player.zo, player.getZ())); + info.cancel(); + } } } diff --git a/src/main/resources/assets/superbwarfare/animations/mk_42.animation.json b/src/main/resources/assets/superbwarfare/animations/mk_42.animation.json index af1d013a7..72d8f1984 100644 --- a/src/main/resources/assets/superbwarfare/animations/mk_42.animation.json +++ b/src/main/resources/assets/superbwarfare/animations/mk_42.animation.json @@ -18,9 +18,9 @@ "paoguan": { "position": { "0.0": [0, 0, 0], - "0.05": [0, 0, 11], - "0.4917": [0, 0, 0], - "0.6667": [0, 0, 0] + "0.0167": [0, 0, 11], + "0.2917": [0, 0, 0], + "0.6583": [0, 0, 0] } }, "flare": {