diff --git a/common/src/main/java/dev/mrsnowy/teleport_commands/commands/back.java b/common/src/main/java/dev/mrsnowy/teleport_commands/commands/back.java index 731fb76..7d0f2e5 100644 --- a/common/src/main/java/dev/mrsnowy/teleport_commands/commands/back.java +++ b/common/src/main/java/dev/mrsnowy/teleport_commands/commands/back.java @@ -7,7 +7,6 @@ import dev.mrsnowy.teleport_commands.Constants; import java.util.*; import dev.mrsnowy.teleport_commands.TeleportCommands; -import dev.mrsnowy.teleport_commands.storage.DeathLocationStorage; import dev.mrsnowy.teleport_commands.common.DeathLocation; import dev.mrsnowy.teleport_commands.utils.tools; import net.minecraft.ChatFormatting; @@ -84,7 +83,7 @@ public class back { Constants.LOGGER.warn("({}) Error while going back! \nCouldn't find a world with the id: \"{}\" \nAvailable worlds: {}", player.getName().getString(), deathLocation.getWorldString(), - tools.getWorldIds()); + tools.getWorldIds(teleportCommands.server)); player.displayClientMessage(getTranslatedText("commands.teleport_commands.common.worldNotFound", player) .withStyle(ChatFormatting.RED, ChatFormatting.BOLD), true); @@ -134,8 +133,8 @@ public class back { // teleport the player! Vec3 teleportPos = new Vec3(teleportBlockPos.getX() + 0.5, teleportBlockPos.getY(), teleportBlockPos.getZ() + 0.5); - player.displayClientMessage(getTranslatedText("commands.teleport_commands.back.go", player), true); - teleportCommands.tools.Teleporter(player, deathLocationWorld, teleportPos); +// player.displayClientMessage(getTranslatedText("commands.teleport_commands.back.go", player), true); + teleportCommands.teleporter.queue(player, deathLocationWorld, teleportPos, "commands.teleport_commands.back.go"); } } } diff --git a/common/src/main/java/dev/mrsnowy/teleport_commands/commands/tpa.java b/common/src/main/java/dev/mrsnowy/teleport_commands/commands/tpa.java index ed79c5d..b70a6c5 100644 --- a/common/src/main/java/dev/mrsnowy/teleport_commands/commands/tpa.java +++ b/common/src/main/java/dev/mrsnowy/teleport_commands/commands/tpa.java @@ -209,10 +209,10 @@ public class tpa { BlockPos safeBlockPos = teleportData.get(); Vec3 teleportPos = new Vec3(safeBlockPos.getX() + 0.5, safeBlockPos.getY(), safeBlockPos.getZ() + 0.5); - teleportCommands.teleporter.teleportQueue(toSentPlayer, destinationPlayer.serverLevel(), teleportPos); + teleportCommands.teleporter.queue(toSentPlayer, destinationPlayer.serverLevel(), teleportPos); } else { // if no safe location then just teleport to the player - teleportCommands.teleporter.teleportQueue(toSentPlayer, destinationPlayer.serverLevel(), destinationPlayer.position()); + teleportCommands.teleporter.queue(toSentPlayer, destinationPlayer.serverLevel(), destinationPlayer.position()); } // if the player teleported then these messages get sent && the request gets removed diff --git a/common/src/main/java/dev/mrsnowy/teleport_commands/mixin/PlayerDeathMixin.java b/common/src/main/java/dev/mrsnowy/teleport_commands/mixin/PlayerDeathMixin.java index 477cede..518c9fb 100644 --- a/common/src/main/java/dev/mrsnowy/teleport_commands/mixin/PlayerDeathMixin.java +++ b/common/src/main/java/dev/mrsnowy/teleport_commands/mixin/PlayerDeathMixin.java @@ -1,11 +1,18 @@ package dev.mrsnowy.teleport_commands.mixin; import dev.mrsnowy.teleport_commands.TeleportCommands; +import net.minecraft.client.renderer.item.properties.numeric.Damage; +import net.minecraft.commands.Commands; +import net.minecraft.server.level.ServerLevel; import net.minecraft.server.level.ServerPlayer; +import net.minecraft.world.damagesource.DamageSource; +import net.minecraft.world.entity.MoverType; +import net.minecraft.world.phys.Vec3; import org.spongepowered.asm.mixin.Mixin; import org.spongepowered.asm.mixin.injection.At; import org.spongepowered.asm.mixin.injection.Inject; import org.spongepowered.asm.mixin.injection.callback.CallbackInfo; +import org.spongepowered.asm.mixin.injection.callback.CallbackInfoReturnable; @Mixin(ServerPlayer.class) public class PlayerDeathMixin { @@ -15,13 +22,32 @@ public class PlayerDeathMixin { TeleportCommands.INSTANCE.onPlayerDeath((ServerPlayer) (Object) this); } - @Inject(method = "onEnterCombat", at = @At("TAIL")) - private void combatEntered(CallbackInfo info) { -// TeleportCommands.INSTANCE.onPlayerDeath((ServerPlayer) (Object) this); +// @Inject(method = "onEnterCombat", at = @At("TAIL")) +// private void combatEntered(CallbackInfo info) { +//// TeleportCommands.INSTANCE.onPlayerDeath((ServerPlayer) (Object) this); +// } +// +// @Inject(method = "onLeaveCombat", at = @At("TAIL")) +// private void combatLeft(CallbackInfo info) { +//// TeleportCommands.INSTANCE.onPlayerDeath((ServerPlayer) (Object) this); +// } + + // This function is not on the ServerPlayer, but on the entity which the ServerPlayer is based on :P + @Inject(method = "move", at = @At("TAIL")) + private void onMove(MoverType type, Vec3 delta, CallbackInfo info) { + if (type != MoverType.PLAYER && type != MoverType.SELF) return; + if (delta.lengthSqr() == 0) return; + + ServerPlayer self = (ServerPlayer) (Object) this; + TeleportCommands.INSTANCE.teleporter.reportPlayerMoved(self); } - @Inject(method = "onLeaveCombat", at = @At("TAIL")) - private void combatLeft(CallbackInfo info) { -// TeleportCommands.INSTANCE.onPlayerDeath((ServerPlayer) (Object) this); + @Inject(method = "hurtServer", at = @At("TAIL")) + private void onHurt(ServerLevel leve, DamageSource source, float amount, CallbackInfoReturnable info) { + // It returns true if the player got meaningfully damaged / they weren't immune + if (info.getReturnValue()) { + ServerPlayer self = (ServerPlayer) (Object) this; + TeleportCommands.INSTANCE.teleporter.reportPlayerHurt(self); + } } } \ No newline at end of file diff --git a/common/src/main/java/dev/mrsnowy/teleport_commands/mixin/ServerStartMixin.java b/common/src/main/java/dev/mrsnowy/teleport_commands/mixin/ServerStartMixin.java index ef713c7..d1baae4 100644 --- a/common/src/main/java/dev/mrsnowy/teleport_commands/mixin/ServerStartMixin.java +++ b/common/src/main/java/dev/mrsnowy/teleport_commands/mixin/ServerStartMixin.java @@ -20,7 +20,7 @@ public class ServerStartMixin { @Inject(method = "tickServer", at = @At(value = "TAIL")) private void tickServer(BooleanSupplier hasTimeLeft, CallbackInfo info) { - TeleportCommands.INSTANCE.teleporter.checkPlayerData((MinecraftServer) (Object) this); + TeleportCommands.INSTANCE.teleporter.tick((MinecraftServer) (Object) this); // todo! do the same for TPA } diff --git a/common/src/main/java/dev/mrsnowy/teleport_commands/storage/configManager.java b/common/src/main/java/dev/mrsnowy/teleport_commands/storage/configManager.java index 6da1a33..80b87df 100644 --- a/common/src/main/java/dev/mrsnowy/teleport_commands/storage/configManager.java +++ b/common/src/main/java/dev/mrsnowy/teleport_commands/storage/configManager.java @@ -3,6 +3,7 @@ package dev.mrsnowy.teleport_commands.storage; import com.google.gson.*; import dev.mrsnowy.teleport_commands.Constants; import dev.mrsnowy.teleport_commands.TeleportCommands; +import dev.mrsnowy.teleport_commands.utils.tools; import java.io.FileReader; import java.nio.file.Files; @@ -88,7 +89,7 @@ public class configManager { Files.write(configFile, json, StandardOpenOption.WRITE, StandardOpenOption.TRUNCATE_EXISTING, StandardOpenOption.CREATE); } - public static class ConfigClass { + public class ConfigClass { private final int version = 0; public Teleporting teleporting = new Teleporting(); public Back back = new Back(); @@ -101,61 +102,67 @@ public class configManager { return version; } - public static final class Teleporting { - /// Delay before teleporting - private int delay = 3; - /// Cooldown before they can teleport again - private int cooldown = 5; + public final class Teleporting { + /// Delay (in ticks) before teleporting + private int delay = 60; + /// Cooldown (in ticks) before a player can teleport again + private int cooldown = 100; /// Allow moving while teleporting - private boolean whileMoving = true; + private boolean allowMoving = true; /// Allow fighting while teleporting - private boolean whileFighting = false; - /// Cooldown after fighting before they can teleport again - private int fightCooldown = 10; + private boolean allowFighting = false; + /// Cooldown (in ticks) after fighting before a player can teleport again + private int fightCooldown = 200; public int getDelay() { return delay; } - public void setDelay(int delay) { + public void setDelay(int delay) throws Exception { this.delay = delay; + configSaver(); } - public boolean isWhileMoving() { - return whileMoving; + public boolean isAllowMoving() { + return allowMoving; } - public void setWhileMoving(boolean whileMoving) { - this.whileMoving = whileMoving; + public void setAllowMoving(boolean allowMoving) throws Exception { + this.allowMoving = allowMoving; + configSaver(); } - public boolean isWhileFighting() { - return whileFighting; + public boolean isAllowFighting() { + return allowFighting; } - public void setWhileFighting(boolean whileFighting) { - this.whileFighting = whileFighting; + public void setAllowFighting(boolean allowFighting) throws Exception { + this.allowFighting = allowFighting; + configSaver(); } public int getFightCooldown() { return fightCooldown; } - public void setFightCooldown(int fightCooldown) { + public void setFightCooldown(int fightCooldown) throws Exception { this.fightCooldown = fightCooldown; + configSaver(); } public int getCooldown() { return cooldown; } - public void setCooldown(int cooldown) { + public void setCooldown(int cooldown) throws Exception { this.cooldown = cooldown; + configSaver(); } } - public static final class Back { + public final class Back { private boolean enabled = true; + private String command = "back"; // TODO! do this for more commands /// Deletes the /back after teleporting, so you cant call /back twice. private boolean deleteAfterTeleport = false; @@ -163,20 +170,32 @@ public class configManager { return enabled; } - public void setEnabled(boolean enabled) { + public void setEnabled(boolean enabled) throws Exception { this.enabled = enabled; + configSaver(); + } + + public String getCommand() { + return command; + } + + public void setCommand(String command) throws Exception { + this.command = command; + configSaver(); + tools.reloadResources(teleportCommands.server); // Reload the commands } public boolean isDeleteAfterTeleport() { return deleteAfterTeleport; } - public void setDeleteAfterTeleport(boolean deleteAfterTeleport) { + public void setDeleteAfterTeleport(boolean deleteAfterTeleport) throws Exception { this.deleteAfterTeleport = deleteAfterTeleport; + configSaver(); } } - public static final class Home { + public final class Home { private boolean enabled = true; /// The maximum amount of homes a player can have private int playerMaximum = 20; @@ -187,41 +206,46 @@ public class configManager { return enabled; } - public void setEnabled(boolean enabled) { + public void setEnabled(boolean enabled) throws Exception { this.enabled = enabled; + configSaver(); } public int getPlayerMaximum() { return playerMaximum; } - public void setPlayerMaximum(int playerMaximum) { + public void setPlayerMaximum(int playerMaximum) throws Exception { this.playerMaximum = playerMaximum; + configSaver(); } public boolean isDeleteInvalid() { return deleteInvalid; } - public void setDeleteInvalid(boolean deleteInvalid) { + public void setDeleteInvalid(boolean deleteInvalid) throws Exception { this.deleteInvalid = deleteInvalid; + configSaver(); } } - public static final class Tpa { + public final class Tpa { private boolean enabled = true; public boolean isEnabled() { return enabled; } - public void setEnabled(boolean enabled) { + public void setEnabled(boolean enabled) throws Exception { this.enabled = enabled; + configSaver(); } } - public static final class Warp { + public final class Warp { private boolean enabled = true; + /// If a warp with an invalid dimension should get automatically deleted private boolean deleteInvalid = false; @@ -229,43 +253,57 @@ public class configManager { return enabled; } - public void setEnabled(boolean enabled) { + public void setEnabled(boolean enabled) throws Exception { this.enabled = enabled; + configSaver(); } public boolean isDeleteInvalid() { return deleteInvalid; } - public void setDeleteInvalid(boolean deleteInvalid) { + public void setDeleteInvalid(boolean deleteInvalid) throws Exception { this.deleteInvalid = deleteInvalid; + configSaver(); } } - public static final class WorldSpawn { + public final class WorldSpawn { private boolean enabled = true; + private String command = "worldspawn"; private String world_id = "minecraft:overworld"; public boolean isEnabled() { return enabled; } - public void setEnabled(boolean enabled) { + public void setEnabled(boolean enabled) throws Exception { this.enabled = enabled; + configSaver(); } public String getWorld_id() { return world_id; } - public void setWorld_id(String world_id) { + public void setWorld_id(String world_id) throws Exception { this.world_id = world_id; + configSaver(); + } + + public String getCommand() { + return command; + } + + public void setCommand(String command) throws Exception { + this.command = command; + configSaver(); + tools.reloadResources(teleportCommands.server); // Reload the commands } } } // --- Ideas! --- - // Make config options for disabling certain commands // Make config options for renaming certain commands // Make config option for changing required permission level for certain commands // Make config for setting max homes diff --git a/common/src/main/java/dev/mrsnowy/teleport_commands/utils/teleporter.java b/common/src/main/java/dev/mrsnowy/teleport_commands/utils/teleporter.java index 107873a..38e0583 100644 --- a/common/src/main/java/dev/mrsnowy/teleport_commands/utils/teleporter.java +++ b/common/src/main/java/dev/mrsnowy/teleport_commands/utils/teleporter.java @@ -2,7 +2,9 @@ package dev.mrsnowy.teleport_commands.utils; import dev.mrsnowy.teleport_commands.TeleportCommands; import net.minecraft.ChatFormatting; +import net.minecraft.core.BlockPos; import net.minecraft.core.particles.ParticleTypes; +import net.minecraft.network.chat.Component; import net.minecraft.server.MinecraftServer; import net.minecraft.server.level.ServerLevel; import net.minecraft.server.level.ServerPlayer; @@ -18,106 +20,142 @@ import static net.minecraft.sounds.SoundEvents.ENDERMAN_TELEPORT; public class teleporter { private final TeleportCommands teleportCommands; - private final Map playersData = new HashMap<>(); + private final Map players = new HashMap<>(); private static class PlayerData { - /// This value is set to when the teleport cooldown expires. - int teleportCooldownExpiry = 0; - boolean teleportCooldownExpired = true; + /// This value is set to when the teleport cooldown expires (note this is the *cooldown* between teleports, not the delay before teleporting!). + int teleportCooldownUntil = 0; + boolean teleportOnCooldown = false; /// This value is set to when the fight cooldown expires. - int fightCooldownExpiry = 0; - boolean fightCooldownExpired = true; + int fightCooldownUntil = 0; + boolean fightOnCooldown = false; /// A pending teleport, is null when nothing is pending. @Nullable pendingTeleport pendingTeleport = null; - -// Vec3 lastPosition = Vec3.ZERO; } private static class pendingTeleport { ServerLevel destinationWorld; + BlockPos startingCoords; Vec3 destinationCoords; - int teleportDelayExpiry; + int teleportDelayUntil; + /// The tps that will be upheld until the teleport is finished (for displaying purposes) + int tps; + /// Message that gets sent when the teleportation happens + String completionMessage; - pendingTeleport(ServerLevel destinationWorld, Vec3 destinationCoords, int teleportDelayExpiry) { + pendingTeleport(ServerLevel destinationWorld, Vec3 destinationCoords, BlockPos startingCoords, int teleportDelayUntil, int tps, String completionMessage) { this.destinationWorld = destinationWorld; this.destinationCoords = destinationCoords; - this.teleportDelayExpiry = teleportDelayExpiry; + this.startingCoords = startingCoords; + this.teleportDelayUntil = teleportDelayUntil; + this.tps = tps; + this.completionMessage = completionMessage; } } + // ---- + public teleporter(TeleportCommands teleportCommands) { this.teleportCommands = teleportCommands; } - /// This gets ran every tick - public void checkPlayerData(MinecraftServer server) { + /// This function checks if any of the timers/cooldowns/delays have expired of each player in the "players" hashmap. + /// This gets ran every tick. + public void tick(MinecraftServer server) { int currentTick = server.getTickCount(); - playersData.entrySet().removeIf(entry -> { + players.entrySet().removeIf(entry -> { PlayerData data = entry.getValue(); + boolean wasOnCooldown = data.teleportOnCooldown || data.fightOnCooldown; - // Check if we are past the cooldown - if (!data.teleportCooldownExpired && (currentTick >= data.teleportCooldownExpiry)) { - data.teleportCooldownExpired = true; - - ServerPlayer player = server.getPlayerList().getPlayer(entry.getKey()); - if (player != null) { - /// TODO! add actual generic message (just copied this one) - player.displayClientMessage(getTranslatedText("commands.teleport_commands.warp.exists", player).withStyle(ChatFormatting.WHITE), false); - } + if (data.teleportOnCooldown && (currentTick >= data.teleportCooldownUntil)) { + data.teleportOnCooldown = false; } - // Check if we are past the cooldown - if (!data.fightCooldownExpired && (currentTick >= data.fightCooldownExpiry)) { - data.fightCooldownExpired = true; + if (data.fightOnCooldown && (currentTick >= data.fightCooldownUntil)) { + data.fightOnCooldown = false; + } + // Let the player know when the cooldowns are expired and that they are cool to teleport again + if (wasOnCooldown && !data.teleportOnCooldown && !data.fightOnCooldown) { ServerPlayer player = server.getPlayerList().getPlayer(entry.getKey()); if (player != null) { - /// TODO! add actual generic message (just copied this one) - player.displayClientMessage(getTranslatedText("commands.teleport_commands.warp.exists", player).withStyle(ChatFormatting.WHITE), false); + player.displayClientMessage(getTranslatedText("commands.teleport_commands.teleport.ready", player).withStyle(ChatFormatting.WHITE), true); } } - /// Check if there is a pending teleport request and if we are ready to teleport (we ignore the fightDelay since that is only relevant for starting a request) - if (data.pendingTeleport != null && (currentTick >= data.pendingTeleport.teleportDelayExpiry)) { + // Check if there is a pending teleport request (and if the delay is over) + if (data.pendingTeleport != null) { ServerPlayer player = server.getPlayerList().getPlayer(entry.getKey()); - if (player != null) { - teleport(player, data.pendingTeleport.destinationWorld, data.pendingTeleport.destinationCoords); - } - data.pendingTeleport = null; + /// delay is over + if (currentTick >= data.pendingTeleport.teleportDelayUntil) { + if (player != null) { + teleport(player, data.pendingTeleport.destinationWorld, data.pendingTeleport.destinationCoords, data.pendingTeleport.completionMessage); + } + + data.pendingTeleport = null; + } else { + // check if this is a whole number + float secondsLeft = (float) (data.pendingTeleport.teleportDelayUntil - currentTick) / data.pendingTeleport.tps; + if ((secondsLeft % 1) == 0 && player != null) { + player.displayClientMessage(getTranslatedText("commands.teleport_commands.teleport.progress", player).withStyle(ChatFormatting.WHITE), true); + } + } } - return (data.teleportCooldownExpired && data.fightCooldownExpired); + + + // remove the entry if there is no cooldowns and no teleports happening + return (!data.teleportOnCooldown && !data.fightOnCooldown && data.pendingTeleport == null); }); } - /// Teleport the player :P - public void teleportQueue( ServerPlayer player, ServerLevel world, Vec3 coords) { + /// Adds the player to the teleportation queue + public void queue(ServerPlayer player, ServerLevel world, Vec3 coords) { + queue(player, world, coords, "commands.teleport_commands.teleport.go"); + } + + /// Adds the player to the teleportation queue + public void queue(ServerPlayer player, ServerLevel world, Vec3 coords, String completionMessage) { // Check if user is allowed to teleport by config settings UUID playerUUID = player.getUUID(); - - if (!playersData.containsKey(playerUUID)) { - playersData.put(playerUUID, new PlayerData()); + if (!players.containsKey(playerUUID)) { + players.put(playerUUID, new PlayerData()); } - PlayerData data = playersData.get(playerUUID); + PlayerData data = players.get(playerUUID); + int currentTick = teleportCommands.server.getTickCount(); + int tps = (int) (1.0 / teleportCommands.server.tickRateManager().tickrate()); // Check if we are already teleporting if (data.pendingTeleport != null) { - /// TODO! add actual generic message (just copied this one) - player.displayClientMessage(getTranslatedText("commands.teleport_commands.teleporting.delay", player).withStyle(ChatFormatting.WHITE), false); + int ticksLeft = data.pendingTeleport.teleportDelayUntil - currentTick; + int secondsLeft = (int) Math.ceil( (double) ticksLeft / data.pendingTeleport.tps); + + player.displayClientMessage(getTranslatedText("commands.teleport_commands.teleport.delay", player, + Component.literal(String.valueOf(secondsLeft)), + Component.literal(String.valueOf(ticksLeft)) + ).withStyle(ChatFormatting.WHITE), false); + return; } - // Check if the teleport cooldowns are expired. - if (!data.teleportCooldownExpired || !data.fightCooldownExpired) { - /// TODO! add actual generic message (just copied this one) (and add seconds left :P) - player.displayClientMessage(getTranslatedText("commands.teleport_commands.teleporting.delay", player).withStyle(ChatFormatting.WHITE), false); + // Check if we are still on cooldown + if (data.teleportOnCooldown || data.fightOnCooldown) { + int cooldownUntil = Math.max(data.teleportCooldownUntil, data.fightCooldownUntil); + int ticksLeft = cooldownUntil - currentTick; + int secondsLeft = (int) Math.ceil( (double) ticksLeft / tps); + + player.displayClientMessage(getTranslatedText("commands.teleport_commands.teleport.cooldown", player, + Component.literal(String.valueOf(secondsLeft)), + Component.literal(String.valueOf(ticksLeft)) + ).withStyle(ChatFormatting.WHITE), false); + return; } @@ -125,11 +163,12 @@ public class teleporter { int teleportingDelay = teleportCommands.config.config.teleporting.getDelay(); if (teleportingDelay >= 0) { - int currentTick = teleportCommands.server.getTickCount(); - data.pendingTeleport = new pendingTeleport(world, coords, currentTick + (teleportingDelay * 20)); + BlockPos currentPos = player.blockPosition(); + + data.pendingTeleport = new pendingTeleport(world, coords, currentPos, currentTick + (teleportingDelay * 20), tps, completionMessage); } else { // bypass the delay - teleport(player, world, coords); + teleport(player, world, coords, completionMessage); } @@ -141,17 +180,16 @@ public class teleporter { } - - private void teleport(ServerPlayer player, ServerLevel world, Vec3 coords) { + /// Teleports the player :P + private void teleport(ServerPlayer player, ServerLevel world, Vec3 coords, String completionMessage) { // teleportation effects & sounds before teleporting world.sendParticles(ParticleTypes.SNOWFLAKE, player.getX(), player.getY() + 1, player.getZ(), 20, 0.0D, 0.0D, 0.0D, 0.01); world.sendParticles(ParticleTypes.WHITE_SMOKE, player.getX(), player.getY(), player.getZ(), 15, 0.0D, 1.0D, 0.0D, 0.03); world.playSound(null, player.blockPosition(), SoundEvent.createVariableRangeEvent(ENDERMAN_TELEPORT.location()), SoundSource.PLAYERS, 0.4f, 1.0f); - // check if the player is currently flying boolean flying = player.getAbilities().flying; - // teleport! + player.displayClientMessage(getTranslatedText(completionMessage, player).withStyle(ChatFormatting.WHITE), true); player.teleportTo(world, coords.x, coords.y, coords.z, Set.of(), player.getYRot(), player.getXRot(), false); // Restore flying when teleporting trough dimensions @@ -165,4 +203,45 @@ public class teleporter { world.sendParticles(ParticleTypes.SNOWFLAKE, player.getX(), player.getY() , player.getZ(), 20, 0.0D, 1.0D, 0.0D, 0.01); world.sendParticles(ParticleTypes.WHITE_SMOKE, player.getX(), player.getY(), player.getZ(), 15, 0.0D, 0.0D, 0.0D, 0.03); } + + + public void reportPlayerMoved(ServerPlayer player) { + if (teleportCommands.config.config.teleporting.isAllowMoving()) { + return; // The config option isn't disabled + } + + PlayerData data = players.get(player.getUUID()); + + if (data != null && data.pendingTeleport != null) { + BlockPos pos = player.blockPosition(); + boolean tooFar = data.pendingTeleport.startingCoords.closerThan(pos, 1.5); // Checks if they moved more than one block (1.5 for diagonals) + + if (tooFar) { + player.displayClientMessage(getTranslatedText("commands.teleport_commands.teleport.moving", player).withStyle(ChatFormatting.WHITE), true); + data.pendingTeleport = null; + } + + } + } + + public void reportPlayerHurt(ServerPlayer player) { + if (teleportCommands.config.config.teleporting.isAllowFighting()) { + return; // The config option isn't disabled + } + + PlayerData data = players.get(player.getUUID()); + + if (data != null) { + int currentTick = teleportCommands.server.getTickCount(); + + data.fightCooldownUntil = currentTick + teleportCommands.config.config.teleporting.getFightCooldown(); + data.fightOnCooldown = true; + + if (data.pendingTeleport != null) { + player.displayClientMessage(getTranslatedText("commands.teleport_commands.teleport.fighting", player).withStyle(ChatFormatting.WHITE), true); + data.pendingTeleport = null; + } + } + + } } diff --git a/common/src/main/java/dev/mrsnowy/teleport_commands/utils/tools.java b/common/src/main/java/dev/mrsnowy/teleport_commands/utils/tools.java index 6f6d1c3..10eeab0 100644 --- a/common/src/main/java/dev/mrsnowy/teleport_commands/utils/tools.java +++ b/common/src/main/java/dev/mrsnowy/teleport_commands/utils/tools.java @@ -185,4 +185,10 @@ public class tools { } return false; // it's not safe! } + + /// This function reloads "reloadable resources" which includes commands + public static void reloadResources(MinecraftServer server) { + Collection collection = server.getPackRepository().getSelectedIds(); + server.reloadResources(collection); + } } diff --git a/common/src/main/resources/assets/teleport_commands/lang/en_us.json b/common/src/main/resources/assets/teleport_commands/lang/en_us.json index 80a937a..0a0761a 100644 --- a/common/src/main/resources/assets/teleport_commands/lang/en_us.json +++ b/common/src/main/resources/assets/teleport_commands/lang/en_us.json @@ -52,6 +52,14 @@ "commands.teleport_commands.tpa.accepted": "Request accepted", "commands.teleport_commands.tpa.denied": "Request denied", + "commands.teleport_commands.teleport.go": "Teleporting", + "commands.teleport_commands.teleport.progress": "Teleporting in %0% seconds (%1% ticks)", + "commands.teleport_commands.teleport.delay": "You are already teleporting! (%0% seconds / %1% ticks left)", + "commands.teleport_commands.teleport.ready": "Teleportation cooldowns have expired.", + "commands.teleport_commands.teleport.onCooldown": "You are still on cooldown!\nPlease wait %0% seconds (%1% ticks) before teleporting.", + "commands.teleport_commands.teleport.moving": "Teleportation has been canceled.\nPlease remain still while teleporting!", + "commands.teleport_commands.teleport.fighting": "Teleportation has been canceled.\nPlease do not fight while teleporting!", + "commands.teleport_commands.common.teleport": "Teleporting", "commands.teleport_commands.common.error": "An error occurred while teleporting!", "commands.teleport_commands.common.noSafeLocation": "No safe location has been found!",