From dcaaca149b8c85507f0b60a91ee92817051c099c Mon Sep 17 00:00:00 2001 From: Sollace Date: Fri, 26 Apr 2024 16:09:37 +0100 Subject: [PATCH] Synchronise server configs to the client --- .../com/minelittlepony/unicopia/Config.java | 6 +++++ .../unicopia/InteractionManager.java | 14 +++++++++++ .../minelittlepony/unicopia/SyncedConfig.java | 8 ++++++ .../com/minelittlepony/unicopia/Unicopia.java | 1 - .../unicopia/command/ConfigCommand.java | 20 +++++++++++---- .../unicopia/entity/Creature.java | 4 +-- .../unicopia/entity/player/PlayerPhysics.java | 2 +- .../unicopia/network/Channel.java | 5 ++-- .../network/MsgConfigurationChange.java | 25 +++++++++++++++++++ .../handler/ClientNetworkHandlerImpl.java | 6 +++++ 10 files changed, 80 insertions(+), 11 deletions(-) create mode 100644 src/main/java/com/minelittlepony/unicopia/SyncedConfig.java create mode 100644 src/main/java/com/minelittlepony/unicopia/network/MsgConfigurationChange.java diff --git a/src/main/java/com/minelittlepony/unicopia/Config.java b/src/main/java/com/minelittlepony/unicopia/Config.java index af798840..0eba3a8d 100644 --- a/src/main/java/com/minelittlepony/unicopia/Config.java +++ b/src/main/java/com/minelittlepony/unicopia/Config.java @@ -15,9 +15,11 @@ public class Config extends com.minelittlepony.common.util.settings.Config { .addComment("whilst any ones left off are not permitted") .addComment("An empty list disables whitelisting entirely."); + @Deprecated public final Setting> wantItNeedItEntityExcludelist = value("server", "wantItNeedItEntityExcludelist", (Set)new HashSet<>(Set.of("minecraft:creeper"))) .addComment("A list of entity types that are immune to the want it need it spell's effects"); + @Deprecated public final Setting> dimensionsWithoutAtmosphere = value("server", "dimensionsWithoutAtmosphere", (Set)new HashSet()) .addComment("A list of dimensions ids that do not have an atmosphere, and thus shouldn't allow pegasi to fly."); @@ -66,4 +68,8 @@ public class Config extends com.minelittlepony.common.util.settings.Config { .registerTypeAdapter(Race.class, RegistryTypeAdapter.of(Race.REGISTRY)) ), GamePaths.getConfigDirectory().resolve("unicopia.json")); } + + public SyncedConfig toSynced() { + return new SyncedConfig(wantItNeedItEntityExcludelist.get(), dimensionsWithoutAtmosphere.get()); + } } diff --git a/src/main/java/com/minelittlepony/unicopia/InteractionManager.java b/src/main/java/com/minelittlepony/unicopia/InteractionManager.java index af191c63..d865eb70 100644 --- a/src/main/java/com/minelittlepony/unicopia/InteractionManager.java +++ b/src/main/java/com/minelittlepony/unicopia/InteractionManager.java @@ -34,6 +34,9 @@ public class InteractionManager { private static InteractionManager INSTANCE = new InteractionManager(); + @Nullable + private SyncedConfig config; + public static InteractionManager getInstance() { return INSTANCE; } @@ -110,4 +113,15 @@ public class InteractionManager { public final Race getClientSpecies() { return getClientPony().map(Pony::getSpecies).orElse(Race.HUMAN); } + + public void setSyncedConfig(SyncedConfig config) { + this.config = config; + } + + public SyncedConfig getSyncedConfig() { + if (config == null) { + config = Unicopia.getConfig().toSynced(); + } + return config; + } } diff --git a/src/main/java/com/minelittlepony/unicopia/SyncedConfig.java b/src/main/java/com/minelittlepony/unicopia/SyncedConfig.java new file mode 100644 index 00000000..6bbf4f6e --- /dev/null +++ b/src/main/java/com/minelittlepony/unicopia/SyncedConfig.java @@ -0,0 +1,8 @@ +package com.minelittlepony.unicopia; + +import java.util.Set; + +public record SyncedConfig ( + Set wantItNeedItExcludeList, + Set dimensionsWithoutAtmosphere) { +} diff --git a/src/main/java/com/minelittlepony/unicopia/Unicopia.java b/src/main/java/com/minelittlepony/unicopia/Unicopia.java index 72d53377..29c01867 100644 --- a/src/main/java/com/minelittlepony/unicopia/Unicopia.java +++ b/src/main/java/com/minelittlepony/unicopia/Unicopia.java @@ -8,7 +8,6 @@ import net.minecraft.util.Identifier; import org.apache.logging.log4j.LogManager; import org.apache.logging.log4j.Logger; - import com.minelittlepony.unicopia.ability.Abilities; import com.minelittlepony.unicopia.ability.data.tree.TreeTypeLoader; import com.minelittlepony.unicopia.ability.magic.spell.effect.SpellType; diff --git a/src/main/java/com/minelittlepony/unicopia/command/ConfigCommand.java b/src/main/java/com/minelittlepony/unicopia/command/ConfigCommand.java index 10cd162a..81b0abab 100644 --- a/src/main/java/com/minelittlepony/unicopia/command/ConfigCommand.java +++ b/src/main/java/com/minelittlepony/unicopia/command/ConfigCommand.java @@ -4,9 +4,12 @@ import java.util.HashSet; import java.util.Objects; import java.util.Set; import java.util.function.Function; -import com.minelittlepony.common.util.settings.Config; import com.minelittlepony.common.util.settings.Setting; +import com.minelittlepony.unicopia.Config; +import com.minelittlepony.unicopia.InteractionManager; import com.minelittlepony.unicopia.Unicopia; +import com.minelittlepony.unicopia.network.Channel; +import com.minelittlepony.unicopia.network.MsgConfigurationChange; import com.mojang.brigadier.builder.LiteralArgumentBuilder; import com.mojang.brigadier.exceptions.CommandSyntaxException; import com.mojang.brigadier.suggestion.SuggestionProvider; @@ -36,10 +39,10 @@ public class ConfigCommand { return CommandManager.literal(configName) .then(CommandManager.literal("clear").executes(source -> { source.getSource().sendFeedback(() -> Text.translatable("command.unicopia.config.clear", configName), true); - return changeProperty(configName, values -> new HashSet<>()); + return changeProperty(source.getSource(), configName, values -> new HashSet<>()); })) .then(CommandManager.literal("add").then( - CommandManager.argument("id", IdentifierArgumentType.identifier()).suggests(suggestions).executes(source -> ConfigCommand.>changeProperty(configName, values -> { + CommandManager.argument("id", IdentifierArgumentType.identifier()).suggests(suggestions).executes(source -> ConfigCommand.>changeProperty(source.getSource(), configName, values -> { String value = IdentifierArgumentType.getIdentifier(source, "id").toString(); source.getSource().sendFeedback(() -> Text.translatable("command.unicopia.config.add", value, configName), true); values.add(value); @@ -52,7 +55,7 @@ public class ConfigCommand { .map(Identifier::tryParse) .filter(Objects::nonNull) .toList(), builder); - }).executes(source -> ConfigCommand.>changeProperty(configName, values -> { + }).executes(source -> ConfigCommand.>changeProperty(source.getSource(), configName, values -> { String value = IdentifierArgumentType.getIdentifier(source, "id").toString(); source.getSource().sendFeedback(() -> Text.translatable("command.unicopia.config.remove", value, configName), true); values.remove(value); @@ -73,11 +76,18 @@ public class ConfigCommand { return (context, builder) -> CommandSource.suggestIdentifiers(wrapper.streamKeys().map(RegistryKey::getValue), builder); } - private static int changeProperty(String configName, Function changer) { + private static int changeProperty(ServerCommandSource source, String configName, Function changer) { Config config = Unicopia.getConfig(); Setting setting = config.getCategory("server").get(configName); setting.set(changer.apply(setting.get())); config.save(); + + MsgConfigurationChange msg = new MsgConfigurationChange(config.toSynced()); + InteractionManager.getInstance().setSyncedConfig(msg.config()); + source.getServer().getPlayerManager().getPlayerList().forEach(recipient -> { + Channel.CONFIGURATION_CHANGE.sendToPlayer(msg, recipient); + }); + return 0; } diff --git a/src/main/java/com/minelittlepony/unicopia/entity/Creature.java b/src/main/java/com/minelittlepony/unicopia/entity/Creature.java index 77d0c083..cd0277dd 100644 --- a/src/main/java/com/minelittlepony/unicopia/entity/Creature.java +++ b/src/main/java/com/minelittlepony/unicopia/entity/Creature.java @@ -7,8 +7,8 @@ import org.jetbrains.annotations.NotNull; import org.jetbrains.annotations.Nullable; import com.minelittlepony.unicopia.Affinity; +import com.minelittlepony.unicopia.InteractionManager; import com.minelittlepony.unicopia.Race; -import com.minelittlepony.unicopia.Unicopia; import com.minelittlepony.unicopia.WeaklyOwned; import com.minelittlepony.unicopia.ability.magic.*; import com.minelittlepony.unicopia.ability.magic.spell.Spell; @@ -147,7 +147,7 @@ public class Creature extends Living implements WeaklyOwned.Mutabl DynamicTargetGoal targetter = new DynamicTargetGoal((MobEntity)entity); targets.add(1, targetter); - if (!Unicopia.getConfig().wantItNeedItEntityExcludelist.get().contains(EntityType.getId(entity.getType()).toString())) { + if (!InteractionManager.getInstance().getSyncedConfig().wantItNeedItExcludeList().contains(EntityType.getId(entity.getType()).toString())) { goals.add(1, new WantItTakeItGoal(this, targetter)); } if (entity.getType().getSpawnGroup() == SpawnGroup.MONSTER) { diff --git a/src/main/java/com/minelittlepony/unicopia/entity/player/PlayerPhysics.java b/src/main/java/com/minelittlepony/unicopia/entity/player/PlayerPhysics.java index 699a2e95..8aed9af4 100644 --- a/src/main/java/com/minelittlepony/unicopia/entity/player/PlayerPhysics.java +++ b/src/main/java/com/minelittlepony/unicopia/entity/player/PlayerPhysics.java @@ -199,7 +199,7 @@ public class PlayerPhysics extends EntityPhysics implements Tickab DimensionType dimension = entity.getWorld().getDimension(); if ((RegistryUtils.isIn(entity.getWorld(), dimension, RegistryKeys.DIMENSION_TYPE, UTags.DimensionTypes.HAS_NO_ATMOSPHERE) - || Unicopia.getConfig().dimensionsWithoutAtmosphere.get().contains(RegistryUtils.getId(entity.getWorld(), dimension, RegistryKeys.DIMENSION_TYPE).toString())) + || InteractionManager.getInstance().getSyncedConfig().dimensionsWithoutAtmosphere().contains(RegistryUtils.getId(entity.getWorld(), dimension, RegistryKeys.DIMENSION_TYPE).toString())) && !OxygenApi.API.get().hasOxygen(entity.getWorld(), entity.getBlockPos())) { return FlightType.NONE; } diff --git a/src/main/java/com/minelittlepony/unicopia/network/Channel.java b/src/main/java/com/minelittlepony/unicopia/network/Channel.java index 3f65e69c..8e6bc8c2 100644 --- a/src/main/java/com/minelittlepony/unicopia/network/Channel.java +++ b/src/main/java/com/minelittlepony/unicopia/network/Channel.java @@ -34,6 +34,7 @@ public interface Channel { S2CPacketType SERVER_OTHER_PLAYER_CAPABILITIES = SimpleNetworking.serverToClient(Unicopia.id("other_player_capabilities"), MsgOtherPlayerCapabilities::new); S2CPacketType SERVER_PLAYER_ANIMATION_CHANGE = SimpleNetworking.serverToClient(Unicopia.id("other_player_animation_change"), MsgPlayerAnimationChange::new); S2CPacketType SERVER_SKY_ANGLE = SimpleNetworking.serverToClient(Unicopia.id("sky_angle"), MsgSkyAngle::new); + S2CPacketType CONFIGURATION_CHANGE = SimpleNetworking.serverToClient(Unicopia.id("config"), MsgConfigurationChange::new); S2CPacketType SERVER_ZAP_STAGE = SimpleNetworking.serverToClient(Unicopia.id("zap_stage"), MsgZapAppleStage::new); static void bootstrap() { @@ -53,8 +54,8 @@ public interface Channel { } sender.sendPacket(SERVER_RESOURCES.id(), new MsgServerResources().toBuffer()); sender.sendPacket(SERVER_SKY_ANGLE.id(), new MsgSkyAngle(UnicopiaWorldProperties.forWorld(handler.getPlayer().getServerWorld()).getTangentalSkyAngle()).toBuffer()); - ZapAppleStageStore store = ZapAppleStageStore.get(handler.player.getServerWorld()); - sender.sendPacket(SERVER_ZAP_STAGE.id(), new MsgZapAppleStage(store.getStage()).toBuffer()); + sender.sendPacket(CONFIGURATION_CHANGE.id(), new MsgConfigurationChange(InteractionManager.getInstance().getSyncedConfig()).toBuffer()); + sender.sendPacket(SERVER_ZAP_STAGE.id(), new MsgZapAppleStage(ZapAppleStageStore.get(handler.player.getServerWorld()).getStage()).toBuffer()); }); } } diff --git a/src/main/java/com/minelittlepony/unicopia/network/MsgConfigurationChange.java b/src/main/java/com/minelittlepony/unicopia/network/MsgConfigurationChange.java new file mode 100644 index 00000000..d1eb747c --- /dev/null +++ b/src/main/java/com/minelittlepony/unicopia/network/MsgConfigurationChange.java @@ -0,0 +1,25 @@ +package com.minelittlepony.unicopia.network; + +import java.util.HashSet; + +import com.minelittlepony.unicopia.SyncedConfig; +import com.sollace.fabwork.api.packets.Packet; + +import net.minecraft.entity.player.PlayerEntity; +import net.minecraft.network.PacketByteBuf; + +public record MsgConfigurationChange(SyncedConfig config) implements Packet { + public MsgConfigurationChange(PacketByteBuf buffer) { + this(new SyncedConfig( + buffer.readCollection(HashSet::new, PacketByteBuf::readString), + buffer.readCollection(HashSet::new, PacketByteBuf::readString) + )); + } + + @Override + public void toBuffer(PacketByteBuf buffer) { + buffer.writeCollection(config.wantItNeedItExcludeList(), PacketByteBuf::writeString); + buffer.writeCollection(config.dimensionsWithoutAtmosphere(), PacketByteBuf::writeString); + } + +} diff --git a/src/main/java/com/minelittlepony/unicopia/network/handler/ClientNetworkHandlerImpl.java b/src/main/java/com/minelittlepony/unicopia/network/handler/ClientNetworkHandlerImpl.java index e4c97d2e..e17dc1ff 100644 --- a/src/main/java/com/minelittlepony/unicopia/network/handler/ClientNetworkHandlerImpl.java +++ b/src/main/java/com/minelittlepony/unicopia/network/handler/ClientNetworkHandlerImpl.java @@ -2,6 +2,7 @@ package com.minelittlepony.unicopia.network.handler; import java.util.Map; +import com.minelittlepony.unicopia.InteractionManager; import com.minelittlepony.unicopia.USounds; import com.minelittlepony.unicopia.ability.data.Rot; import com.minelittlepony.unicopia.ability.data.tree.TreeTypes; @@ -35,6 +36,7 @@ public class ClientNetworkHandlerImpl { Channel.SERVER_ZAP_STAGE.receiver().addPersistentListener(this::handleZapStage); Channel.SERVER_PLAYER_ANIMATION_CHANGE.receiver().addPersistentListener(this::handlePlayerAnimation); Channel.SERVER_REQUEST_PLAYER_LOOK.receiver().addPersistentListener(this::handleCasterLookRequest); + Channel.CONFIGURATION_CHANGE.receiver().addPersistentListener(this::handleConfigurationChange); } private void handleTribeScreen(PlayerEntity sender, MsgTribeSelect packet) { @@ -93,4 +95,8 @@ public class ClientNetworkHandlerImpl { Channel.CLIENT_CASTER_LOOK.sendToServer(new Reply(packet.spellId(), Rot.of(player))); } + + private void handleConfigurationChange(PlayerEntity sender, MsgConfigurationChange packet) { + InteractionManager.getInstance().setSyncedConfig(packet.config()); + } }