diff --git a/src/main/java/com/lovetropics/minigames/client/game/handler/GameCraftingBeeHandler.java b/src/main/java/com/lovetropics/minigames/client/game/handler/GameCraftingBeeHandler.java index 0bc3d57ca..17ae50e2d 100644 --- a/src/main/java/com/lovetropics/minigames/client/game/handler/GameCraftingBeeHandler.java +++ b/src/main/java/com/lovetropics/minigames/client/game/handler/GameCraftingBeeHandler.java @@ -5,7 +5,7 @@ import com.lovetropics.minigames.common.content.crafting_bee.CraftingBeeTexts; import com.lovetropics.minigames.common.content.crafting_bee.SelectedRecipe; import com.lovetropics.minigames.common.core.game.client_state.GameClientStateTypes; -import com.lovetropics.minigames.common.core.game.client_state.instance.CraftingBeeCrafts; +import com.lovetropics.minigames.common.core.game.client_state.instance.CraftingBeeCraftsClientState; import com.mojang.blaze3d.platform.GlStateManager; import com.mojang.blaze3d.platform.Lighting; import com.mojang.blaze3d.systems.RenderSystem; @@ -188,7 +188,7 @@ protected void updateWidgetNarration(NarrationElementOutput narrationElementOutp } @Nullable - private static CraftingBeeCrafts getState() { + private static CraftingBeeCraftsClientState getState() { return ClientGameStateManager.getOrNull(GameClientStateTypes.CRAFTING_BEE_CRAFTS); } diff --git a/src/main/java/com/lovetropics/minigames/common/content/crafting_bee/CraftingBeeBehavior.java b/src/main/java/com/lovetropics/minigames/common/content/crafting_bee/CraftingBeeBehavior.java index 4ae575f2e..8e7da80ff 100644 --- a/src/main/java/com/lovetropics/minigames/common/content/crafting_bee/CraftingBeeBehavior.java +++ b/src/main/java/com/lovetropics/minigames/common/content/crafting_bee/CraftingBeeBehavior.java @@ -14,9 +14,8 @@ import com.lovetropics.minigames.common.core.game.behavior.event.GamePhaseEvents; import com.lovetropics.minigames.common.core.game.behavior.event.GamePlayerEvents; import com.lovetropics.minigames.common.core.game.client_state.GameClientState; -import com.lovetropics.minigames.common.core.game.client_state.instance.CraftingBeeCrafts; +import com.lovetropics.minigames.common.core.game.client_state.instance.CraftingBeeCraftsClientState; import com.lovetropics.minigames.common.core.game.player.PlayerSet; -import com.lovetropics.minigames.common.core.game.state.statistics.PlayerKey; import com.lovetropics.minigames.common.core.game.state.statistics.StatisticKey; import com.lovetropics.minigames.common.core.game.state.team.GameTeam; import com.lovetropics.minigames.common.core.game.state.team.GameTeamKey; @@ -183,7 +182,7 @@ private void sync(GameTeamKey team) { private void sync(Player player) { if (player instanceof ServerPlayer sp) { - GameClientState.sendToPlayer(new CraftingBeeCrafts(tasks.get(teams.getTeamForPlayer(player)).stream().map(CraftingTask::toCraft).toList(), + GameClientState.sendToPlayer(new CraftingBeeCraftsClientState(tasks.get(teams.getTeamForPlayer(player)).stream().map(CraftingTask::toCraft).toList(), game.gameUuid(), allowedHints), sp); } } @@ -203,8 +202,8 @@ private CraftingTask(ItemStack output, SelectedRecipe recipe) { this.recipe = recipe; } - public CraftingBeeCrafts.Craft toCraft() { - return new CraftingBeeCrafts.Craft(output, recipe.id(), done); + public CraftingBeeCraftsClientState.Craft toCraft() { + return new CraftingBeeCraftsClientState.Craft(output, recipe.id(), done); } } } diff --git a/src/main/java/com/lovetropics/minigames/common/core/game/client_state/GameClientStateTypes.java b/src/main/java/com/lovetropics/minigames/common/core/game/client_state/GameClientStateTypes.java index 61b2693c2..58bd0a849 100644 --- a/src/main/java/com/lovetropics/minigames/common/core/game/client_state/GameClientStateTypes.java +++ b/src/main/java/com/lovetropics/minigames/common/core/game/client_state/GameClientStateTypes.java @@ -2,16 +2,18 @@ import com.lovetropics.minigames.LoveTropics; import com.lovetropics.minigames.common.core.game.client_state.instance.BeaconClientState; -import com.lovetropics.minigames.common.core.game.client_state.instance.CraftingBeeCrafts; +import com.lovetropics.minigames.common.core.game.client_state.instance.CraftingBeeCraftsClientState; import com.lovetropics.minigames.common.core.game.client_state.instance.FogClientState; import com.lovetropics.minigames.common.core.game.client_state.instance.GlowTeamMembersState; import com.lovetropics.minigames.common.core.game.client_state.instance.HealthTagClientState; -import com.lovetropics.minigames.common.core.game.client_state.instance.HideRecipeBookState; +import com.lovetropics.minigames.common.core.game.client_state.instance.HideRecipeBookClientState; +import com.lovetropics.minigames.common.core.game.client_state.instance.InvertControlsClientState; import com.lovetropics.minigames.common.core.game.client_state.instance.PointTagClientState; import com.lovetropics.minigames.common.core.game.client_state.instance.ReplaceTexturesClientState; import com.lovetropics.minigames.common.core.game.client_state.instance.ResourcePackClientState; import com.lovetropics.minigames.common.core.game.client_state.instance.SidebarClientState; import com.lovetropics.minigames.common.core.game.client_state.instance.SpectatingClientState; +import com.lovetropics.minigames.common.core.game.client_state.instance.SwapMovementClientState; import com.lovetropics.minigames.common.core.game.client_state.instance.TeamMembersClientState; import com.lovetropics.minigames.common.core.game.client_state.instance.TimeInterpolationClientState; import com.lovetropics.minigames.common.util.registry.GameClientTweakEntry; @@ -45,8 +47,10 @@ public final class GameClientStateTypes { public static final GameClientTweakEntry TEAM_MEMBERS = register("team_members", TeamMembersClientState.CODEC); public static final GameClientTweakEntry GLOW_TEAM_MEMBERS = register("glow_team_members", MapCodec.unit(GlowTeamMembersState.INSTANCE)); public static final GameClientTweakEntry POINT_TAGS = register("point_tags", PointTagClientState.CODEC); - public static final GameClientTweakEntry HIDE_RECIPE_BOOK = register("hide_recipe_book", HideRecipeBookState.CODEC); - public static final GameClientTweakEntry CRAFTING_BEE_CRAFTS = register("crafting_bee_crafts", CraftingBeeCrafts.CODEC); + public static final GameClientTweakEntry HIDE_RECIPE_BOOK = register("hide_recipe_book", HideRecipeBookClientState.CODEC); + public static final GameClientTweakEntry CRAFTING_BEE_CRAFTS = register("crafting_bee_crafts", CraftingBeeCraftsClientState.CODEC); + public static final GameClientTweakEntry INVERT_CONTROLS = register("invert_controls", InvertControlsClientState.CODEC); + public static final GameClientTweakEntry SWAP_MOVEMENT = register("swap_movement", SwapMovementClientState.CODEC); public static GameClientTweakEntry register(final String name, final MapCodec codec) { return REGISTRATE.object(name) diff --git a/src/main/java/com/lovetropics/minigames/common/core/game/client_state/instance/CraftingBeeCrafts.java b/src/main/java/com/lovetropics/minigames/common/core/game/client_state/instance/CraftingBeeCraftsClientState.java similarity index 78% rename from src/main/java/com/lovetropics/minigames/common/core/game/client_state/instance/CraftingBeeCrafts.java rename to src/main/java/com/lovetropics/minigames/common/core/game/client_state/instance/CraftingBeeCraftsClientState.java index 4ad5f7622..c53690080 100644 --- a/src/main/java/com/lovetropics/minigames/common/core/game/client_state/instance/CraftingBeeCrafts.java +++ b/src/main/java/com/lovetropics/minigames/common/core/game/client_state/instance/CraftingBeeCraftsClientState.java @@ -8,18 +8,17 @@ import com.mojang.serialization.codecs.RecordCodecBuilder; import net.minecraft.core.UUIDUtil; import net.minecraft.resources.ResourceLocation; -import net.minecraft.util.ExtraCodecs; import net.minecraft.world.item.ItemStack; import java.util.List; import java.util.UUID; -public record CraftingBeeCrafts(List crafts, UUID gameId, int allowedHints) implements GameClientState { - public static final MapCodec CODEC = RecordCodecBuilder.mapCodec(in -> in.group( - Craft.CODEC.listOf().fieldOf("crafts").forGetter(CraftingBeeCrafts::crafts), - UUIDUtil.CODEC.fieldOf("gameId").forGetter(CraftingBeeCrafts::gameId), - Codec.INT.fieldOf("allowedHints").forGetter(CraftingBeeCrafts::allowedHints) - ).apply(in, CraftingBeeCrafts::new)); +public record CraftingBeeCraftsClientState(List crafts, UUID gameId, int allowedHints) implements GameClientState { + public static final MapCodec CODEC = RecordCodecBuilder.mapCodec(in -> in.group( + Craft.CODEC.listOf().fieldOf("crafts").forGetter(CraftingBeeCraftsClientState::crafts), + UUIDUtil.CODEC.fieldOf("gameId").forGetter(CraftingBeeCraftsClientState::gameId), + Codec.INT.fieldOf("allowedHints").forGetter(CraftingBeeCraftsClientState::allowedHints) + ).apply(in, CraftingBeeCraftsClientState::new)); @Override public GameClientStateType getType() { diff --git a/src/main/java/com/lovetropics/minigames/common/core/game/client_state/instance/HideRecipeBookState.java b/src/main/java/com/lovetropics/minigames/common/core/game/client_state/instance/HideRecipeBookClientState.java similarity index 67% rename from src/main/java/com/lovetropics/minigames/common/core/game/client_state/instance/HideRecipeBookState.java rename to src/main/java/com/lovetropics/minigames/common/core/game/client_state/instance/HideRecipeBookClientState.java index 4ab26155c..16d5959fe 100644 --- a/src/main/java/com/lovetropics/minigames/common/core/game/client_state/instance/HideRecipeBookState.java +++ b/src/main/java/com/lovetropics/minigames/common/core/game/client_state/instance/HideRecipeBookClientState.java @@ -7,9 +7,9 @@ import net.minecraft.network.chat.Component; import net.minecraft.network.chat.ComponentSerialization; -public record HideRecipeBookState(Component message) implements GameClientState { - public static final MapCodec CODEC = ComponentSerialization.CODEC - .fieldOf("message").xmap(HideRecipeBookState::new, HideRecipeBookState::message); +public record HideRecipeBookClientState(Component message) implements GameClientState { + public static final MapCodec CODEC = ComponentSerialization.CODEC + .fieldOf("message").xmap(HideRecipeBookClientState::new, HideRecipeBookClientState::message); @Override public GameClientStateType getType() { diff --git a/src/main/java/com/lovetropics/minigames/common/core/game/client_state/instance/InvertControlsClientState.java b/src/main/java/com/lovetropics/minigames/common/core/game/client_state/instance/InvertControlsClientState.java new file mode 100644 index 000000000..1efe55742 --- /dev/null +++ b/src/main/java/com/lovetropics/minigames/common/core/game/client_state/instance/InvertControlsClientState.java @@ -0,0 +1,20 @@ +package com.lovetropics.minigames.common.core.game.client_state.instance; + +import com.lovetropics.minigames.common.core.game.client_state.GameClientState; +import com.lovetropics.minigames.common.core.game.client_state.GameClientStateType; +import com.lovetropics.minigames.common.core.game.client_state.GameClientStateTypes; +import com.mojang.serialization.Codec; +import com.mojang.serialization.MapCodec; +import com.mojang.serialization.codecs.RecordCodecBuilder; + +public record InvertControlsClientState(boolean xAxis, boolean yAxis) implements GameClientState { + public static final MapCodec CODEC = RecordCodecBuilder.mapCodec(in -> in.group( + Codec.BOOL.optionalFieldOf("x_axis", false).forGetter(InvertControlsClientState::xAxis), + Codec.BOOL.optionalFieldOf("y_axis", true).forGetter(InvertControlsClientState::yAxis) + ).apply(in, InvertControlsClientState::new)); + + @Override + public GameClientStateType getType() { + return GameClientStateTypes.INVERT_CONTROLS.get(); + } +} diff --git a/src/main/java/com/lovetropics/minigames/common/core/game/client_state/instance/SwapMovementClientState.java b/src/main/java/com/lovetropics/minigames/common/core/game/client_state/instance/SwapMovementClientState.java new file mode 100644 index 000000000..8947e0945 --- /dev/null +++ b/src/main/java/com/lovetropics/minigames/common/core/game/client_state/instance/SwapMovementClientState.java @@ -0,0 +1,15 @@ +package com.lovetropics.minigames.common.core.game.client_state.instance; + +import com.lovetropics.minigames.common.core.game.client_state.GameClientState; +import com.lovetropics.minigames.common.core.game.client_state.GameClientStateType; +import com.lovetropics.minigames.common.core.game.client_state.GameClientStateTypes; +import com.mojang.serialization.MapCodec; + +public record SwapMovementClientState() implements GameClientState { + public static final MapCodec CODEC = MapCodec.unit(SwapMovementClientState::new); + + @Override + public GameClientStateType getType() { + return GameClientStateTypes.SWAP_MOVEMENT.get(); + } +} diff --git a/src/main/java/com/lovetropics/minigames/mixin/client/KeyboardInputMixin.java b/src/main/java/com/lovetropics/minigames/mixin/client/KeyboardInputMixin.java new file mode 100644 index 000000000..2bba29d54 --- /dev/null +++ b/src/main/java/com/lovetropics/minigames/mixin/client/KeyboardInputMixin.java @@ -0,0 +1,22 @@ +package com.lovetropics.minigames.mixin.client; + +import com.lovetropics.minigames.client.game.ClientGameStateManager; +import com.lovetropics.minigames.common.core.game.client_state.GameClientStateTypes; +import net.minecraft.client.player.Input; +import net.minecraft.client.player.KeyboardInput; +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; + +@Mixin(KeyboardInput.class) +public class KeyboardInputMixin extends Input { + @Inject(method = "tick", at = @At("TAIL")) + private void respectSwappedMovement(boolean isSneaking, float sneakingSpeedMultiplier, CallbackInfo ci) { + if (ClientGameStateManager.getOrNull(GameClientStateTypes.SWAP_MOVEMENT) != null) { + float oldLeft = leftImpulse; + leftImpulse = forwardImpulse; + forwardImpulse = oldLeft; + } + } +} diff --git a/src/main/java/com/lovetropics/minigames/mixin/client/MouseHandlerMixin.java b/src/main/java/com/lovetropics/minigames/mixin/client/MouseHandlerMixin.java new file mode 100644 index 000000000..81eb7d8f3 --- /dev/null +++ b/src/main/java/com/lovetropics/minigames/mixin/client/MouseHandlerMixin.java @@ -0,0 +1,37 @@ +package com.lovetropics.minigames.mixin.client; + +import com.llamalad7.mixinextras.injector.wrapoperation.Operation; +import com.llamalad7.mixinextras.injector.wrapoperation.WrapOperation; +import com.lovetropics.minigames.client.game.ClientGameStateManager; +import com.lovetropics.minigames.common.core.game.client_state.GameClientStateTypes; +import net.minecraft.client.Minecraft; +import net.minecraft.client.MouseHandler; +import net.minecraft.client.player.LocalPlayer; +import org.spongepowered.asm.mixin.Final; +import org.spongepowered.asm.mixin.Mixin; +import org.spongepowered.asm.mixin.Shadow; +import org.spongepowered.asm.mixin.injection.At; + +@Mixin(MouseHandler.class) +public class MouseHandlerMixin { + @Shadow + @Final + private Minecraft minecraft; + + @WrapOperation(method = "turnPlayer", at = @At(value = "INVOKE", target = "Lnet/minecraft/client/player/LocalPlayer;turn(DD)V")) + private void respectControlModificationState(LocalPlayer player, double dx, double dy, Operation original) { + var state = ClientGameStateManager.getOrNull(GameClientStateTypes.INVERT_CONTROLS); + if (state != null) { + if (state.xAxis()) { + dx = dx * -1; + } + + // Avoid allowing the bypass of the setting by modifying the options + if (state.yAxis() && !minecraft.options.invertYMouse().get()) { + dy = dy * -1; + } + } + + original.call(player, dx, dy); + } +} diff --git a/src/main/resources/ltminigames.mixins.json b/src/main/resources/ltminigames.mixins.json index 4397675e9..be228bab1 100644 --- a/src/main/resources/ltminigames.mixins.json +++ b/src/main/resources/ltminigames.mixins.json @@ -29,7 +29,9 @@ "client.MinecraftMixin", "client.PlayerTabOverlayGuiMixin", "client.PoseStackAccessor", - "client.HiddenRecipeBookMixin" + "client.HiddenRecipeBookMixin", + "client.MouseHandlerMixin", + "client.KeyboardInputMixin" ], "injectors": { "defaultRequire": 1