From 75d94b0570751e6ef319016cd5797ccf3737a12f Mon Sep 17 00:00:00 2001 From: gnembon <41132274+gnembon@users.noreply.github.com> Date: Mon, 6 Feb 2023 02:57:38 +0100 Subject: [PATCH] cleanup of scarpet dependencies --- src/main/java/carpet/CarpetServer.java | 17 +- src/main/java/carpet/CarpetSettings.java | 4 +- .../carpet/api/settings/SettingsManager.java | 31 +- .../java/carpet/commands/MobAICommand.java | 2 +- .../java/carpet/commands/PlayerCommand.java | 7 +- ...va => AbstractContainerMenuInterface.java} | 5 +- .../carpet/fakes/ChunkGeneratorInterface.java | 13 - .../fakes/MinecraftServerInterface.java | 4 + ...erface.java => ServerPlayerInterface.java} | 2 +- .../helpers/EntityPlayerActionPack.java | 12 +- .../java/carpet/helpers/ParticleDisplay.java | 33 +- ...tContainerMenuSubclasses_scarpetMixin.java | 4 +- .../AbstractContainerMenu_scarpetMixin.java | 7 +- .../mixins/ChunkGenerator_scarpetMixin.java | 26 - src/main/java/carpet/mixins/EntityMixin.java | 1 + .../mixins/Ingredient_scarpetMixin.java | 4 +- .../mixins/MinecraftServer_scarpetMixin.java | 26 +- .../mixins/PlayerList_scarpetEventsMixin.java | 4 +- .../mixins/RecipeBookMenu_scarpetMixin.java | 4 +- .../mixins/ServerLevel_scarpetMixin.java | 1 + .../mixins/ServerPlayer_actionPackMixin.java | 5 +- .../ServerPlayer_scarpetEventMixin.java | 4 +- .../carpet/patches/EntityPlayerMPFake.java | 4 +- .../java/carpet/script/CarpetEventServer.java | 245 +++++----- .../java/carpet/script/CarpetExpression.java | 14 +- .../java/carpet/script/CarpetScriptHost.java | 71 ++- .../carpet/script/CarpetScriptServer.java | 74 ++- src/main/java/carpet/script/Context.java | 5 + .../java/carpet/script/EntityEventsGroup.java | 13 +- src/main/java/carpet/script/Expression.java | 51 +- src/main/java/carpet/script/Fluff.java | 3 +- src/main/java/carpet/script/Module.java | 15 +- .../{commands => script}/ScriptCommand.java | 457 ++++++++++-------- src/main/java/carpet/script/ScriptHost.java | 6 + src/main/java/carpet/script/ScriptServer.java | 5 +- .../java/carpet/script/api/Auxiliary.java | 57 ++- .../java/carpet/script/api/Inventories.java | 7 +- .../java/carpet/script/api/Monitoring.java | 6 +- .../java/carpet/script/api/Scoreboards.java | 15 +- .../java/carpet/script/api/WorldAccess.java | 70 ++- .../carpet/script/argument/FileArgument.java | 22 +- .../script/command/CommandArgument.java | 16 +- .../exception/CarpetExpressionException.java | 4 +- .../script/exception/ExpressionException.java | 4 +- .../exception/StacklessRuntimeException.java | 2 +- .../java/carpet/script/external/Carpet.java | 181 +++++++ .../java/carpet/script/external/Vanilla.java | 364 ++++++++++++++ .../carpet/script/external/VanillaClient.java | 13 + .../carpet/script/external/package-info.java | 8 + .../carpet/script/utils/AppStoreManager.java | 53 +- .../java/carpet/script/utils/BiomeInfo.java | 4 +- .../java/carpet/script/utils/EntityTools.java | 34 ++ .../carpet/script/utils/Experimental.java | 4 +- .../utils}/FeatureGenerator.java | 214 ++++---- .../carpet/script/utils/ParticleParser.java | 42 ++ .../carpet/script/utils/ShapeDispatcher.java | 24 +- .../carpet/script/utils/ShapesRenderer.java | 24 +- .../script/utils/SnoopyCommandSource.java | 6 +- .../java/carpet/script/utils/SystemInfo.java | 46 +- .../{helpers => script/utils}/Tracer.java | 42 +- .../java/carpet/script/utils/WorldTools.java | 15 +- .../script/value/AbstractListValue.java | 1 - .../java/carpet/script/value/BlockValue.java | 7 +- .../java/carpet/script/value/EntityValue.java | 70 ++- .../carpet/script/value/FunctionValue.java | 5 +- .../script/value/NBTSerializableValue.java | 7 +- .../java/carpet/script/value/ScreenValue.java | 43 +- src/main/java/carpet/script/value/Value.java | 4 +- .../carpet/script/value/ValueConversions.java | 16 +- src/main/java/carpet/utils/MobAI.java | 27 +- src/main/resources/carpet.mixins.json | 1 - 71 files changed, 1623 insertions(+), 1014 deletions(-) rename src/main/java/carpet/fakes/{ScreenHandlerInterface.java => AbstractContainerMenuInterface.java} (81%) delete mode 100644 src/main/java/carpet/fakes/ChunkGeneratorInterface.java rename src/main/java/carpet/fakes/{ServerPlayerEntityInterface.java => ServerPlayerInterface.java} (83%) delete mode 100644 src/main/java/carpet/mixins/ChunkGenerator_scarpetMixin.java rename src/main/java/carpet/{commands => script}/ScriptCommand.java (56%) create mode 100644 src/main/java/carpet/script/external/Carpet.java create mode 100644 src/main/java/carpet/script/external/Vanilla.java create mode 100644 src/main/java/carpet/script/external/VanillaClient.java create mode 100644 src/main/java/carpet/script/external/package-info.java create mode 100644 src/main/java/carpet/script/utils/EntityTools.java rename src/main/java/carpet/{helpers => script/utils}/FeatureGenerator.java (67%) create mode 100644 src/main/java/carpet/script/utils/ParticleParser.java rename src/main/java/carpet/{helpers => script/utils}/Tracer.java (55%) diff --git a/src/main/java/carpet/CarpetServer.java b/src/main/java/carpet/CarpetServer.java index ea0f34c3..2b9aa05e 100644 --- a/src/main/java/carpet/CarpetServer.java +++ b/src/main/java/carpet/CarpetServer.java @@ -14,19 +14,19 @@ import carpet.commands.MobAICommand; import carpet.commands.PerimeterInfoCommand; import carpet.commands.PlayerCommand; import carpet.commands.ProfileCommand; -import carpet.commands.ScriptCommand; +import carpet.script.ScriptCommand; import carpet.commands.SpawnCommand; import carpet.commands.TestCommand; import carpet.commands.TickCommand; import carpet.network.ServerNetworkHandler; import carpet.helpers.HopperCounter; -import carpet.helpers.ParticleDisplay; import carpet.helpers.TickSpeed; import carpet.logging.LoggerRegistry; import carpet.script.CarpetScriptServer; import carpet.api.settings.SettingsManager; import carpet.logging.HUDController; -import carpet.utils.FabricAPIHooks; +import carpet.script.external.Carpet; +import carpet.script.utils.ParticleParser; import carpet.utils.MobAI; import carpet.utils.SpawnReporter; import com.mojang.brigadier.CommandDispatcher; @@ -90,6 +90,7 @@ public class CarpetServer // static for now - easier to handle all around the co e.onServerLoaded(server); }); scriptServer = new CarpetScriptServer(server); + Carpet.MinecraftServer_addScriptServer(server, scriptServer); MobAI.resetTrackers(); LoggerRegistry.initLoggers(); //TickSpeed.reset(); @@ -99,6 +100,14 @@ public class CarpetServer // static for now - easier to handle all around the co { HopperCounter.resetAll(minecraftServer, true); extensions.forEach(e -> e.onServerLoadedWorlds(minecraftServer)); + // initialize scarpet rules after all extensions are loaded + settingsManager.initializeScarpetRules(); + extensions.forEach(e -> { + if (e.extensionSettingsManager() != null) + { + e.extensionSettingsManager().initializeScarpetRules(); + } + }); scriptServer.initializeForWorld(); } @@ -185,7 +194,7 @@ public class CarpetServer // static for now - easier to handle all around the co LoggerRegistry.stopLoggers(); HUDController.resetScarpetHUDs(); - ParticleDisplay.resetCache(); + ParticleParser.resetCache(); extensions.forEach(e -> e.onServerClosed(server)); minecraft_server = null; } diff --git a/src/main/java/carpet/CarpetSettings.java b/src/main/java/carpet/CarpetSettings.java index 92dc919f..97b144a0 100644 --- a/src/main/java/carpet/CarpetSettings.java +++ b/src/main/java/carpet/CarpetSettings.java @@ -4,7 +4,7 @@ import carpet.api.settings.CarpetRule; import carpet.api.settings.RuleCategory; import carpet.api.settings.Validators; import carpet.api.settings.Validator; -import carpet.script.utils.AppStoreManager; +import carpet.script.external.Carpet; import carpet.settings.Rule; import carpet.utils.Translations; import carpet.utils.CommandHelper; @@ -562,7 +562,7 @@ public class CarpetSettings }, category = SCARPET, strict = false, - validate= AppStoreManager.ScarpetAppStoreValidator.class + validate= Carpet.ScarpetAppStoreValidator.class ) public static String scriptsAppStore = "gnembon/scarpet/contents/programs"; diff --git a/src/main/java/carpet/api/settings/SettingsManager.java b/src/main/java/carpet/api/settings/SettingsManager.java index 18703606..8dec18d6 100644 --- a/src/main/java/carpet/api/settings/SettingsManager.java +++ b/src/main/java/carpet/api/settings/SettingsManager.java @@ -25,6 +25,8 @@ import java.util.function.Predicate; import java.util.stream.Collectors; import java.util.stream.Stream; +import carpet.script.CarpetEventServer; +import carpet.script.value.StringValue; import com.google.common.collect.Sets; import com.mojang.brigadier.CommandDispatcher; import com.mojang.brigadier.arguments.StringArgumentType; @@ -54,7 +56,6 @@ import net.minecraft.network.chat.Component; import net.minecraft.server.MinecraftServer; import net.minecraft.world.level.storage.LevelResource; -import static carpet.script.CarpetEventServer.Event.CARPET_RULE_CHANGES; import static carpet.utils.Translations.tr; import static java.util.Comparator.comparing; import static net.minecraft.commands.Commands.argument; @@ -258,13 +259,39 @@ public class SettingsManager { rules.put(rule.name(), rule); } + public static final CarpetEventServer.Event CARPET_RULE_CHANGES = new CarpetEventServer.Event("carpet_rule_changes", 2, true) + { + @Override + public void handleAny(final Object ... args) + { + final CarpetRule rule = (CarpetRule) args[0]; + final CommandSourceStack source = (CommandSourceStack) args[1]; + final String id = rule.settingsManager().identifier(); + final String namespace; + if (!id.equals("carpet")) + { + namespace = id + ":"; + } + else + { + namespace = ""; + } + handler.call( + () -> Arrays.asList( + new StringValue(namespace + rule.name()), + new StringValue(RuleHelper.toRuleString(rule.value())) + ), () -> source + ); + } + }; + public void notifyRuleChanged(CommandSourceStack source, CarpetRule rule, String userInput) { observers.forEach(observer -> observer.ruleChanged(source, rule, userInput)); staticObservers.forEach(observer -> observer.ruleChanged(source, rule, userInput)); ServerNetworkHandler.updateRuleWithConnectedClients(rule); switchScarpetRuleIfNeeded(source, rule); //TODO move into rule - if (CARPET_RULE_CHANGES.isNeeded()) CARPET_RULE_CHANGES.onCarpetRuleChanges(rule, source); + if (CARPET_RULE_CHANGES.isNeeded()) CARPET_RULE_CHANGES.handleAny(rule, source); } /** diff --git a/src/main/java/carpet/commands/MobAICommand.java b/src/main/java/carpet/commands/MobAICommand.java index f905ebda..53455830 100644 --- a/src/main/java/carpet/commands/MobAICommand.java +++ b/src/main/java/carpet/commands/MobAICommand.java @@ -27,7 +27,7 @@ public class MobAICommand suggests( (c, b) -> suggest(MobAI.availbleTypes(c.getSource()), b)). then(literal("clear").executes( (c) -> { - MobAI.clearTracking(getSummonableEntityType(c, "entity type").value()); + MobAI.clearTracking(c.getSource().getServer(), getSummonableEntityType(c, "entity type").value()); return 1; } )). diff --git a/src/main/java/carpet/commands/PlayerCommand.java b/src/main/java/carpet/commands/PlayerCommand.java index c93eafed..da2c8dd7 100644 --- a/src/main/java/carpet/commands/PlayerCommand.java +++ b/src/main/java/carpet/commands/PlayerCommand.java @@ -2,7 +2,7 @@ package carpet.commands; import carpet.helpers.EntityPlayerActionPack; import carpet.CarpetSettings; -import carpet.fakes.ServerPlayerEntityInterface; +import carpet.fakes.ServerPlayerInterface; import carpet.patches.EntityPlayerMPFake; import carpet.utils.CommandHelper; import carpet.utils.Messenger; @@ -14,7 +14,6 @@ import com.mojang.brigadier.arguments.StringArgumentType; import com.mojang.brigadier.builder.LiteralArgumentBuilder; import com.mojang.brigadier.context.CommandContext; import com.mojang.brigadier.exceptions.CommandSyntaxException; -import com.mojang.util.UUIDTypeAdapter; import net.minecraft.commands.CommandBuildContext; import net.minecraft.commands.CommandSourceStack; import net.minecraft.commands.arguments.DimensionArgument; @@ -336,7 +335,7 @@ public class PlayerCommand { if (cantManipulate(context)) return 0; ServerPlayer player = getPlayer(context); - ((ServerPlayerEntityInterface) player).getActionPack().stopAll(); + ((ServerPlayerInterface) player).getActionPack().stopAll(); return 1; } @@ -344,7 +343,7 @@ public class PlayerCommand { if (cantManipulate(context)) return 0; ServerPlayer player = getPlayer(context); - action.accept(((ServerPlayerEntityInterface) player).getActionPack()); + action.accept(((ServerPlayerInterface) player).getActionPack()); return 1; } diff --git a/src/main/java/carpet/fakes/ScreenHandlerInterface.java b/src/main/java/carpet/fakes/AbstractContainerMenuInterface.java similarity index 81% rename from src/main/java/carpet/fakes/ScreenHandlerInterface.java rename to src/main/java/carpet/fakes/AbstractContainerMenuInterface.java index fbd0e11d..501784d4 100644 --- a/src/main/java/carpet/fakes/ScreenHandlerInterface.java +++ b/src/main/java/carpet/fakes/AbstractContainerMenuInterface.java @@ -5,8 +5,9 @@ import net.minecraft.world.entity.player.Player; import net.minecraft.world.inventory.DataSlot; import net.minecraft.world.item.crafting.Recipe; -public interface ScreenHandlerInterface { - DataSlot getProperty(int index); +public interface AbstractContainerMenuInterface +{ + DataSlot getDataSlot(int index); boolean callButtonClickListener(int button, Player player); boolean callSelectRecipeListener(ServerPlayer player, Recipe recipe, boolean craftAll); } diff --git a/src/main/java/carpet/fakes/ChunkGeneratorInterface.java b/src/main/java/carpet/fakes/ChunkGeneratorInterface.java deleted file mode 100644 index de3d2ffd..00000000 --- a/src/main/java/carpet/fakes/ChunkGeneratorInterface.java +++ /dev/null @@ -1,13 +0,0 @@ -package carpet.fakes; - -import net.minecraft.server.level.ServerLevel; -import net.minecraft.world.level.levelgen.structure.Structure; -import net.minecraft.world.level.levelgen.structure.placement.StructurePlacement; - -import java.util.List; - -public interface ChunkGeneratorInterface -{ - void initStrongholds(final ServerLevel level); - List getPlacementsForFeatureCM(final ServerLevel level, final Structure structure); -} diff --git a/src/main/java/carpet/fakes/MinecraftServerInterface.java b/src/main/java/carpet/fakes/MinecraftServerInterface.java index f68a18c9..8b045436 100644 --- a/src/main/java/carpet/fakes/MinecraftServerInterface.java +++ b/src/main/java/carpet/fakes/MinecraftServerInterface.java @@ -3,6 +3,7 @@ package carpet.fakes; import java.util.Map; import java.util.function.BooleanSupplier; +import carpet.script.CarpetScriptServer; import net.minecraft.core.RegistryAccess; import net.minecraft.resources.ResourceKey; //import net.minecraft.server.ServerResources; @@ -19,4 +20,7 @@ public interface MinecraftServerInterface void reloadAfterReload(RegistryAccess newRegs); MinecraftServer.ReloadableResources getResourceManager(); + + void addScriptServer(CarpetScriptServer scriptServer); + CarpetScriptServer getScriptServer(); } diff --git a/src/main/java/carpet/fakes/ServerPlayerEntityInterface.java b/src/main/java/carpet/fakes/ServerPlayerInterface.java similarity index 83% rename from src/main/java/carpet/fakes/ServerPlayerEntityInterface.java rename to src/main/java/carpet/fakes/ServerPlayerInterface.java index 173081b1..06fea590 100644 --- a/src/main/java/carpet/fakes/ServerPlayerEntityInterface.java +++ b/src/main/java/carpet/fakes/ServerPlayerInterface.java @@ -2,7 +2,7 @@ package carpet.fakes; import carpet.helpers.EntityPlayerActionPack; -public interface ServerPlayerEntityInterface +public interface ServerPlayerInterface { EntityPlayerActionPack getActionPack(); void invalidateEntityObjectReference(); diff --git a/src/main/java/carpet/helpers/EntityPlayerActionPack.java b/src/main/java/carpet/helpers/EntityPlayerActionPack.java index 788b58af..4e71cf12 100644 --- a/src/main/java/carpet/helpers/EntityPlayerActionPack.java +++ b/src/main/java/carpet/helpers/EntityPlayerActionPack.java @@ -1,10 +1,12 @@ package carpet.helpers; -import carpet.fakes.ServerPlayerEntityInterface; +import carpet.fakes.ServerPlayerInterface; import java.util.HashMap; import java.util.List; import java.util.Map; import java.util.TreeMap; + +import carpet.script.utils.Tracer; import net.minecraft.commands.arguments.EntityAnchorArgument; import net.minecraft.core.BlockPos; import net.minecraft.core.Direction; @@ -289,7 +291,7 @@ public class EntityPlayerActionPack @Override boolean execute(ServerPlayer player, Action action) { - EntityPlayerActionPack ap = ((ServerPlayerEntityInterface) player).getActionPack(); + EntityPlayerActionPack ap = ((ServerPlayerInterface) player).getActionPack(); if (ap.itemUseCooldown > 0) { ap.itemUseCooldown--; @@ -358,7 +360,7 @@ public class EntityPlayerActionPack @Override void inactiveTick(ServerPlayer player, Action action) { - EntityPlayerActionPack ap = ((ServerPlayerEntityInterface) player).getActionPack(); + EntityPlayerActionPack ap = ((ServerPlayerInterface) player).getActionPack(); ap.itemUseCooldown = 0; player.releaseUsingItem(); } @@ -380,7 +382,7 @@ public class EntityPlayerActionPack return true; } case BLOCK: { - EntityPlayerActionPack ap = ((ServerPlayerEntityInterface) player).getActionPack(); + EntityPlayerActionPack ap = ((ServerPlayerInterface) player).getActionPack(); if (ap.blockHitDelay > 0) { ap.blockHitDelay--; @@ -451,7 +453,7 @@ public class EntityPlayerActionPack @Override void inactiveTick(ServerPlayer player, Action action) { - EntityPlayerActionPack ap = ((ServerPlayerEntityInterface) player).getActionPack(); + EntityPlayerActionPack ap = ((ServerPlayerInterface) player).getActionPack(); if (ap.currentBlock == null) return; player.level.destroyBlockProgress(-1, ap.currentBlock, -1); player.gameMode.handleBlockBreakAction(ap.currentBlock, ServerboundPlayerActionPacket.Action.ABORT_DESTROY_BLOCK, Direction.DOWN, player.getLevel().getMaxBuildHeight(), -1); diff --git a/src/main/java/carpet/helpers/ParticleDisplay.java b/src/main/java/carpet/helpers/ParticleDisplay.java index 086a8c23..5335f0b2 100644 --- a/src/main/java/carpet/helpers/ParticleDisplay.java +++ b/src/main/java/carpet/helpers/ParticleDisplay.java @@ -1,10 +1,6 @@ package carpet.helpers; -import com.mojang.brigadier.StringReader; -import com.mojang.brigadier.exceptions.CommandSyntaxException; -import java.util.HashMap; -import java.util.Map; -import net.minecraft.commands.arguments.ParticleArgument; +import carpet.script.utils.ParticleParser; import net.minecraft.core.HolderLookup; import net.minecraft.core.particles.ParticleOptions; import net.minecraft.core.particles.ParticleType; @@ -14,34 +10,11 @@ import net.minecraft.world.phys.Vec3; public class ParticleDisplay { - private static final Map particleCache = new HashMap<>(); // we reset this on reloads, but probably need something better - - private static ParticleOptions parseParticle(String name, HolderLookup> lookup) - { - try - { - return ParticleArgument.readParticle(new StringReader(name), lookup); - } - catch (CommandSyntaxException e) - { - throw new IllegalArgumentException("No such particle: " + name); - } - } - public static ParticleOptions getEffect(String name, HolderLookup> lookup) - { - if (name == null) return null; - return particleCache.computeIfAbsent(name, particle -> parseParticle(particle, lookup)); - } - - public static void resetCache() { - particleCache.clear(); - } - public static void drawParticleLine(ServerPlayer player, Vec3 from, Vec3 to, String main, String accent, int count, double spread) { HolderLookup> lookup = player.getLevel().holderLookup(Registries.PARTICLE_TYPE); - ParticleOptions accentParticle = getEffect(accent, lookup); - ParticleOptions mainParticle = getEffect(main, lookup); + ParticleOptions accentParticle = ParticleParser.getEffect(accent, lookup); + ParticleOptions mainParticle = ParticleParser.getEffect(main, lookup); if (accentParticle != null) player.getLevel().sendParticles( player, diff --git a/src/main/java/carpet/mixins/AbstractContainerMenuSubclasses_scarpetMixin.java b/src/main/java/carpet/mixins/AbstractContainerMenuSubclasses_scarpetMixin.java index c164a227..1b72742f 100644 --- a/src/main/java/carpet/mixins/AbstractContainerMenuSubclasses_scarpetMixin.java +++ b/src/main/java/carpet/mixins/AbstractContainerMenuSubclasses_scarpetMixin.java @@ -1,6 +1,6 @@ package carpet.mixins; -import carpet.fakes.ScreenHandlerInterface; +import carpet.fakes.AbstractContainerMenuInterface; import net.minecraft.world.entity.player.Player; import net.minecraft.world.inventory.AbstractContainerMenu; import net.minecraft.world.inventory.EnchantmentMenu; @@ -23,7 +23,7 @@ public abstract class AbstractContainerMenuSubclasses_scarpetMixin extends Abstr @Inject(method = "clickMenuButton", at = @At("HEAD"), cancellable = true) private void buttonClickCallback(Player player, int id, CallbackInfoReturnable cir) { - if(((ScreenHandlerInterface) this).callButtonClickListener(id,player)) + if(((AbstractContainerMenuInterface) this).callButtonClickListener(id,player)) cir.cancel(); } } diff --git a/src/main/java/carpet/mixins/AbstractContainerMenu_scarpetMixin.java b/src/main/java/carpet/mixins/AbstractContainerMenu_scarpetMixin.java index 3cc06d7b..3f3fe6ce 100644 --- a/src/main/java/carpet/mixins/AbstractContainerMenu_scarpetMixin.java +++ b/src/main/java/carpet/mixins/AbstractContainerMenu_scarpetMixin.java @@ -1,7 +1,6 @@ package carpet.mixins; - -import carpet.fakes.ScreenHandlerInterface; +import carpet.fakes.AbstractContainerMenuInterface; import carpet.script.value.ScreenValue; import org.spongepowered.asm.mixin.Final; import org.spongepowered.asm.mixin.Mixin; @@ -20,7 +19,7 @@ import net.minecraft.world.inventory.DataSlot; import net.minecraft.world.item.crafting.Recipe; @Mixin(AbstractContainerMenu.class) -public abstract class AbstractContainerMenu_scarpetMixin implements ScreenHandlerInterface +public abstract class AbstractContainerMenu_scarpetMixin implements AbstractContainerMenuInterface { @Shadow @Final private List containerListeners; @Shadow public abstract void sendAllDataToRemote(); @@ -73,7 +72,7 @@ public abstract class AbstractContainerMenu_scarpetMixin implements ScreenHandle } @Override - public DataSlot getProperty(int index) { + public DataSlot getDataSlot(int index) { return this.dataSlots.get(index); } } \ No newline at end of file diff --git a/src/main/java/carpet/mixins/ChunkGenerator_scarpetMixin.java b/src/main/java/carpet/mixins/ChunkGenerator_scarpetMixin.java deleted file mode 100644 index a923c800..00000000 --- a/src/main/java/carpet/mixins/ChunkGenerator_scarpetMixin.java +++ /dev/null @@ -1,26 +0,0 @@ -package carpet.mixins; - -import carpet.fakes.ChunkGeneratorInterface; -import net.minecraft.core.Holder; -import net.minecraft.server.level.ServerLevel; -import net.minecraft.world.level.chunk.ChunkGenerator; -import net.minecraft.world.level.levelgen.structure.Structure; -import net.minecraft.world.level.levelgen.structure.placement.StructurePlacement; -import org.spongepowered.asm.mixin.Mixin; - -import java.util.List; - -@Mixin(ChunkGenerator.class) -public abstract class ChunkGenerator_scarpetMixin implements ChunkGeneratorInterface -{ - @Override - public void initStrongholds(final ServerLevel level) - { - level.getChunkSource().getGeneratorState().ensureStructuresGenerated(); - } - - @Override - public List getPlacementsForFeatureCM(final ServerLevel level, Structure structure) { - return level.getChunkSource().getGeneratorState().getPlacementsForStructure(Holder.direct(structure)); - } -} diff --git a/src/main/java/carpet/mixins/EntityMixin.java b/src/main/java/carpet/mixins/EntityMixin.java index fca20d32..03cfd2c7 100644 --- a/src/main/java/carpet/mixins/EntityMixin.java +++ b/src/main/java/carpet/mixins/EntityMixin.java @@ -25,6 +25,7 @@ public abstract class EntityMixin implements EntityInterface @Shadow public Level level; + @Override public float getMainYaw(float partialTicks) { return partialTicks == 1.0F ? this.yRot : Mth.lerp(partialTicks, this.yRotO, this.yRot); diff --git a/src/main/java/carpet/mixins/Ingredient_scarpetMixin.java b/src/main/java/carpet/mixins/Ingredient_scarpetMixin.java index 79a10391..4d33697e 100644 --- a/src/main/java/carpet/mixins/Ingredient_scarpetMixin.java +++ b/src/main/java/carpet/mixins/Ingredient_scarpetMixin.java @@ -8,7 +8,6 @@ import org.spongepowered.asm.mixin.Shadow; import java.util.Arrays; import java.util.Collection; import java.util.List; -import java.util.stream.Collectors; import net.minecraft.world.item.ItemStack; import net.minecraft.world.item.crafting.Ingredient; @@ -20,7 +19,6 @@ public class Ingredient_scarpetMixin implements IngredientInterface @Override public List> getRecipeStacks() { - List> res = Arrays.stream(values).map(Ingredient.Value::getItems).collect(Collectors.toList()); - return res; + return Arrays.stream(values).map(Ingredient.Value::getItems).toList(); } } diff --git a/src/main/java/carpet/mixins/MinecraftServer_scarpetMixin.java b/src/main/java/carpet/mixins/MinecraftServer_scarpetMixin.java index 8848fa99..27591cbb 100644 --- a/src/main/java/carpet/mixins/MinecraftServer_scarpetMixin.java +++ b/src/main/java/carpet/mixins/MinecraftServer_scarpetMixin.java @@ -2,6 +2,7 @@ package carpet.mixins; import carpet.fakes.MinecraftServerInterface; import carpet.helpers.TickSpeed; +import carpet.script.CarpetScriptServer; import net.minecraft.Util; import net.minecraft.core.RegistryAccess; import net.minecraft.resources.ResourceKey; @@ -31,6 +32,8 @@ import static carpet.script.CarpetEventServer.Event.TICK; @Mixin(MinecraftServer.class) public abstract class MinecraftServer_scarpetMixin extends ReentrantBlockableEventLoop implements MinecraftServerInterface { + private CarpetScriptServer scriptServer; + public MinecraftServer_scarpetMixin(String string_1) { super(string_1); @@ -74,11 +77,6 @@ public abstract class MinecraftServer_scarpetMixin extends ReentrantBlockableEve return storageSource; } - //@Override - //public ServerResources getResourceManager() { - // return resources; - //} - @Override public Map, ServerLevel> getCMWorlds() { @@ -93,9 +91,9 @@ public abstract class MinecraftServer_scarpetMixin extends ReentrantBlockableEve { if (!TickSpeed.process_entities) return; - TICK.onTick(); - NETHER_TICK.onTick(); - ENDER_TICK.onTick(); + TICK.onTick((MinecraftServer) (Object) this); + NETHER_TICK.onTick((MinecraftServer) (Object) this); + ENDER_TICK.onTick((MinecraftServer) (Object) this); } @Override @@ -113,4 +111,16 @@ public abstract class MinecraftServer_scarpetMixin extends ReentrantBlockableEve { return resources; } + + @Override + public void addScriptServer(final CarpetScriptServer scriptServer) + { + this.scriptServer = scriptServer; + } + + @Override + public CarpetScriptServer getScriptServer() + { + return scriptServer; + } } diff --git a/src/main/java/carpet/mixins/PlayerList_scarpetEventsMixin.java b/src/main/java/carpet/mixins/PlayerList_scarpetEventsMixin.java index cacfb50c..5ca7afb4 100644 --- a/src/main/java/carpet/mixins/PlayerList_scarpetEventsMixin.java +++ b/src/main/java/carpet/mixins/PlayerList_scarpetEventsMixin.java @@ -1,7 +1,7 @@ package carpet.mixins; import carpet.CarpetServer; -import carpet.fakes.ServerPlayerEntityInterface; +import carpet.fakes.ServerPlayerInterface; import net.minecraft.server.level.ServerPlayer; import net.minecraft.server.players.PlayerList; import org.spongepowered.asm.mixin.Mixin; @@ -27,7 +27,7 @@ public class PlayerList_scarpetEventsMixin )) private void invalidatePreviousInstance(ServerPlayer player, boolean alive, CallbackInfoReturnable cir) { - ((ServerPlayerEntityInterface)player).invalidateEntityObjectReference(); + ((ServerPlayerInterface)player).invalidateEntityObjectReference(); } @Inject(method = "reloadResources", at = @At("HEAD")) diff --git a/src/main/java/carpet/mixins/RecipeBookMenu_scarpetMixin.java b/src/main/java/carpet/mixins/RecipeBookMenu_scarpetMixin.java index d9b291bb..c13ba047 100644 --- a/src/main/java/carpet/mixins/RecipeBookMenu_scarpetMixin.java +++ b/src/main/java/carpet/mixins/RecipeBookMenu_scarpetMixin.java @@ -1,6 +1,6 @@ package carpet.mixins; -import carpet.fakes.ScreenHandlerInterface; +import carpet.fakes.AbstractContainerMenuInterface; import net.minecraft.server.level.ServerPlayer; import net.minecraft.world.inventory.RecipeBookMenu; import net.minecraft.world.item.crafting.Recipe; @@ -13,7 +13,7 @@ import org.spongepowered.asm.mixin.injection.callback.CallbackInfo; public class RecipeBookMenu_scarpetMixin { @Inject(method = "handlePlacement",at = @At("HEAD"), cancellable = true) private void selectRecipeCallback(boolean craftAll, Recipe recipe, ServerPlayer player, CallbackInfo ci) { - if(((ScreenHandlerInterface) this).callSelectRecipeListener(player,recipe,craftAll)) + if(((AbstractContainerMenuInterface) this).callSelectRecipeListener(player,recipe,craftAll)) ci.cancel(); } } diff --git a/src/main/java/carpet/mixins/ServerLevel_scarpetMixin.java b/src/main/java/carpet/mixins/ServerLevel_scarpetMixin.java index 7bde2865..9ace41bb 100644 --- a/src/main/java/carpet/mixins/ServerLevel_scarpetMixin.java +++ b/src/main/java/carpet/mixins/ServerLevel_scarpetMixin.java @@ -92,6 +92,7 @@ public abstract class ServerLevel_scarpetMixin extends Level implements ServerWo private ServerLevelData serverLevelData; @Shadow @Final private PersistentEntitySectionManager entityManager; + @Override public ServerLevelData getWorldPropertiesCM(){ return serverLevelData; } diff --git a/src/main/java/carpet/mixins/ServerPlayer_actionPackMixin.java b/src/main/java/carpet/mixins/ServerPlayer_actionPackMixin.java index e49cff01..6eda0884 100644 --- a/src/main/java/carpet/mixins/ServerPlayer_actionPackMixin.java +++ b/src/main/java/carpet/mixins/ServerPlayer_actionPackMixin.java @@ -1,9 +1,8 @@ package carpet.mixins; -import carpet.fakes.ServerPlayerEntityInterface; +import carpet.fakes.ServerPlayerInterface; import carpet.helpers.EntityPlayerActionPack; import com.mojang.authlib.GameProfile; -import net.minecraft.network.chat.RemoteChatSession; import net.minecraft.server.MinecraftServer; import net.minecraft.server.level.ServerLevel; import net.minecraft.server.level.ServerPlayer; @@ -14,7 +13,7 @@ import org.spongepowered.asm.mixin.injection.Inject; import org.spongepowered.asm.mixin.injection.callback.CallbackInfo; @Mixin(ServerPlayer.class) -public abstract class ServerPlayer_actionPackMixin implements ServerPlayerEntityInterface +public abstract class ServerPlayer_actionPackMixin implements ServerPlayerInterface { @Unique public EntityPlayerActionPack actionPack; diff --git a/src/main/java/carpet/mixins/ServerPlayer_scarpetEventMixin.java b/src/main/java/carpet/mixins/ServerPlayer_scarpetEventMixin.java index ac66c14e..a1a76b0a 100644 --- a/src/main/java/carpet/mixins/ServerPlayer_scarpetEventMixin.java +++ b/src/main/java/carpet/mixins/ServerPlayer_scarpetEventMixin.java @@ -1,7 +1,7 @@ package carpet.mixins; import carpet.fakes.EntityInterface; -import carpet.fakes.ServerPlayerEntityInterface; +import carpet.fakes.ServerPlayerInterface; import carpet.script.EntityEventsGroup; import com.mojang.authlib.GameProfile; import net.minecraft.core.BlockPos; @@ -31,7 +31,7 @@ import static carpet.script.CarpetEventServer.Event.PLAYER_FINISHED_USING_ITEM; import static carpet.script.CarpetEventServer.Event.STATISTICS; @Mixin(ServerPlayer.class) -public abstract class ServerPlayer_scarpetEventMixin extends Player implements ServerPlayerEntityInterface +public abstract class ServerPlayer_scarpetEventMixin extends Player implements ServerPlayerInterface { // to denote if the player reference is valid diff --git a/src/main/java/carpet/patches/EntityPlayerMPFake.java b/src/main/java/carpet/patches/EntityPlayerMPFake.java index 3872bd88..2401d147 100644 --- a/src/main/java/carpet/patches/EntityPlayerMPFake.java +++ b/src/main/java/carpet/patches/EntityPlayerMPFake.java @@ -23,7 +23,7 @@ import net.minecraft.world.item.ItemStack; import net.minecraft.world.level.GameType; import net.minecraft.world.level.Level; import net.minecraft.world.level.block.entity.SkullBlockEntity; -import carpet.fakes.ServerPlayerEntityInterface; +import carpet.fakes.ServerPlayerInterface; import carpet.utils.Messenger; import java.util.concurrent.atomic.AtomicReference; @@ -90,7 +90,7 @@ public class EntityPlayerMPFake extends ServerPlayer playerShadow.setHealth(player.getHealth()); playerShadow.connection.teleport(player.getX(), player.getY(), player.getZ(), player.getYRot(), player.getXRot()); playerShadow.gameMode.changeGameModeForPlayer(player.gameMode.getGameModeForPlayer()); - ((ServerPlayerEntityInterface) playerShadow).getActionPack().copyFrom(((ServerPlayerEntityInterface) player).getActionPack()); + ((ServerPlayerInterface) playerShadow).getActionPack().copyFrom(((ServerPlayerInterface) player).getActionPack()); playerShadow.maxUpStep = 0.6F; playerShadow.entityData.set(DATA_PLAYER_MODE_CUSTOMISATION, player.getEntityData().get(DATA_PLAYER_MODE_CUSTOMISATION)); diff --git a/src/main/java/carpet/script/CarpetEventServer.java b/src/main/java/carpet/script/CarpetEventServer.java index 96a19877..1867dc76 100644 --- a/src/main/java/carpet/script/CarpetEventServer.java +++ b/src/main/java/carpet/script/CarpetEventServer.java @@ -1,13 +1,10 @@ package carpet.script; -import carpet.CarpetServer; -import carpet.CarpetSettings; -import carpet.api.settings.CarpetRule; -import carpet.api.settings.RuleHelper; -import carpet.helpers.TickSpeed; import carpet.script.exception.IntegrityException; import carpet.script.exception.InternalExpressionException; import carpet.script.exception.InvalidCallbackException; +import carpet.script.external.Carpet; +import carpet.script.external.Vanilla; import carpet.script.utils.GlocalFlag; import carpet.script.value.BlockValue; import carpet.script.value.BooleanValue; @@ -19,8 +16,6 @@ import carpet.script.value.NumericValue; import carpet.script.value.StringValue; import carpet.script.value.Value; import carpet.script.value.ValueConversions; -import carpet.utils.CarpetProfiler; -import carpet.utils.Messenger; import com.mojang.brigadier.exceptions.CommandSyntaxException; import java.util.ArrayList; @@ -51,6 +46,7 @@ import net.minecraft.core.registries.BuiltInRegistries; import net.minecraft.core.registries.Registries; import net.minecraft.resources.ResourceKey; import net.minecraft.resources.ResourceLocation; +import net.minecraft.server.MinecraftServer; import net.minecraft.server.level.ServerLevel; import net.minecraft.server.level.ServerPlayer; import net.minecraft.stats.Stat; @@ -93,13 +89,15 @@ public class CarpetEventServer public final String optionalTarget; public final FunctionValue function; public final List parametrizedArgs; + public final CarpetScriptServer scriptServer; - public Callback(final String host, final String target, final FunctionValue function, final List parametrizedArgs) + public Callback(final String host, final String target, final FunctionValue function, final List parametrizedArgs, final CarpetScriptServer scriptServer) { this.host = host; this.function = function; this.optionalTarget = target; this.parametrizedArgs = parametrizedArgs == null ? NOARGS : parametrizedArgs; + this.scriptServer = scriptServer; } /** @@ -115,12 +113,12 @@ public class CarpetEventServer runtimeArgs = new ArrayList<>(runtimeArgs); runtimeArgs.addAll(this.parametrizedArgs); } - if (CarpetServer.scriptServer == null) + if (scriptServer.stopAll) { return CallbackResult.FAIL; // already stopped } - return CarpetServer.scriptServer.events.runEventCall( - sender.withPermission(CarpetSettings.runPermissionLevel), + return scriptServer.events.runEventCall( + sender.withPermission(Vanilla.MinecraftServer_getRunPermissionLevel(sender.getServer())), host, optionalTarget, function, runtimeArgs); } @@ -169,7 +167,7 @@ public class CarpetEventServer public ScheduledCall(final CarpetContext context, final FunctionValue function, final List args, final long dueTime) { // ignoring target as we will be always calling self - super(context.host.getName(), null, function, args); + super(context.host.getName(), null, function, args, (CarpetScriptServer) context.scriptServer()); this.ctx = context.duplicate(); this.dueTime = dueTime; } @@ -179,7 +177,7 @@ public class CarpetEventServer */ public void execute() { - CarpetServer.scriptServer.events.runScheduledCall(ctx.origin(), ctx.source(), host, (CarpetScriptHost) ctx.host, function, parametrizedArgs); + scriptServer.events.runScheduledCall(ctx.origin(), ctx.source(), host, (CarpetScriptHost) ctx.host, function, parametrizedArgs); } } @@ -237,64 +235,69 @@ public class CarpetEventServer */ public boolean call(final Supplier> argumentSupplier, final Supplier cmdSourceSupplier) { - if (!callList.isEmpty() && CarpetServer.scriptServer != null) + if (callList.isEmpty()) { - final Boolean isCancelled = CarpetServer.scriptServer.events.handleEvents.runIfEnabled(() -> { - final CarpetProfiler.ProfilerToken currentSection = CarpetProfiler.start_section(null, "Scarpet events", CarpetProfiler.TYPE.GENERAL); - final List argv = argumentSupplier.get(); // empty for onTickDone - final CommandSourceStack source; - try + return false; + } + final CommandSourceStack source; + try + { + source = cmdSourceSupplier.get(); + } + catch (final NullPointerException noReference) // todo figure out what happens when closing. + { + return false; + } + final CarpetScriptServer scriptServer = Vanilla.MinecraftServer_getScriptServer(source.getServer()); + if (scriptServer.stopAll) + { + return false; + } + final Boolean isCancelled = scriptServer.events.handleEvents.runIfEnabled(() -> { + final Runnable profilerToken = Carpet.startProfilerSection("Scarpet events"); + final List argv = argumentSupplier.get(); // empty for onTickDone + final String nameCheck = perPlayerDistribution ? source.getTextName() : null; + assert argv.size() == reqArgs; + boolean cancelled = false; + try + { + // we are ok with list growing in the meantime + // which might happen during inCall or inSignal + inCall = true; + for (int i = 0; i < callList.size(); i++) { - source = cmdSourceSupplier.get(); - } - catch (final NullPointerException noReference) // todo figure out what happens when closing. - { - return false; - } - final String nameCheck = perPlayerDistribution ? source.getTextName() : null; - assert argv.size() == reqArgs; - boolean cancelled = false; - try - { - // we are ok with list growing in the meantime - // which might happen during inCall or inSignal - inCall = true; - for (int i = 0; i < callList.size(); i++) + final Callback call = callList.get(i); + // supressing calls where target player hosts simply don't match + // handling global hosts with player targets is left to when the host is resolved (few calls deeper). + if (nameCheck != null && call.optionalTarget != null && !nameCheck.equals(call.optionalTarget)) { - final Callback call = callList.get(i); - // supressing calls where target player hosts simply don't match - // handling global hosts with player targets is left to when the host is resolved (few calls deeper). - if (nameCheck != null && call.optionalTarget != null && !nameCheck.equals(call.optionalTarget)) - { - continue; - } - final CallbackResult result = call.execute(source, argv); - if (result == CallbackResult.CANCEL) - { - cancelled = true; - break; - } - if (result == CallbackResult.FAIL) - { - removedCalls.add(call); - } + continue; + } + final CallbackResult result = call.execute(source, argv); + if (result == CallbackResult.CANCEL) + { + cancelled = true; + break; + } + if (result == CallbackResult.FAIL) + { + removedCalls.add(call); } } - finally - { - inCall = false; - } - for (final Callback call : removedCalls) - { - callList.remove(call); - } - removedCalls.clear(); - CarpetProfiler.end_current_section(currentSection); - return cancelled; - }); - return isCancelled != null && isCancelled; - } - return false; + } + finally + { + inCall = false; + } + for (final Callback call : removedCalls) + { + callList.remove(call); + } + removedCalls.clear(); + profilerToken.run(); + return cancelled; + }); + return isCancelled != null && isCancelled; } public int signal(final CommandSourceStack sender, final ServerPlayer optinoalReceipient, final List callArg) @@ -323,13 +326,13 @@ public class CarpetEventServer return successes; } - public boolean addFromExternal(final CommandSourceStack source, final String hostName, final String funName, final Consumer hostOnEventHandler) + public boolean addFromExternal(final CommandSourceStack source, final String hostName, final String funName, final Consumer hostOnEventHandler, final CarpetScriptServer scriptServer) { - final ScriptHost host = CarpetServer.scriptServer.getAppHostByName(hostName); + final ScriptHost host = scriptServer.getAppHostByName(hostName); if (host == null) { // impossible call to add - Messenger.m(source, "r Unknown app " + hostName); + Carpet.Messenger_message(source, "r Unknown app " + hostName); return false; } hostOnEventHandler.accept(host); @@ -337,7 +340,7 @@ public class CarpetEventServer if (udf == null || udf.getArguments().size() != reqArgs) { // call won't match arguments - Messenger.m(source, "r Callback doesn't expect required number of arguments: " + reqArgs); + Carpet.Messenger_message(source, "r Callback doesn't expect required number of arguments: " + reqArgs); return false; } String target = null; @@ -349,7 +352,7 @@ public class CarpetEventServer } catch (final CommandSyntaxException e) { - Messenger.m(source, "r Cannot add event to a player scoped app from a command without a player context"); + Carpet.Messenger_message(source, "r Cannot add event to a player scoped app from a command without a player context"); return false; } } @@ -357,7 +360,7 @@ public class CarpetEventServer //remove duplicates removeEventCall(hostName, target, udf.getString()); - callList.add(new Callback(hostName, target, udf, null)); + callList.add(new Callback(hostName, target, udf, null, scriptServer)); return true; } @@ -369,7 +372,7 @@ public class CarpetEventServer } //removing duplicates removeEventCall(host.getName(), host.user, function.getString()); - callList.add(new Callback(host.getName(), host.user, function, args)); + callList.add(new Callback(host.getName(), host.user, function, args, (CarpetScriptServer) host.scriptServer())); return true; } @@ -392,10 +395,10 @@ public class CarpetEventServer final List copyCalls = new ArrayList<>(); callList.forEach((c) -> { - if ((Objects.equals(c.host, host.getName())) + if ((Objects.equals(c.host, host.getName())) // TODO fix me && c.optionalTarget == null) { - copyCalls.add(new Callback(c.host, host.user, c.function, c.parametrizedArgs)); + copyCalls.add(new Callback(c.host, host.user, c.function, c.parametrizedArgs, host.scriptServer())); } }); callList.addAll(copyCalls); @@ -434,11 +437,10 @@ public class CarpetEventServer public static final Event START = new Event("server_starts", 0, true) { @Override - public void onTick() + public void onTick(final MinecraftServer server) { handler.call(Collections::emptyList, () -> - CarpetServer.minecraft_server.createCommandSourceStack(). - withLevel(CarpetServer.minecraft_server.getLevel(Level.OVERWORLD)) + server.createCommandSourceStack().withLevel(server.getLevel(Level.OVERWORLD)) ); } }; @@ -446,11 +448,10 @@ public class CarpetEventServer public static final Event SHUTDOWN = new Event("server_shuts_down", 0, true) { @Override - public void onTick() + public void onTick(final MinecraftServer server) { handler.call(Collections::emptyList, () -> - CarpetServer.minecraft_server.createCommandSourceStack(). - withLevel(CarpetServer.minecraft_server.getLevel(Level.OVERWORLD)) + server.createCommandSourceStack().withLevel(server.getLevel(Level.OVERWORLD)) ); } }; @@ -458,11 +459,10 @@ public class CarpetEventServer public static final Event TICK = new Event("tick", 0, true) { @Override - public void onTick() + public void onTick(final MinecraftServer server) { handler.call(Collections::emptyList, () -> - CarpetServer.minecraft_server.createCommandSourceStack(). - withLevel(CarpetServer.minecraft_server.getLevel(Level.OVERWORLD)) + server.createCommandSourceStack().withLevel(server.getLevel(Level.OVERWORLD)) ); } }; @@ -475,11 +475,11 @@ public class CarpetEventServer } @Override - public void onTick() + public void onTick(final MinecraftServer server) { handler.call(Collections::emptyList, () -> - CarpetServer.minecraft_server.createCommandSourceStack(). - withLevel(CarpetServer.minecraft_server.getLevel(Level.NETHER)) + server.createCommandSourceStack(). + withLevel(server.getLevel(Level.NETHER)) ); } }; @@ -492,11 +492,11 @@ public class CarpetEventServer } @Override - public void onTick() + public void onTick(final MinecraftServer server) { handler.call(Collections::emptyList, () -> - CarpetServer.minecraft_server.createCommandSourceStack(). - withLevel(CarpetServer.minecraft_server.getLevel(Level.END)) + server.createCommandSourceStack(). + withLevel(server.getLevel(Level.END)) ); } }; @@ -507,7 +507,7 @@ public class CarpetEventServer { handler.call( () -> Arrays.asList(new NumericValue(chPos.x << 4), new NumericValue(chPos.z << 4)), - () -> CarpetServer.minecraft_server.createCommandSourceStack().withLevel(world) + () -> world.getServer().createCommandSourceStack().withLevel(world) ); } }; @@ -518,7 +518,7 @@ public class CarpetEventServer { handler.call( () -> Arrays.asList(new NumericValue(chPos.x << 4), new NumericValue(chPos.z << 4)), - () -> CarpetServer.minecraft_server.createCommandSourceStack().withLevel(world) + () -> world.getServer().createCommandSourceStack().withLevel(world) ); } }; @@ -530,7 +530,7 @@ public class CarpetEventServer { handler.call( () -> Arrays.asList(new NumericValue(chPos.x << 4), new NumericValue(chPos.z << 4)), - () -> CarpetServer.minecraft_server.createCommandSourceStack().withLevel(world) + () -> world.getServer().createCommandSourceStack().withLevel(world) ); } }; @@ -714,7 +714,7 @@ public class CarpetEventServer final RegistryAccess regs = player.getLevel().registryAccess(); handler.call(() -> Arrays.asList( new EntityValue(player), - merchant instanceof final AbstractVillager villager? new EntityValue(villager) : Value.NULL, + merchant instanceof final AbstractVillager villager ? new EntityValue(villager) : Value.NULL, ValueConversions.of(tradeOffer.getBaseCostA(), regs), ValueConversions.of(tradeOffer.getCostB(), regs), ValueConversions.of(tradeOffer.getResult(), regs) @@ -1015,30 +1015,7 @@ public class CarpetEventServer () -> Arrays.asList( new BlockValue(null, world, pos), flag > 0 ? Value.TRUE : Value.FALSE - ), () -> CarpetServer.minecraft_server.createCommandSourceStack().withLevel(world) - ); - } - }; - public static final Event CARPET_RULE_CHANGES = new Event("carpet_rule_changes", 2, true) - { - @Override - public void onCarpetRuleChanges(final CarpetRule rule, final CommandSourceStack source) - { - final String identifier = rule.settingsManager().identifier(); - final String namespace; - if (!identifier.equals("carpet")) - { - namespace = identifier + ":"; - } - else - { - namespace = ""; - } - handler.call( - () -> Arrays.asList( - new StringValue(namespace + rule.name()), - new StringValue(RuleHelper.toRuleString(rule.value())) - ), () -> source + ), () -> world.getServer().createCommandSourceStack().withLevel(world) ); } }; @@ -1086,7 +1063,7 @@ public class CarpetEventServer b -> new BlockValue(world.getBlockState(b), world, b) )), ListValue.wrap(affectedEntities.stream().map(EntityValue::of)) - ), () -> CarpetServer.minecraft_server.createCommandSourceStack().withLevel(world) + ), () -> world.getServer().createCommandSourceStack().withLevel(world) ); } }; @@ -1105,7 +1082,7 @@ public class CarpetEventServer EntityValue.of(attacker != null ? attacker.get() : Event.getExplosionCausingEntity(e)), StringValue.of(type.name().toLowerCase(Locale.ROOT)), BooleanValue.of(createFire) - ), () -> CarpetServer.minecraft_server.createCommandSourceStack().withLevel(world) + ), () -> world.getServer().createCommandSourceStack().withLevel(world) ); } }; @@ -1126,7 +1103,7 @@ public class CarpetEventServer { handler.call( () -> Collections.singletonList(new EntityValue(entity)), - () -> CarpetServer.minecraft_server.createCommandSourceStack().withLevel((ServerLevel) entity.level).withPermission(CarpetSettings.runPermissionLevel) + () -> entity.getServer().createCommandSourceStack().withLevel((ServerLevel) entity.level).withPermission(Vanilla.MinecraftServer_getRunPermissionLevel(entity.getServer())) ); } })).collect(Collectors.toUnmodifiableMap(Map.Entry::getKey, Map.Entry::getValue)); @@ -1145,7 +1122,7 @@ public class CarpetEventServer { handler.call( () -> Arrays.asList(new EntityValue(entity), BooleanValue.of(created)), - () -> CarpetServer.minecraft_server.createCommandSourceStack().withLevel((ServerLevel) entity.level).withPermission(CarpetSettings.runPermissionLevel) + () -> entity.getServer().createCommandSourceStack().withLevel((ServerLevel) entity.level).withPermission(Vanilla.MinecraftServer_getRunPermissionLevel(entity.getServer())) ); } })) @@ -1241,7 +1218,7 @@ public class CarpetEventServer } //stubs for calls just to ease calls in vanilla code so they don't need to deal with scarpet value types - public void onTick() + public void onTick(final MinecraftServer server) { } @@ -1339,7 +1316,7 @@ public class CarpetEventServer { } - public void onCarpetRuleChanges(final CarpetRule rule, final CommandSourceStack source) + public void handleAny(final Object... args) { } @@ -1376,7 +1353,7 @@ public class CarpetEventServer valArgs.add(ValueConversions.guess(world, o)); } return valArgs; - }, () -> CarpetServer.minecraft_server.createCommandSourceStack().withLevel(world) + }, () -> world.getServer().createCommandSourceStack().withLevel(world) ); } } @@ -1390,7 +1367,7 @@ public class CarpetEventServer public void tick() { - if (!TickSpeed.process_entities) + if (Carpet.isTickProcessingPaused()) { return; } @@ -1455,7 +1432,7 @@ public class CarpetEventServer return CallbackResult.FAIL; } } - final CommandSourceStack source = sender.withPermission(CarpetSettings.runPermissionLevel); + final CommandSourceStack source = sender.withPermission(Vanilla.MinecraftServer_getRunPermissionLevel(sender.getServer())); final CarpetScriptHost executingHost = appHost.retrieveForExecution(sender, target); if (executingHost == null) { @@ -1463,7 +1440,7 @@ public class CarpetEventServer } try { - final Value returnValue = executingHost.callUDF(source.withPermission(CarpetSettings.runPermissionLevel), udf, argv); + final Value returnValue = executingHost.callUDF(source, udf, argv); return returnValue instanceof StringValue && returnValue.getString().equals("cancel") ? CallbackResult.CANCEL : CallbackResult.SUCCESS; } catch (final NullPointerException | InvalidCallbackException | IntegrityException error) @@ -1475,15 +1452,15 @@ public class CarpetEventServer public boolean addEventFromCommand(final CommandSourceStack source, final String event, final String host, final String funName) { - final Event ev = Event.getEvent(event, CarpetServer.scriptServer); + final Event ev = Event.getEvent(event, scriptServer); if (ev == null) { return false; } - final boolean added = ev.handler.addFromExternal(source, host, funName, h -> onEventAddedToHost(ev, h)); + final boolean added = ev.handler.addFromExternal(source, host, funName, h -> onEventAddedToHost(ev, h), scriptServer); if (added) { - Messenger.m(source, "gi Added " + funName + " to " + event); + Carpet.Messenger_message(source, "gi Added " + funName + " to " + event); } return added; } @@ -1524,16 +1501,16 @@ public class CarpetEventServer public boolean removeEventFromCommand(final CommandSourceStack source, final String event, final String funName) { - final Event ev = Event.getEvent(event, CarpetServer.scriptServer); + final Event ev = Event.getEvent(event, scriptServer); if (ev == null) { - Messenger.m(source, "r Unknown event: " + event); + Carpet.Messenger_message(source, "r Unknown event: " + event); return false; } final Callback.Signature call = Callback.fromString(funName); ev.handler.removeEventCall(call.host, call.target, call.function); // could verified if actually removed - Messenger.m(source, "gi Removed event: " + funName + " from " + event); + Carpet.Messenger_message(source, "gi Removed event: " + funName + " from " + event); return true; } diff --git a/src/main/java/carpet/script/CarpetExpression.java b/src/main/java/carpet/script/CarpetExpression.java index ef78a103..e3597688 100644 --- a/src/main/java/carpet/script/CarpetExpression.java +++ b/src/main/java/carpet/script/CarpetExpression.java @@ -1,6 +1,5 @@ package carpet.script; -import carpet.CarpetServer; import carpet.script.annotation.AnnotationParser; import carpet.script.api.Auxiliary; import carpet.script.api.BlockIterators; @@ -12,6 +11,7 @@ import carpet.script.api.Threading; import carpet.script.api.WorldAccess; import carpet.script.exception.CarpetExpressionException; import carpet.script.exception.ExpressionException; +import carpet.script.external.Carpet; import carpet.script.value.BlockValue; import carpet.script.value.EntityValue; import carpet.script.value.NumericValue; @@ -58,12 +58,13 @@ public class CarpetExpression Scoreboards.apply(this.expr); Monitoring.apply(this.expr); AnnotationParser.apply(this.expr); - CarpetServer.extensions.forEach(e -> e.scarpetApi(this)); + Carpet.handleExtensionsAPI(this); } public boolean fillAndScanCommand(final ScriptHost host, final int x, final int y, final int z) { - if (CarpetServer.scriptServer.stopAll) + CarpetScriptServer scriptServer = (CarpetScriptServer) host.scriptServer(); + if (scriptServer.stopAll) { return false; } @@ -85,7 +86,7 @@ public class CarpetExpression final Value playerValue = new EntityValue(e).bindTo("p"); context.with("p", (cc, tt) -> playerValue); } - return CarpetServer.scriptServer.events.handleEvents.getWhileDisabled(() -> this.expr.eval(context).getBoolean()); + return scriptServer.events.handleEvents.getWhileDisabled(() -> this.expr.eval(context).getBoolean()); } catch (final ExpressionException e) { @@ -103,7 +104,8 @@ public class CarpetExpression public Value scriptRunCommand(final ScriptHost host, final BlockPos pos) { - if (CarpetServer.scriptServer.stopAll) + CarpetScriptServer scriptServer = (CarpetScriptServer) host.scriptServer(); + if (scriptServer.stopAll) { throw new CarpetExpressionException("SCRIPTING PAUSED (unpause with /script resume)", null); } @@ -124,7 +126,7 @@ public class CarpetExpression final Value playerValue = new EntityValue(e).bindTo("p"); context.with("p", (cc, tt) -> playerValue); } - return CarpetServer.scriptServer.events.handleEvents.getWhileDisabled(() -> this.expr.eval(context)); + return scriptServer.events.handleEvents.getWhileDisabled(() -> this.expr.eval(context)); } catch (final ExpressionException e) { diff --git a/src/main/java/carpet/script/CarpetScriptHost.java b/src/main/java/carpet/script/CarpetScriptHost.java index 64a46da0..4edf62db 100644 --- a/src/main/java/carpet/script/CarpetScriptHost.java +++ b/src/main/java/carpet/script/CarpetScriptHost.java @@ -1,7 +1,5 @@ package carpet.script; -import carpet.CarpetServer; -import carpet.CarpetSettings; import carpet.script.api.Auxiliary; import carpet.script.argument.FileArgument; import carpet.script.argument.FunctionArgument; @@ -13,6 +11,8 @@ import carpet.script.exception.IntegrityException; import carpet.script.exception.InternalExpressionException; import carpet.script.exception.InvalidCallbackException; import carpet.script.exception.LoadException; +import carpet.script.external.Carpet; +import carpet.script.external.Vanilla; import carpet.script.utils.AppStoreManager; import carpet.script.value.EntityValue; import carpet.script.value.FunctionValue; @@ -21,8 +21,6 @@ import carpet.script.value.MapValue; import carpet.script.value.NumericValue; import carpet.script.value.StringValue; import carpet.script.value.Value; -import carpet.utils.CarpetProfiler; -import carpet.utils.Messenger; import com.google.gson.JsonElement; import com.mojang.brigadier.arguments.StringArgumentType; @@ -144,8 +142,9 @@ public class CarpetScriptHost extends ScriptHost private static int execute(final CommandContext ctx, final String hostName, final FunctionArgument funcSpec, final List paramNames) throws CommandSyntaxException { - final CarpetProfiler.ProfilerToken currentSection = CarpetProfiler.start_section(null, "Scarpet command", CarpetProfiler.TYPE.GENERAL); - final CarpetScriptHost cHost = CarpetServer.scriptServer.modules.get(hostName).retrieveOwnForExecution(ctx.getSource()); + final Runnable token = Carpet.startProfilerSection("Scarpet command"); + final CarpetScriptServer scriptServer = Vanilla.MinecraftServer_getScriptServer(ctx.getSource().getServer()); + final CarpetScriptHost cHost = scriptServer.modules.get(hostName).retrieveOwnForExecution(ctx.getSource()); final List argNames = funcSpec.function.getArguments(); if ((argNames.size() - funcSpec.args.size()) != paramNames.size()) { @@ -159,7 +158,7 @@ public class CarpetScriptHost extends ScriptHost args.addAll(funcSpec.args); final Value response = cHost.handleCommand(ctx.getSource(), funcSpec.function, args); final int intres = (int) response.readInteger(); - CarpetProfiler.end_current_section(currentSection); + token.run(); return intres; } @@ -239,18 +238,18 @@ public class CarpetScriptHost extends ScriptHost return s -> { try { - final CarpetProfiler.ProfilerToken currentSection = CarpetProfiler.start_section(null, "Scarpet command", CarpetProfiler.TYPE.GENERAL); - final CarpetScriptHost cHost = CarpetServer.scriptServer.modules.get(hostName).retrieveOwnForExecution(s); + final Runnable token = Carpet.startProfilerSection("Scarpet command"); + final CarpetScriptHost cHost = scriptServer().modules.get(hostName).retrieveOwnForExecution(s); final Value response = cHost.handleCommand(s, fun, Collections.singletonList( (s.getEntity() instanceof ServerPlayer) ? new EntityValue(s.getEntity()) : Value.NULL) ); final boolean res = response.getBoolean(); - CarpetProfiler.end_current_section(currentSection); + token.run(); return res; } catch (final CommandSyntaxException e) { - Messenger.m(s, "rb Unable to run app command: " + e.getMessage()); + Carpet.Messenger_message(s, "rb Unable to run app command: " + e.getMessage()); return false; } }; @@ -434,14 +433,14 @@ public class CarpetScriptHost extends ScriptHost } catch (final CommandSyntaxException e) { - notifier.accept(Messenger.c("r Error when handling of setting up custom argument types: " + e.getMessage())); + notifier.accept(Carpet.Messenger_compose("r Error when handling of setting up custom argument types: " + e.getMessage())); return false; } if (appConfig.get(StringValue.of("commands")) != null) { if (scriptServer().isInvalidCommandRoot(getName())) { - notifier.accept(Messenger.c("g A command with the app's name already exists in vanilla or an installed mod.")); + notifier.accept(Carpet.Messenger_compose("g A command with the app's name already exists in vanilla or an installed mod.")); return null; } try @@ -457,7 +456,7 @@ public class CarpetScriptHost extends ScriptHost catch (final CommandSyntaxException cse) { // failed - notifier.accept(Messenger.c("r Failed to build command system: ", cse.getRawMessage())); + notifier.accept(Carpet.Messenger_compose("r Failed to build command system: ", cse.getRawMessage())); return null; } @@ -512,7 +511,7 @@ public class CarpetScriptHost extends ScriptHost if (scriptServer().isInvalidCommandRoot(getName())) { - notifier.accept(Messenger.c("g A command with the app's name already exists in vanilla or an installed mod.")); + notifier.accept(Carpet.Messenger_compose("g A command with the app's name already exists in vanilla or an installed mod.")); return null; } @@ -523,7 +522,7 @@ public class CarpetScriptHost extends ScriptHost } catch (final CommandSyntaxException e) { - notifier.accept(Messenger.c("rb " + e.getMessage())); + notifier.accept(Carpet.Messenger_compose("rb " + e.getMessage())); return null; } final String hostName = getName(); @@ -535,7 +534,7 @@ public class CarpetScriptHost extends ScriptHost final Value response = targetHost.handleCommandLegacy(c.getSource(), "__command", null, ""); if (!response.isNull()) { - Messenger.m(c.getSource(), "gi " + response.getString()); + Carpet.Messenger_message(c.getSource(), "gi " + response.getString()); } return (int) response.readInteger(); }); @@ -570,7 +569,7 @@ public class CarpetScriptHost extends ScriptHost final Value response = targetHost.handleCommandLegacy(c.getSource(), function, null, ""); if (!response.isNull()) { - Messenger.m(c.getSource(), "gi " + response.getString()); + Carpet.Messenger_message(c.getSource(), "gi " + response.getString()); } return (int) response.readInteger(); }). @@ -580,7 +579,7 @@ public class CarpetScriptHost extends ScriptHost final Value response = targetHost.handleCommandLegacy(c.getSource(), function, null, StringArgumentType.getString(c, "args...")); if (!response.isNull()) { - Messenger.m(c.getSource(), "gi " + response.getString()); + Carpet.Messenger_message(c.getSource(), "gi " + response.getString()); } return (int) response.readInteger(); }))); @@ -721,9 +720,9 @@ public class CarpetScriptHost extends ScriptHost { try { - final CarpetProfiler.ProfilerToken currentSection = CarpetProfiler.start_section(null, "Scarpet command", CarpetProfiler.TYPE.GENERAL); + final Runnable token = Carpet.startProfilerSection("Scarpet command"); final Value res = callLegacy(source, call, coords, arg); - CarpetProfiler.end_current_section(currentSection); + token.run(); return res; } catch (final CarpetExpressionException exc) @@ -764,7 +763,7 @@ public class CarpetScriptHost extends ScriptHost public Value callLegacy(final CommandSourceStack source, final String call, final List coords, final String arg) { - if (CarpetServer.scriptServer.stopAll) + if (scriptServer().stopAll) { throw new CarpetExpressionException("SCARPET PAUSED (unpause with /script resume)", null); } @@ -871,7 +870,7 @@ public class CarpetScriptHost extends ScriptHost public Value call(final CommandSourceStack source, final FunctionValue function, final List argv) { - if (CarpetServer.scriptServer.stopAll) + if (scriptServer().stopAll) { throw new CarpetExpressionException("SCARPET PAUSED (unpause with /script resume)", null); } @@ -909,7 +908,7 @@ public class CarpetScriptHost extends ScriptHost public Value callUDF(final BlockPos origin, final CommandSourceStack source, final FunctionValue fun, final List argv) throws InvalidCallbackException, IntegrityException { - if (CarpetServer.scriptServer.stopAll) + if (scriptServer().stopAll) { return Value.NULL; } @@ -987,12 +986,12 @@ public class CarpetScriptHost extends ScriptHost private void dumpState() { - Module.saveData(main, globalState); + Module.saveData(main, globalState, this.scriptServer()); } private Tag loadState() { - return Module.getData(main); + return Module.getData(main, this.scriptServer()); } public Tag readFileTag(final FileArgument fdesc) @@ -1061,7 +1060,7 @@ public class CarpetScriptHost extends ScriptHost public boolean applyActionForResource(final String path, final boolean shared, final Consumer action) { - final FileArgument fdesc = FileArgument.resourceFromPath(path, FileArgument.Reason.CREATE, shared); + final FileArgument fdesc = FileArgument.resourceFromPath(this, path, FileArgument.Reason.CREATE, shared); return fdesc.findPathAndApply(main, action); } @@ -1104,21 +1103,21 @@ public class CarpetScriptHost extends ScriptHost { shebang += " at pos " + (token.pos + 1); } - Messenger.m(source, "r " + shebang); + Carpet.Messenger_message(source, "r " + shebang); if (lines.length > 1 && token.lineno > 0) { - Messenger.m(source, withLocals("l", lines[token.lineno - 1], ctx)); + Carpet.Messenger_message(source, withLocals("l", lines[token.lineno - 1], ctx)); } - Messenger.m(source, withLocals("l", lines[token.lineno].substring(0, token.linepos), ctx), "r HERE>> ", + Carpet.Messenger_message(source, withLocals("l", lines[token.lineno].substring(0, token.linepos), ctx), "r HERE>> ", withLocals("l", lines[token.lineno].substring(token.linepos), ctx)); if (lines.length > 1 && token.lineno < lines.length - 1) { - Messenger.m(source, withLocals("l", lines[token.lineno + 1], ctx)); + Carpet.Messenger_message(source, withLocals("l", lines[token.lineno + 1], ctx)); } } else { - Messenger.m(source, "r " + shebang); + Carpet.Messenger_message(source, "r " + shebang); } return new ArrayList<>(); }; @@ -1182,7 +1181,7 @@ public class CarpetScriptHost extends ScriptHost { stringsToFormat.add(format + line.substring(lastPos)); } - return Messenger.c(stringsToFormat.toArray()); + return Carpet.Messenger_compose(stringsToFormat.toArray()); } @Override @@ -1201,11 +1200,11 @@ public class CarpetScriptHost extends ScriptHost cee.printStack(responsibleSource); } final String message = exception.getMessage(); - Messenger.m(responsibleSource, "r " + intro + ((message == null || message.isEmpty()) ? "" : ": " + message)); + Carpet.Messenger_message(responsibleSource, "r " + intro + ((message == null || message.isEmpty()) ? "" : ": " + message)); } else { - CarpetSettings.LOG.error(intro + ": " + exception.getMessage()); + CarpetScriptServer.LOG.error(intro + ": " + exception.getMessage()); } } @@ -1235,7 +1234,7 @@ public class CarpetScriptHost extends ScriptHost { if (super.issueDeprecation(feature)) { - Messenger.m(responsibleSource, "rb '" + feature + "' is deprecated and soon will be removed. Please consult the docs for their replacement"); + Carpet.Messenger_message(responsibleSource, "rb '" + feature + "' is deprecated and soon will be removed. Please consult the docs for their replacement"); return true; } return false; diff --git a/src/main/java/carpet/script/CarpetScriptServer.java b/src/main/java/carpet/script/CarpetScriptServer.java index 9ae29a2c..ba17d0f2 100644 --- a/src/main/java/carpet/script/CarpetScriptServer.java +++ b/src/main/java/carpet/script/CarpetScriptServer.java @@ -1,7 +1,5 @@ package carpet.script; -import carpet.CarpetSettings; -import carpet.fakes.CommandDispatcherInterface; import carpet.script.annotation.AnnotationParser; import carpet.script.api.Auxiliary; import carpet.script.api.BlockIterators; @@ -9,9 +7,10 @@ import carpet.script.api.Entities; import carpet.script.api.Inventories; import carpet.script.api.Scoreboards; import carpet.script.api.WorldAccess; -import carpet.CarpetServer; import carpet.script.exception.ExpressionException; import carpet.script.exception.LoadException; +import carpet.script.external.Carpet; +import carpet.script.external.Vanilla; import carpet.script.language.Arithmetic; import carpet.script.language.ControlFlow; import carpet.script.language.DataStructures; @@ -21,9 +20,6 @@ import carpet.script.language.Sys; import carpet.script.language.Threading; import carpet.script.utils.AppStoreManager; import carpet.script.value.FunctionValue; -import carpet.utils.CarpetProfiler; -import carpet.utils.CommandHelper; -import carpet.utils.Messenger; import com.mojang.brigadier.exceptions.CommandSyntaxException; import com.mojang.brigadier.tree.CommandNode; @@ -127,21 +123,14 @@ public class CarpetScriptServer extends ScriptServer public void initializeForWorld() { - CarpetServer.settingsManager.initializeScarpetRules(); - CarpetServer.extensions.forEach(e -> { - if (e.extensionSettingsManager() != null) - { - e.extensionSettingsManager().initializeScarpetRules(); - } - }); - if (CarpetSettings.scriptsAutoload) + if (Vanilla.MinecraftServer_doScriptsAutoload(server)) { for (final String moduleName : listAvailableModules(false)) { addScriptHost(server.createCommandSourceStack(), moduleName, null, true, true, false, null); } } - CarpetEventServer.Event.START.onTick(); + CarpetEventServer.Event.START.onTick(server); } public Module getModule(final String name, final boolean allowLibraries) @@ -188,7 +177,7 @@ public class CarpetScriptServer extends ScriptServer } catch (final IOException e) { - CarpetSettings.LOG.error("Exception while loading the app: ", e); + LOG.error("Exception while loading the app: ", e); } for (final Module moduleData : bundledModuleData) { @@ -256,7 +245,7 @@ public class CarpetScriptServer extends ScriptServer } catch (final IOException e) { - CarpetSettings.LOG.error("Exception while searching for apps: ", e); + LOG.error("Exception while searching for apps: ", e); } return moduleNames; } @@ -269,7 +258,7 @@ public class CarpetScriptServer extends ScriptServer public boolean addScriptHost(final CommandSourceStack source, String name, Predicate commandValidator, final boolean perPlayer, final boolean autoload, final boolean isRuleApp, final AppStoreManager.StoreNode installer) { - final CarpetProfiler.ProfilerToken currentSection = CarpetProfiler.start_section(null, "Scarpet load", CarpetProfiler.TYPE.GENERAL); + final Runnable token = Carpet.startProfilerSection("Scarpet load"); if (commandValidator == null) { commandValidator = p -> true; @@ -289,7 +278,7 @@ public class CarpetScriptServer extends ScriptServer final Module module = isRuleApp ? getRuleModule(name) : getModule(name, false); if (module == null) { - Messenger.m(source, "r Failed to add " + name + " app: App not found"); + Carpet.Messenger_message(source, "r Failed to add " + name + " app: App not found"); return false; } final CarpetScriptHost newHost; @@ -299,7 +288,7 @@ public class CarpetScriptServer extends ScriptServer } catch (final LoadException e) { - Messenger.m(source, "r Failed to add " + name + " app" + (e.getMessage() == null ? "" : ": " + e.getMessage())); + Carpet.Messenger_message(source, "r Failed to add " + name + " app" + (e.getMessage() == null ? "" : ": " + e.getMessage())); return false; } @@ -320,7 +309,7 @@ public class CarpetScriptServer extends ScriptServer final Boolean isCommandAdded = newHost.addAppCommands(s -> { if (!isRuleApp) { - Messenger.m(source, Messenger.c("r Failed to add app '" + finalName + "': ", s)); + Carpet.Messenger_message(source, "r Failed to add app '" + finalName + "': ", s); } }); if (isCommandAdded == null) // error should be dispatched @@ -330,17 +319,17 @@ public class CarpetScriptServer extends ScriptServer } else if (isCommandAdded) { - CommandHelper.notifyPlayersCommandsChanged(server); + Vanilla.MinecraftServer_notifyPlayersCommandsChanged(server); if (!isRuleApp) { - Messenger.m(source, "gi " + name + " app " + action + " with /" + name + " command"); + Carpet.Messenger_message(source, "gi " + name + " app " + action + " with /" + name + " command"); } } else { if (!isRuleApp) { - Messenger.m(source, "gi " + name + " app " + action); + Carpet.Messenger_message(source, "gi " + name + " app " + action); } } @@ -361,9 +350,9 @@ public class CarpetScriptServer extends ScriptServer newHost.callNow(onStart, Collections.emptyList()); } } - CarpetProfiler.end_current_section(currentSection); + token.run(); final long end = System.nanoTime(); - CarpetSettings.LOG.info("App " + name + " loaded in " + (end - start) / 1000000 + " ms"); + LOG.info("App " + name + " loaded in " + (end - start) / 1000000 + " ms"); return true; } @@ -380,7 +369,7 @@ public class CarpetScriptServer extends ScriptServer { if (notifySource) { - Messenger.m(source, "r No such app found: ", "wb " + name); + Carpet.Messenger_message(source, "r No such app found: ", "wb " + name); } return false; } @@ -390,16 +379,16 @@ public class CarpetScriptServer extends ScriptServer host.onClose(); if (host.hasCommand) { - ((CommandDispatcherInterface) server.getCommands().getDispatcher()).carpet$unregister(name); + Vanilla.CommandDispatcher_unregisterCommand(server.getCommands().getDispatcher(), name); } if (!isRuleApp) { unloadableModules.remove(name); } - CommandHelper.notifyPlayersCommandsChanged(server); + Vanilla.MinecraftServer_notifyPlayersCommandsChanged(server); if (notifySource) { - Messenger.m(source, "gi Removed " + name + " app"); + Carpet.Messenger_message(source, "gi Removed " + name + " app"); } return true; } @@ -416,46 +405,47 @@ public class CarpetScriptServer extends ScriptServer } if (!Files.exists(folder.getParent().resolve(name + ".sc"))) { - Messenger.m(source, "App doesn't exist in the world scripts folder, so can only be unloaded"); + Carpet.Messenger_message(source, "App doesn't exist in the world scripts folder, so can only be unloaded"); return false; } removeScriptHost(source, name, false, false); Files.move(folder.getParent().resolve(name + ".sc"), folder.resolve(name + ".sc"), StandardCopyOption.REPLACE_EXISTING); - Messenger.m(source, "gi Removed " + name + " app"); + Carpet.Messenger_message(source, "gi Removed " + name + " app"); return true; } catch (final IOException exc) { - Messenger.m(source, "rb Failed to uninstall the app"); + Carpet.Messenger_message(source, "rb Failed to uninstall the app"); } return false; } public void tick() { - CarpetProfiler.ProfilerToken token; - token = CarpetProfiler.start_section(null, "Scarpet schedule", CarpetProfiler.TYPE.GENERAL); + Runnable token; + token = Carpet.startProfilerSection("Scarpet schedule"); events.handleEvents.getWhileDisabled(() -> { events.tick(); return null; }); - CarpetProfiler.end_current_section(token); - token = CarpetProfiler.start_section(null, "Scarpet app data", CarpetProfiler.TYPE.GENERAL); + token.run(); + token = Carpet.startProfilerSection("Scarpet app data"); for (final CarpetScriptHost host : modules.values()) { host.tick(); } - CarpetProfiler.end_current_section(token); + token.run(); } public void onClose() { - CarpetEventServer.Event.SHUTDOWN.onTick(); + CarpetEventServer.Event.SHUTDOWN.onTick(server); for (final CarpetScriptHost host : modules.values()) { host.onClose(); events.removeAllHostEvents(host); } + stopAll = true; } public void onPlayerJoin(final ServerPlayer player) @@ -475,6 +465,12 @@ public class CarpetScriptServer extends ScriptServer }); } + @Override + public Path resolveResource(final String suffix) + { + return server.getWorldPath(LevelResource.ROOT).resolve("scripts/" + suffix); + } + private record TransferData(boolean perUser, Predicate commandValidator, boolean isRuleApp) { diff --git a/src/main/java/carpet/script/Context.java b/src/main/java/carpet/script/Context.java index 430159ca..8450667f 100644 --- a/src/main/java/carpet/script/Context.java +++ b/src/main/java/carpet/script/Context.java @@ -91,6 +91,11 @@ public class Context return host.errorSnooper; } + public ScriptServer scriptServer() + { + return host.scriptServer(); + } + /** * immutable context only for reason on reporting access violations in evaluating expressions in optimizization * mode detecting any potential violations that may happen on the way diff --git a/src/main/java/carpet/script/EntityEventsGroup.java b/src/main/java/carpet/script/EntityEventsGroup.java index 41b1dc3e..f3b9bb42 100644 --- a/src/main/java/carpet/script/EntityEventsGroup.java +++ b/src/main/java/carpet/script/EntityEventsGroup.java @@ -1,7 +1,7 @@ package carpet.script; -import carpet.CarpetServer; import carpet.script.exception.InternalExpressionException; +import carpet.script.external.Vanilla; import carpet.script.value.EntityValue; import carpet.script.value.FunctionValue; import carpet.script.value.NumericValue; @@ -46,7 +46,8 @@ public class EntityEventsGroup { return; } - if (CarpetServer.scriptServer == null) + final CarpetScriptServer scriptServer = Vanilla.MinecraftServer_getScriptServer(entity.getServer()); + if (scriptServer.stopAll) { return; // executed after world is closin down } @@ -54,7 +55,7 @@ public class EntityEventsGroup { final Map.Entry action = iterator.next(); final EventKey key = action.getKey(); - final ScriptHost host = CarpetServer.scriptServer.getAppHostByName(key.host()); + final ScriptHost host = scriptServer.getAppHostByName(key.host()); if (host == null) { iterator.remove(); @@ -81,7 +82,7 @@ public class EntityEventsGroup final EventKey key = new EventKey(host.getName(), host.user); if (fun != null) { - final CarpetEventServer.Callback call = type.create(key, fun, extraargs); + final CarpetEventServer.Callback call = type.create(key, fun, extraargs, (CarpetScriptServer) host.scriptServer()); if (call == null) { throw new InternalExpressionException("wrong number of arguments for callback, required " + type.argcount); @@ -154,13 +155,13 @@ public class EntityEventsGroup byName.put(identifier, this); } - public CarpetEventServer.Callback create(final EventKey key, final FunctionValue function, final List extraArgs) + public CarpetEventServer.Callback create(final EventKey key, final FunctionValue function, final List extraArgs, final CarpetScriptServer scriptServer) { if ((function.getArguments().size() - (extraArgs == null ? 0 : extraArgs.size())) != argcount) { return null; } - return new CarpetEventServer.Callback(key.host(), key.user(), function, extraArgs); + return new CarpetEventServer.Callback(key.host(), key.user(), function, extraArgs, scriptServer); } public CarpetEventServer.CallbackResult call(final CarpetEventServer.Callback tickCall, final Entity entity, final Object... args) diff --git a/src/main/java/carpet/script/Expression.java b/src/main/java/carpet/script/Expression.java index c9aca6af..290f4fc5 100644 --- a/src/main/java/carpet/script/Expression.java +++ b/src/main/java/carpet/script/Expression.java @@ -1,6 +1,5 @@ package carpet.script; -import carpet.CarpetSettings; import carpet.script.Fluff.AbstractFunction; import carpet.script.Fluff.AbstractLazyFunction; import carpet.script.Fluff.AbstractLazyOperator; @@ -20,6 +19,7 @@ import carpet.script.exception.IntegrityException; import carpet.script.exception.InternalExpressionException; import carpet.script.exception.ResolvedException; import carpet.script.exception.ReturnStatement; +import carpet.script.external.Vanilla; import carpet.script.language.Arithmetic; import carpet.script.language.ControlFlow; import carpet.script.language.DataStructures; @@ -44,12 +44,14 @@ import java.util.HashMap; import java.util.List; import java.util.Map; import java.util.Set; -import java.util.function.*; +import java.util.function.BiFunction; +import java.util.function.BinaryOperator; +import java.util.function.DoubleToLongFunction; +import java.util.function.DoubleUnaryOperator; +import java.util.function.Function; +import java.util.function.Supplier; import java.util.stream.Collectors; -import static java.lang.Math.max; -import static java.lang.Math.min; - public class Expression { /** @@ -164,8 +166,8 @@ public class Expression } else { - output.add(expr.substring(max(0, token.pos - 40), token.pos)); - output.add(expr.substring(token.pos, min(token.pos + 1 + 40, expr.length()))); + output.add(expr.substring(Math.max(0, token.pos - 40), token.pos)); + output.add(expr.substring(token.pos, Math.min(token.pos + 1 + 40, expr.length()))); } return output; } @@ -424,7 +426,7 @@ public class Expression return exc; } // unexpected really - should be caught earlier and converted to InternalExpressionException - CarpetSettings.LOG.error("Unexpected exception while running Scarpet code", exc); + CarpetScriptServer.LOG.error("Unexpected exception while running Scarpet code", exc); return new ExpressionException(c, e, token, "Internal error (please report this issue to Carpet) while evaluating: " + exc); } @@ -1188,13 +1190,14 @@ public class Expression final List rpn = shuntingYard(context); validate(context, rpn); final ExpressionNode root = RPNToParseTree(rpn, context); - if (!CarpetSettings.scriptsOptimization) + if (!Vanilla.ScriptServer_scriptOptimizations(((CarpetScriptServer)context.scriptServer()).server)) { return root.op; } final Context optimizeOnlyContext = new Context.ContextForErrorReporting(context); - if (CarpetSettings.scriptsDebugging) + final boolean scriptsDebugging = Vanilla.ScriptServer_scriptDebugging(((CarpetScriptServer)context.scriptServer()).server); + if (scriptsDebugging) { CarpetScriptServer.LOG.info("Input code size for " + getModuleName() + ": " + treeSize(root) + " nodes, " + treeDepth(root) + " deep"); } @@ -1209,36 +1212,36 @@ public class Expression changed = false; while (true) { - if (CarpetSettings.scriptsDebugging) + if (scriptsDebugging) { prevTreeSize = treeSize(root); prevTreeDepth = treeDepth(root); } - final boolean optimized = compactTree(root, Context.Type.NONE, 0); + final boolean optimized = compactTree(root, Context.Type.NONE, 0, scriptsDebugging); if (!optimized) { break; } changed = true; - if (CarpetSettings.scriptsDebugging) + if (scriptsDebugging) { CarpetScriptServer.LOG.info("Compacted from " + prevTreeSize + " nodes, " + prevTreeDepth + " code depth to " + treeSize(root) + " nodes, " + treeDepth(root) + " code depth"); } } while (true) { - if (CarpetSettings.scriptsDebugging) + if (scriptsDebugging) { prevTreeSize = treeSize(root); prevTreeDepth = treeDepth(root); } - final boolean optimized = optimizeTree(optimizeOnlyContext, root, Context.Type.NONE, 0); + final boolean optimized = optimizeTree(optimizeOnlyContext, root, Context.Type.NONE, 0, scriptsDebugging); if (!optimized) { break; } changed = true; - if (CarpetSettings.scriptsDebugging) + if (scriptsDebugging) { CarpetScriptServer.LOG.info("Optimized from " + prevTreeSize + " nodes, " + prevTreeDepth + " code depth to " + treeSize(root) + " nodes, " + treeDepth(root) + " code depth"); } @@ -1258,7 +1261,7 @@ public class Expression } - private boolean compactTree(final ExpressionNode node, final Context.Type expectedType, final int indent) + private boolean compactTree(final ExpressionNode node, final Context.Type expectedType, final int indent, final boolean scriptsDebugging) { // ctx is just to report errors, not values evaluation boolean optimized = false; @@ -1278,7 +1281,7 @@ public class Expression final Context.Type requestedType = operation.staticType(expectedType); for (final ExpressionNode arg : node.args) { - if (compactTree(arg, requestedType, indent + 1)) + if (compactTree(arg, requestedType, indent + 1, scriptsDebugging)) { optimized = true; } @@ -1308,7 +1311,7 @@ public class Expression returnNode.token = returnNode.args.get(0).token; returnNode.range = returnNode.args.get(0).range; returnNode.args = returnNode.args.get(0).args; - if (CarpetSettings.scriptsDebugging) + if (scriptsDebugging) { CarpetScriptServer.LOG.info(" - Removed unnecessary tail return of " + returnNode.token.surface + " from function body at line " + (returnNode.token.lineno + 1) + ", node depth " + indent); } @@ -1318,7 +1321,7 @@ public class Expression returnNode.op = LazyValue.ofConstant(Value.NULL); returnNode.token.morph(Tokenizer.Token.TokenType.CONSTANT, ""); returnNode.args = Collections.emptyList(); - if (CarpetSettings.scriptsDebugging) + if (scriptsDebugging) { CarpetScriptServer.LOG.info(" - Removed unnecessary tail return from function body at line " + (returnNode.token.lineno + 1) + ", node depth " + indent); } @@ -1356,7 +1359,7 @@ public class Expression newargs.addAll(optimizedChild.args); } - if (CarpetSettings.scriptsDebugging) + if (scriptsDebugging) { CarpetScriptServer.LOG.info(" - " + symbol + "(" + node.args.size() + ") => " + function + "(" + newargs.size() + ") at line " + (node.token.lineno + 1) + ", node depth " + indent); } @@ -1368,7 +1371,7 @@ public class Expression return optimized; } - private boolean optimizeTree(final Context ctx, final ExpressionNode node, Context.Type expectedType, final int indent) + private boolean optimizeTree(final Context ctx, final ExpressionNode node, Context.Type expectedType, final int indent, final boolean scriptsDebugging) { // ctx is just to report errors, not values evaluation boolean optimized = false; @@ -1390,7 +1393,7 @@ public class Expression final Context.Type requestedType = operation.staticType(expectedType); for (final ExpressionNode arg : node.args) { - if (optimizeTree(ctx, arg, requestedType, indent + 1)) + if (optimizeTree(ctx, arg, requestedType, indent + 1, scriptsDebugging)) { optimized = true; } @@ -1457,7 +1460,7 @@ public class Expression result = ((ILazyOperator) operation).lazyEval(ctx, expectedType, this, node.token, args.get(0), args.get(1)).evalValue(null, expectedType); } node.op = LazyValue.ofConstant(result); - if (CarpetSettings.scriptsDebugging) + if (scriptsDebugging) { CarpetScriptServer.LOG.info(" - " + symbol + "(" + args.stream().map(a -> a.evalValue(null, requestedType).getString()).collect(Collectors.joining(", ")) + ") => " + result.getString() + " at line " + (node.token.lineno + 1) + ", node depth " + indent); } diff --git a/src/main/java/carpet/script/Fluff.java b/src/main/java/carpet/script/Fluff.java index ca91195e..b0fc240e 100644 --- a/src/main/java/carpet/script/Fluff.java +++ b/src/main/java/carpet/script/Fluff.java @@ -1,6 +1,5 @@ package carpet.script; -import carpet.CarpetSettings; import carpet.script.exception.ExpressionException; import carpet.script.exception.InternalExpressionException; import carpet.script.value.FunctionUnpackedArgumentsValue; @@ -218,7 +217,7 @@ public abstract class Fluff } else { - CarpetSettings.LOG.error("How did we get here 1"); + CarpetScriptServer.LOG.error("How did we get here 1"); } return params; } diff --git a/src/main/java/carpet/script/Module.java b/src/main/java/carpet/script/Module.java index b687c073..9eff5647 100644 --- a/src/main/java/carpet/script/Module.java +++ b/src/main/java/carpet/script/Module.java @@ -9,10 +9,8 @@ import java.util.Objects; import org.apache.commons.io.IOUtils; -import carpet.CarpetServer; import carpet.script.argument.FileArgument; import net.minecraft.nbt.Tag; -import net.minecraft.world.level.storage.LevelResource; public record Module(String name, String code, boolean library) { @@ -89,9 +87,9 @@ public record Module(String name, String code, boolean library) } } - public static Tag getData(final Module module) + public static Tag getData(final Module module, final ScriptServer scriptServer) { - final Path dataFile = resolveResource(module); + final Path dataFile = resolveResource(module, scriptServer); if (dataFile == null || !Files.exists(dataFile) || !(Files.isRegularFile(dataFile))) { return null; @@ -102,9 +100,9 @@ public record Module(String name, String code, boolean library) } } - public static void saveData(final Module module, final Tag globalState) + public static void saveData(final Module module, final Tag globalState, final ScriptServer scriptServer) { - final Path dataFile = resolveResource(module); + final Path dataFile = resolveResource(module, scriptServer); if (dataFile == null) { return; @@ -126,9 +124,8 @@ public record Module(String name, String code, boolean library) } } - private static Path resolveResource(final Module module) + private static Path resolveResource(final Module module, final ScriptServer scriptServer) { - return module == null ? null : CarpetServer.minecraft_server.getWorldPath(LevelResource.ROOT).resolve("scripts/" + module.name() + ".data.nbt"); // commandline app + return module == null ? null : scriptServer.resolveResource(module.name() + ".data.nbt"); } - } diff --git a/src/main/java/carpet/commands/ScriptCommand.java b/src/main/java/carpet/script/ScriptCommand.java similarity index 56% rename from src/main/java/carpet/commands/ScriptCommand.java rename to src/main/java/carpet/script/ScriptCommand.java index 8251f051..6f9d2256 100644 --- a/src/main/java/carpet/commands/ScriptCommand.java +++ b/src/main/java/carpet/script/ScriptCommand.java @@ -1,21 +1,11 @@ -package carpet.commands; +package carpet.script; -import carpet.CarpetServer; -import carpet.CarpetSettings; +import carpet.script.external.Carpet; +import carpet.script.external.Vanilla; import carpet.script.utils.AppStoreManager; -import carpet.script.CarpetEventServer; -import carpet.script.CarpetExpression; -import carpet.script.CarpetScriptHost; -import carpet.script.Expression; -import carpet.script.LazyValue; -import carpet.script.ScriptHost; -import carpet.script.Tokenizer; import carpet.script.exception.CarpetExpressionException; import carpet.script.value.FunctionValue; import carpet.script.value.Value; -import carpet.utils.CarpetProfiler; -import carpet.utils.CommandHelper; -import carpet.utils.Messenger; import com.mojang.brigadier.CommandDispatcher; import com.mojang.brigadier.arguments.StringArgumentType; import com.mojang.brigadier.builder.LiteralArgumentBuilder; @@ -24,7 +14,6 @@ import com.mojang.brigadier.exceptions.CommandSyntaxException; import com.mojang.brigadier.suggestion.Suggestions; import com.mojang.brigadier.suggestion.SuggestionsBuilder; import net.minecraft.commands.CommandBuildContext; -import net.minecraft.world.level.GameRules; import org.apache.commons.lang3.StringUtils; import java.io.IOException; @@ -39,6 +28,7 @@ import java.util.concurrent.CompletableFuture; import java.util.function.Predicate; import java.util.function.Supplier; import java.util.stream.Collectors; + import net.minecraft.commands.CommandSourceStack; import net.minecraft.commands.arguments.blocks.BlockInput; import net.minecraft.commands.arguments.blocks.BlockPredicateArgument; @@ -60,52 +50,67 @@ public class ScriptCommand { private static final TreeSet scarpetFunctions; private static final TreeSet APIFunctions; + static { - Set allFunctions = (new CarpetExpression(null, "null", null, null)).getExpr().getFunctionNames(); + final Set allFunctions = (new CarpetExpression(null, "null", null, null)).getExpr().getFunctionNames(); scarpetFunctions = new TreeSet<>(Expression.none.getFunctionNames()); APIFunctions = allFunctions.stream().filter(s -> !scarpetFunctions.contains(s)).collect(Collectors.toCollection(TreeSet::new)); } - public static List suggestFunctions(ScriptHost host, String previous, String prefix) + public static List suggestFunctions(final ScriptHost host, String previous, final String prefix) { previous = previous.replace("\\'", ""); - int quoteCount = StringUtils.countMatches(previous,'\''); + final int quoteCount = StringUtils.countMatches(previous, '\''); if (quoteCount % 2 == 1) + { return Collections.emptyList(); - int maxLen = prefix.length()<3 ? (prefix.length()*2+1) : 1234; - String eventPrefix = prefix.startsWith("__on_")?prefix.substring(5):null; - List scarpetMatches = scarpetFunctions.stream(). - filter(s -> s.startsWith(prefix) && s.length() <= maxLen).map(s -> s+"(").collect(Collectors.toList()); + } + final int maxLen = prefix.length() < 3 ? (prefix.length() * 2 + 1) : 1234; + final String eventPrefix = prefix.startsWith("__on_") ? prefix.substring(5) : null; + final List scarpetMatches = scarpetFunctions.stream(). + filter(s -> s.startsWith(prefix) && s.length() <= maxLen).map(s -> s + "(").collect(Collectors.toList()); scarpetMatches.addAll(APIFunctions.stream(). - filter(s -> s.startsWith(prefix) && s.length() <= maxLen).map(s -> s+"(").collect(Collectors.toList())); + filter(s -> s.startsWith(prefix) && s.length() <= maxLen).map(s -> s + "(").toList()); // not that useful in commandline, more so in external scripts, so skipping here - if (eventPrefix != null) scarpetMatches.addAll(CarpetEventServer.Event.publicEvents(null).stream(). - filter(e -> e.name.startsWith(eventPrefix)).map(s -> "__on_"+s.name+"(").collect(Collectors.toList())); - scarpetMatches.addAll(host.globalFunctionNames(host.main, s -> s.startsWith(prefix)).map(s -> s+"(").collect(Collectors.toList())); - scarpetMatches.addAll(host.globalVariableNames(host.main, s -> s.startsWith(prefix)).collect(Collectors.toList())); + if (eventPrefix != null) + { + scarpetMatches.addAll(CarpetEventServer.Event.publicEvents(null).stream(). + filter(e -> e.name.startsWith(eventPrefix)).map(s -> "__on_" + s.name + "(").toList()); + } + scarpetMatches.addAll(host.globalFunctionNames(host.main, s -> s.startsWith(prefix)).map(s -> s + "(").toList()); + scarpetMatches.addAll(host.globalVariableNames(host.main, s -> s.startsWith(prefix)).toList()); return scarpetMatches; } private static CompletableFuture suggestCode( - CommandContext context, - SuggestionsBuilder suggestionsBuilder + final CommandContext context, + final SuggestionsBuilder suggestionsBuilder ) throws CommandSyntaxException { - CarpetScriptHost currentHost = getHost(context); - String previous = suggestionsBuilder.getRemaining(); - int strlen = previous.length(); - StringBuilder lastToken = new StringBuilder(); - for (int idx = strlen-1; idx >=0; idx--) + final CarpetScriptHost currentHost = getHost(context); + final String previous = suggestionsBuilder.getRemaining(); + final int strlen = previous.length(); + final StringBuilder lastToken = new StringBuilder(); + for (int idx = strlen - 1; idx >= 0; idx--) { - char ch = previous.charAt(idx); - if (Character.isLetterOrDigit(ch) || ch == '_') lastToken.append(ch); else break; + final char ch = previous.charAt(idx); + if (Character.isLetterOrDigit(ch) || ch == '_') + { + lastToken.append(ch); + } + else + { + break; + } } if (lastToken.length() == 0) + { return suggestionsBuilder.buildFuture(); - String prefix = lastToken.reverse().toString(); - String previousString = previous.substring(0,previous.length()-prefix.length()) ; - suggestFunctions(currentHost, previousString, prefix).forEach(text -> suggestionsBuilder.suggest(previousString+text)); + } + final String prefix = lastToken.reverse().toString(); + final String previousString = previous.substring(0, previous.length() - prefix.length()); + suggestFunctions(currentHost, previousString, prefix).forEach(text -> suggestionsBuilder.suggest(previousString + text)); return suggestionsBuilder.buildFuture(); } @@ -114,59 +119,72 @@ public class ScriptCommand * variable. */ private static CompletableFuture suggestDownloadableApps( - CommandContext context, - SuggestionsBuilder suggestionsBuilder - ) throws CommandSyntaxException { - - return CompletableFuture.supplyAsync(()->{ - String previous = suggestionsBuilder.getRemaining(); - try { + final CommandContext context, + final SuggestionsBuilder suggestionsBuilder + ) throws CommandSyntaxException + { + + return CompletableFuture.supplyAsync(() -> { + final String previous = suggestionsBuilder.getRemaining(); + try + { AppStoreManager.suggestionsFromPath(previous).forEach(suggestionsBuilder::suggest); } - catch (IOException e) + catch (final IOException e) { - CarpetSettings.LOG.warn("Exception when fetching app store structure", e); + CarpetScriptServer.LOG.warn("Exception when fetching app store structure", e); } return suggestionsBuilder.build(); }); } - public static void register(CommandDispatcher dispatcher, final CommandBuildContext commandBuildContext) + private static CarpetScriptServer ss(final CommandContext context) { - LiteralArgumentBuilder b = literal("globals"). + return Vanilla.MinecraftServer_getScriptServer(context.getSource().getServer()); + } + + public static void register(final CommandDispatcher dispatcher, final CommandBuildContext commandBuildContext) + { + final LiteralArgumentBuilder b = literal("globals"). executes(context -> listGlobals(context, false)). then(literal("all").executes(context -> listGlobals(context, true))); - LiteralArgumentBuilder o = literal("stop"). - executes( (cc) -> { CarpetServer.scriptServer.stopAll = true; return 1;}); - LiteralArgumentBuilder u = literal("resume"). - executes( (cc) -> { CarpetServer.scriptServer.stopAll = false; return 1;}); - LiteralArgumentBuilder l = literal("run"). - requires((player) -> CommandHelper.canUseCommand(player, CarpetSettings.commandScriptACE)). + final LiteralArgumentBuilder o = literal("stop"). + executes((cc) -> { + ss(cc).stopAll = true; + return 1; + }); + final LiteralArgumentBuilder u = literal("resume"). + executes((cc) -> { + ss(cc).stopAll = false; + return 1; + }); + final LiteralArgumentBuilder l = literal("run"). + requires(Vanilla::ServerPlayer_canScriptACE). then(argument("expr", StringArgumentType.greedyString()).suggests(ScriptCommand::suggestCode). executes((cc) -> compute( cc, StringArgumentType.getString(cc, "expr")))); - LiteralArgumentBuilder s = literal("invoke"). - then(argument("call", StringArgumentType.word()).suggests( (cc, bb)->suggest(suggestFunctionCalls(cc),bb)). - executes( (cc) -> invoke( + final LiteralArgumentBuilder s = literal("invoke"). + then(argument("call", StringArgumentType.word()).suggests((cc, bb) -> suggest(suggestFunctionCalls(cc), bb)). + executes((cc) -> invoke( cc, StringArgumentType.getString(cc, "call"), null, null, "" - )) . + )). then(argument("arguments", StringArgumentType.greedyString()). - executes( (cc) -> invoke( + executes((cc) -> invoke( cc, StringArgumentType.getString(cc, "call"), null, null, StringArgumentType.getString(cc, "arguments") )))); - LiteralArgumentBuilder c = literal("invokepoint"). - then(argument("call", StringArgumentType.word()).suggests( (cc, bb)->suggest(suggestFunctionCalls(cc),bb)). + final LiteralArgumentBuilder c = literal("invokepoint"). + then(argument("call", StringArgumentType.word()).suggests((cc, bb) -> suggest(suggestFunctionCalls(cc), bb)). then(argument("origin", BlockPosArgument.blockPos()). - executes( (cc) -> invoke( + executes((cc) -> invoke( cc, StringArgumentType.getString(cc, "call"), BlockPosArgument.getSpawnablePos(cc, "origin"), @@ -174,18 +192,18 @@ public class ScriptCommand "" )). then(argument("arguments", StringArgumentType.greedyString()). - executes( (cc) -> invoke( + executes((cc) -> invoke( cc, StringArgumentType.getString(cc, "call"), BlockPosArgument.getSpawnablePos(cc, "origin"), null, StringArgumentType.getString(cc, "arguments") ))))); - LiteralArgumentBuilder h = literal("invokearea"). - then(argument("call", StringArgumentType.word()).suggests( (cc, bb)->suggest(suggestFunctionCalls(cc),bb)). + final LiteralArgumentBuilder h = literal("invokearea"). + then(argument("call", StringArgumentType.word()).suggests((cc, bb) -> suggest(suggestFunctionCalls(cc), bb)). then(argument("from", BlockPosArgument.blockPos()). then(argument("to", BlockPosArgument.blockPos()). - executes( (cc) -> invoke( + executes((cc) -> invoke( cc, StringArgumentType.getString(cc, "call"), BlockPosArgument.getSpawnablePos(cc, "from"), @@ -193,27 +211,27 @@ public class ScriptCommand "" )). then(argument("arguments", StringArgumentType.greedyString()). - executes( (cc) -> invoke( + executes((cc) -> invoke( cc, StringArgumentType.getString(cc, "call"), BlockPosArgument.getSpawnablePos(cc, "from"), BlockPosArgument.getSpawnablePos(cc, "to"), StringArgumentType.getString(cc, "arguments") )))))); - LiteralArgumentBuilder i = literal("scan").requires((player) -> player.hasPermission(2)). + final LiteralArgumentBuilder i = literal("scan").requires((player) -> player.hasPermission(2)). then(argument("origin", BlockPosArgument.blockPos()). then(argument("from", BlockPosArgument.blockPos()). then(argument("to", BlockPosArgument.blockPos()). then(argument("expr", StringArgumentType.greedyString()). suggests(ScriptCommand::suggestCode). - executes( (cc) -> scriptScan( + executes((cc) -> scriptScan( cc, BlockPosArgument.getSpawnablePos(cc, "origin"), BlockPosArgument.getSpawnablePos(cc, "from"), BlockPosArgument.getSpawnablePos(cc, "to"), StringArgumentType.getString(cc, "expr") )))))); - LiteralArgumentBuilder e = literal("fill").requires((player) -> player.hasPermission(2)). + final LiteralArgumentBuilder e = literal("fill").requires((player) -> player.hasPermission(2)). then(argument("origin", BlockPosArgument.blockPos()). then(argument("from", BlockPosArgument.blockPos()). then(argument("to", BlockPosArgument.blockPos()). @@ -240,7 +258,7 @@ public class ScriptCommand BlockPredicateArgument.getBlockPredicate(cc, "filter"), "solid" ))))))))); - LiteralArgumentBuilder t = literal("outline").requires((player) -> player.hasPermission(2)). + final LiteralArgumentBuilder t = literal("outline").requires((player) -> player.hasPermission(2)). then(argument("origin", BlockPosArgument.blockPos()). then(argument("from", BlockPosArgument.blockPos()). then(argument("to", BlockPosArgument.blockPos()). @@ -267,179 +285,187 @@ public class ScriptCommand BlockPredicateArgument.getBlockPredicate(cc, "filter"), "outline" ))))))))); - LiteralArgumentBuilder a = literal("load").requires( (player) -> CommandHelper.canUseCommand(player, CarpetSettings.commandScriptACE) ). + final LiteralArgumentBuilder a = literal("load").requires(Vanilla::ServerPlayer_canScriptACE). then(argument("app", StringArgumentType.word()). - suggests( (cc, bb) -> suggest(CarpetServer.scriptServer.listAvailableModules(true),bb)). + suggests((cc, bb) -> suggest(ss(cc).listAvailableModules(true), bb)). executes((cc) -> { - boolean success = CarpetServer.scriptServer.addScriptHost(cc.getSource(), StringArgumentType.getString(cc, "app"), null, true, false, false, null); - return success?1:0; + final boolean success = ss(cc).addScriptHost(cc.getSource(), StringArgumentType.getString(cc, "app"), null, true, false, false, null); + return success ? 1 : 0; }). then(literal("global"). executes((cc) -> - { - boolean success = CarpetServer.scriptServer.addScriptHost(cc.getSource(), StringArgumentType.getString(cc, "app"), null, false, false, false, null); - return success?1:0; - } + { + final boolean success = ss(cc).addScriptHost(cc.getSource(), StringArgumentType.getString(cc, "app"), null, false, false, false, null); + return success ? 1 : 0; + } ) ) ); - LiteralArgumentBuilder f = literal("unload").requires( (player) -> CommandHelper.canUseCommand(player, CarpetSettings.commandScriptACE) ). + final LiteralArgumentBuilder f = literal("unload").requires(Vanilla::ServerPlayer_canScriptACE). then(argument("app", StringArgumentType.word()). - suggests( (cc, bb) -> suggest(CarpetServer.scriptServer.unloadableModules,bb)). + suggests((cc, bb) -> suggest(ss(cc).unloadableModules, bb)). executes((cc) -> { - boolean success =CarpetServer.scriptServer.removeScriptHost(cc.getSource(), StringArgumentType.getString(cc, "app"), true, false); - return success?1:0; + final boolean success = ss(cc).removeScriptHost(cc.getSource(), StringArgumentType.getString(cc, "app"), true, false); + return success ? 1 : 0; })); - LiteralArgumentBuilder q = literal("event").requires( (player) -> CommandHelper.canUseCommand(player, CarpetSettings.commandScriptACE) ). - executes( (cc) -> listEvents(cc.getSource())). + final LiteralArgumentBuilder q = literal("event").requires(Vanilla::ServerPlayer_canScriptACE). + executes(ScriptCommand::listEvents). then(literal("add_to"). then(argument("event", StringArgumentType.word()). - suggests( (cc, bb) -> suggest(CarpetEventServer.Event.publicEvents(CarpetServer.scriptServer).stream().map(ev -> ev.name).collect(Collectors.toList()),bb)). + suggests((cc, bb) -> suggest(CarpetEventServer.Event.publicEvents(ss(cc)).stream().map(ev -> ev.name).collect(Collectors.toList()), bb)). then(argument("call", StringArgumentType.word()). - suggests( (cc, bb) -> suggest(suggestFunctionCalls(cc), bb)). - executes( (cc) -> CarpetServer.scriptServer.events.addEventFromCommand( + suggests((cc, bb) -> suggest(suggestFunctionCalls(cc), bb)). + executes((cc) -> ss(cc).events.addEventFromCommand( cc.getSource(), StringArgumentType.getString(cc, "event"), null, StringArgumentType.getString(cc, "call") - )?1:0)). + ) ? 1 : 0)). then(literal("from"). then(argument("app", StringArgumentType.word()). - suggests( (cc, bb) -> suggest(CarpetServer.scriptServer.modules.keySet(), bb)). + suggests((cc, bb) -> suggest(ss(cc).modules.keySet(), bb)). then(argument("call", StringArgumentType.word()). - suggests( (cc, bb) -> suggest(suggestFunctionCalls(cc), bb)). - executes( (cc) -> CarpetServer.scriptServer.events.addEventFromCommand( + suggests((cc, bb) -> suggest(suggestFunctionCalls(cc), bb)). + executes((cc) -> ss(cc).events.addEventFromCommand( cc.getSource(), StringArgumentType.getString(cc, "event"), StringArgumentType.getString(cc, "app"), StringArgumentType.getString(cc, "call") - )?1:0)))))). + ) ? 1 : 0)))))). then(literal("remove_from"). then(argument("event", StringArgumentType.word()). - suggests( (cc, bb) -> suggest(CarpetEventServer.Event.publicEvents(CarpetServer.scriptServer).stream().filter(CarpetEventServer.Event::isNeeded).map(ev -> ev.name).collect(Collectors.toList()) ,bb)). + suggests((cc, bb) -> suggest(CarpetEventServer.Event.publicEvents(ss(cc)).stream().filter(CarpetEventServer.Event::isNeeded).map(ev -> ev.name).collect(Collectors.toList()), bb)). then(argument("call", StringArgumentType.greedyString()). - suggests( (cc, bb) -> suggest(CarpetEventServer.Event.getEvent(StringArgumentType.getString(cc, "event"), CarpetServer.scriptServer).handler.inspectCurrentCalls().stream().map(CarpetEventServer.Callback::toString), bb)). - executes( (cc) -> CarpetServer.scriptServer.events.removeEventFromCommand( + suggests((cc, bb) -> suggest(CarpetEventServer.Event.getEvent(StringArgumentType.getString(cc, "event"), ss(cc)).handler.inspectCurrentCalls().stream().map(CarpetEventServer.Callback::toString), bb)). + executes((cc) -> ss(cc).events.removeEventFromCommand( cc.getSource(), StringArgumentType.getString(cc, "event"), StringArgumentType.getString(cc, "call") - )?1:0)))); + ) ? 1 : 0)))); - LiteralArgumentBuilder d = literal("download").requires((player) -> CommandHelper.canUseCommand(player, CarpetSettings.commandScriptACE)). + final LiteralArgumentBuilder d = literal("download").requires(Vanilla::ServerPlayer_canScriptACE). then(argument("path", StringArgumentType.greedyString()). suggests(ScriptCommand::suggestDownloadableApps). - executes(cc-> AppStoreManager.downloadScript(cc.getSource(), StringArgumentType.getString(cc,"path")))); - LiteralArgumentBuilder r = literal("remove").requires( (player) -> CommandHelper.canUseCommand(player, CarpetSettings.commandScriptACE) ). + executes(cc -> AppStoreManager.downloadScript(cc.getSource(), StringArgumentType.getString(cc, "path")))); + final LiteralArgumentBuilder r = literal("remove").requires(Vanilla::ServerPlayer_canScriptACE). then(argument("app", StringArgumentType.word()). - suggests( (cc, bb) -> suggest(CarpetServer.scriptServer.unloadableModules,bb)). + suggests((cc, bb) -> suggest(ss(cc).unloadableModules, bb)). executes((cc) -> { - boolean success =CarpetServer.scriptServer.uninstallApp(cc.getSource(), StringArgumentType.getString(cc, "app")); - return success?1:0; + final boolean success = ss(cc).uninstallApp(cc.getSource(), StringArgumentType.getString(cc, "app")); + return success ? 1 : 0; })); dispatcher.register(literal("script"). - requires((player) -> CommandHelper.canUseCommand(player, CarpetSettings.commandScript)). + requires(Vanilla::ServerPlayer_canScriptGeneral). then(b).then(u).then(o).then(l).then(s).then(c).then(h).then(i).then(e).then(t).then(a).then(f).then(q).then(d).then(r)); dispatcher.register(literal("script"). - requires((player) -> CommandHelper.canUseCommand(player, CarpetSettings.commandScript)). + requires(Vanilla::ServerPlayer_canScriptGeneral). then(literal("in"). then(argument("app", StringArgumentType.word()). - suggests( (cc, bb) -> suggest(CarpetServer.scriptServer.modules.keySet(), bb)). + suggests((cc, bb) -> suggest(ss(cc).modules.keySet(), bb)). then(b).then(u).then(o).then(l).then(s).then(c).then(h).then(i).then(e).then(t)))); } - private static CarpetScriptHost getHost(CommandContext context) throws CommandSyntaxException + + private static CarpetScriptHost getHost(final CommandContext context) throws CommandSyntaxException { CarpetScriptHost host; + final CarpetScriptServer scriptServer = ss(context); try { - String name = StringArgumentType.getString(context, "app").toLowerCase(Locale.ROOT); - CarpetScriptHost parentHost = CarpetServer.scriptServer.modules.getOrDefault(name, CarpetServer.scriptServer.globalHost); - host = parentHost.retrieveOwnForExecution(context.getSource()); + final String name = StringArgumentType.getString(context, "app").toLowerCase(Locale.ROOT); + final CarpetScriptHost parentHost = scriptServer.modules.getOrDefault(name, scriptServer.globalHost); + host = parentHost.retrieveOwnForExecution(context.getSource()); } - catch (IllegalArgumentException ignored) + catch (final IllegalArgumentException ignored) { - host = CarpetServer.scriptServer.globalHost; + host = scriptServer.globalHost; } host.setChatErrorSnooper(context.getSource()); return host; } - private static Collection suggestFunctionCalls(CommandContext c) throws CommandSyntaxException + + private static Collection suggestFunctionCalls(final CommandContext c) throws CommandSyntaxException { - CarpetScriptHost host = getHost(c); - return host.globalFunctionNames(host.main, s -> !s.startsWith("_")).sorted().collect(Collectors.toList()); + final CarpetScriptHost host = getHost(c); + return host.globalFunctionNames(host.main, s -> !s.startsWith("_")).sorted().collect(Collectors.toList()); } - private static int listEvents(CommandSourceStack source) + + private static int listEvents(final CommandContext context) { - Messenger.m(source, "w Lists ALL event handlers:"); - for (CarpetEventServer.Event event: CarpetEventServer.Event.getAllEvents(CarpetServer.scriptServer, null)) + CarpetScriptServer scriptServer = ss(context); + CommandSourceStack source = context.getSource(); + Carpet.Messenger_message(source, "w Lists ALL event handlers:"); + for (final CarpetEventServer.Event event : CarpetEventServer.Event.getAllEvents(scriptServer, null)) { boolean shownEvent = false; - for (CarpetEventServer.Callback c: event.handler.inspectCurrentCalls()) + for (final CarpetEventServer.Callback c : event.handler.inspectCurrentCalls()) { if (!shownEvent) { - Messenger.m(source, "w Handlers for "+event.name+": "); + Carpet.Messenger_message(source, "w Handlers for " + event.name + ": "); shownEvent = true; } - Messenger.m(source, "w - "+c.function.getString() +(c.host==null?"":" (from "+c.host+")")); + Carpet.Messenger_message(source, "w - " + c.function.getString() + (c.host == null ? "" : " (from " + c.host + ")")); } } return 1; } - private static int listGlobals(CommandContext context, boolean all) throws CommandSyntaxException - { - CarpetScriptHost host = getHost(context); - CommandSourceStack source = context.getSource(); - Messenger.m(source, "lb Stored functions"+((host == CarpetServer.scriptServer.globalHost)?":":" in "+host.getName()+":")); - host.globalFunctionNames(host.main, (str) -> all || !str.startsWith("__")).sorted().forEach( (s) -> { - FunctionValue fun = host.getFunction(s); + private static int listGlobals(final CommandContext context, final boolean all) throws CommandSyntaxException + { + final CarpetScriptHost host = getHost(context); + final CommandSourceStack source = context.getSource(); + final CarpetScriptServer scriptServer = ss(context); + + Carpet.Messenger_message(source, "lb Stored functions" + ((host == scriptServer.globalHost) ? ":" : " in " + host.getName() + ":")); + host.globalFunctionNames(host.main, (str) -> all || !str.startsWith("__")).sorted().forEach((s) -> { + final FunctionValue fun = host.getFunction(s); if (fun == null) { - Messenger.m(source, "gb "+s, "g - unused import"); - Messenger.m(source, "gi ----------------"); + Carpet.Messenger_message(source, "gb " + s, "g - unused import"); + Carpet.Messenger_message(source, "gi ----------------"); return; } - Expression expr = fun.getExpression(); - Tokenizer.Token tok = fun.getToken(); - List snippet = expr.getExpressionSnippet(tok); - Messenger.m(source, "wb "+fun.fullName(),"t defined at: line "+(tok.lineno+1)+" pos "+(tok.linepos+1)); - for (String snippetLine: snippet) + final Expression expr = fun.getExpression(); + final Tokenizer.Token tok = fun.getToken(); + final List snippet = expr.getExpressionSnippet(tok); + Carpet.Messenger_message(source, "wb " + fun.fullName(), "t defined at: line " + (tok.lineno + 1) + " pos " + (tok.linepos + 1)); + for (final String snippetLine : snippet) { - Messenger.m(source, "w "+snippetLine); + Carpet.Messenger_message(source, "w " + snippetLine); } - Messenger.m(source, "gi ----------------"); + Carpet.Messenger_message(source, "gi ----------------"); }); //Messenger.m(source, "w "+code); - Messenger.m(source, "w "); - Messenger.m(source, "lb Global variables"+((host == CarpetServer.scriptServer.globalHost)?":":" in "+host.getName()+":")); - host.globalVariableNames(host.main, (s) -> s.startsWith("global_")).sorted().forEach( (s) -> { - LazyValue variable = host.getGlobalVariable(s); + Carpet.Messenger_message(source, "w "); + Carpet.Messenger_message(source, "lb Global variables" + ((host == scriptServer.globalHost) ? ":" : " in " + host.getName() + ":")); + host.globalVariableNames(host.main, (s) -> s.startsWith("global_")).sorted().forEach((s) -> { + final LazyValue variable = host.getGlobalVariable(s); if (variable == null) { - Messenger.m(source, "gb "+s, "g - unused import"); + Carpet.Messenger_message(source, "gb " + s, "g - unused import"); } else { - Messenger.m(source, "wb "+s+": ", "w "+ variable.evalValue(null).getPrettyString()); + Carpet.Messenger_message(source, "wb " + s + ": ", "w " + variable.evalValue(null).getPrettyString()); } }); return 1; } - public static int handleCall(CommandSourceStack source, CarpetScriptHost host, Supplier call) + public static int handleCall(final CommandSourceStack source, final CarpetScriptHost host, final Supplier call) { try { - CarpetProfiler.ProfilerToken currentSection = CarpetProfiler.start_section(null, "Scarpet run", CarpetProfiler.TYPE.GENERAL); + final Runnable token = Carpet.startProfilerSection("Scarpet run"); host.setChatErrorSnooper(source); - long start = System.nanoTime(); - Value result = call.get(); - long time = ((System.nanoTime()-start)/1000); + final long start = System.nanoTime(); + final Value result = call.get(); + long time = ((System.nanoTime() - start) / 1000); String metric = "\u00B5s"; if (time > 5000) { @@ -451,20 +477,20 @@ public class ScriptCommand time /= 1000; metric = "s"; } - Messenger.m(source, "wi = ", "wb "+result.getString(), "gi ("+time+metric+")"); - int intres = (int)result.readInteger(); - CarpetProfiler.end_current_section(currentSection); + Carpet.Messenger_message(source, "wi = ", "wb " + result.getString(), "gi (" + time + metric + ")"); + final int intres = (int) result.readInteger(); + token.run(); return intres; } - catch (CarpetExpressionException e) + catch (final CarpetExpressionException e) { host.handleErrorWithStack("Error while evaluating expression", e); } - catch (ArithmeticException ae) + catch (final ArithmeticException ae) { host.handleErrorWithStack("Math doesn't compute", ae); } - catch (StackOverflowError soe) + catch (final StackOverflowError soe) { host.handleErrorWithStack("Your thoughts are too deep", soe); } @@ -472,16 +498,16 @@ public class ScriptCommand //host.resetErrorSnooper(); // lets say no need to reset the snooper in case something happens on the way } - private static int invoke(CommandContext context, String call, BlockPos pos1, BlockPos pos2, String args) throws CommandSyntaxException + private static int invoke(final CommandContext context, final String call, final BlockPos pos1, final BlockPos pos2, final String args) throws CommandSyntaxException { - CommandSourceStack source = context.getSource(); - CarpetScriptHost host = getHost(context); + final CommandSourceStack source = context.getSource(); + final CarpetScriptHost host = getHost(context); if (call.startsWith("__")) { - Messenger.m(source, "r Hidden functions are only callable in scripts"); + Carpet.Messenger_message(source, "r Hidden functions are only callable in scripts"); return 0; } - List positions = new ArrayList<>(); + final List positions = new ArrayList<>(); if (pos1 != null) { positions.add(pos1.getX()); @@ -496,34 +522,34 @@ public class ScriptCommand } //if (!(args.trim().isEmpty())) // arguments.addAll(Arrays.asList(args.trim().split("\\s+"))); - return handleCall(source, host, () -> host.callLegacy(source, call, positions, args)); + return handleCall(source, host, () -> host.callLegacy(source, call, positions, args)); } - private static int compute(CommandContext context, String expr) throws CommandSyntaxException + private static int compute(final CommandContext context, final String expr) throws CommandSyntaxException { - CommandSourceStack source = context.getSource(); - CarpetScriptHost host = getHost(context); + final CommandSourceStack source = context.getSource(); + final CarpetScriptHost host = getHost(context); return handleCall(source, host, () -> { - CarpetExpression ex = new CarpetExpression(host.main, expr, source, new BlockPos(0, 0, 0)); + final CarpetExpression ex = new CarpetExpression(host.main, expr, source, new BlockPos(0, 0, 0)); return ex.scriptRunCommand(host, new BlockPos(source.getPosition())); }); } - private static int scriptScan(CommandContext context, BlockPos origin, BlockPos a, BlockPos b, String expr) throws CommandSyntaxException + private static int scriptScan(final CommandContext context, final BlockPos origin, final BlockPos a, final BlockPos b, final String expr) throws CommandSyntaxException { - CommandSourceStack source = context.getSource(); - CarpetScriptHost host = getHost(context); - BoundingBox area = BoundingBox.fromCorners(a, b); - CarpetExpression cexpr = new CarpetExpression(host.main, expr, source, origin); - int int_1 = area.getXSpan() * area.getYSpan() * area.getZSpan(); // X Y Z - if (int_1 > Math.max(source.getServer().getGameRules().getInt(GameRules.RULE_COMMAND_MODIFICATION_BLOCK_LIMIT), CarpetSettings.fillLimit)) + final CommandSourceStack source = context.getSource(); + final CarpetScriptHost host = getHost(context); + final BoundingBox area = BoundingBox.fromCorners(a, b); + final CarpetExpression cexpr = new CarpetExpression(host.main, expr, source, origin); + final int int_1 = area.getXSpan() * area.getYSpan() * area.getZSpan(); // X Y Z + if (int_1 > Vanilla.MinecraftServer_getFillLimit(source.getServer()) ) { - Messenger.m(source, "r too many blocks to evaluate: " + int_1); + Carpet.Messenger_message(source, "r too many blocks to evaluate: " + int_1); return 1; } int successCount = 0; - CarpetSettings.impendingFillSkipUpdates.set(!CarpetSettings.fillUpdates); + Carpet.getImpendingFillSkipUpdates().set(!Carpet.getFillUpdates()); try { for (int x = area.minX(); x <= area.maxX(); x++) @@ -534,48 +560,51 @@ public class ScriptCommand { try { - if (cexpr.fillAndScanCommand(host, x, y, z)) successCount++; + if (cexpr.fillAndScanCommand(host, x, y, z)) + { + successCount++; + } } - catch (ArithmeticException ignored) + catch (final ArithmeticException ignored) { } } } } } - catch (CarpetExpressionException exc) + catch (final CarpetExpressionException exc) { host.handleErrorWithStack("Error while processing command", exc); return 0; } finally { - CarpetSettings.impendingFillSkipUpdates.set(false); + Carpet.getImpendingFillSkipUpdates().set(false); } - Messenger.m(source, "w Expression successful in " + successCount + " out of " + int_1 + " blocks"); + Carpet.Messenger_message(source, "w Expression successful in " + successCount + " out of " + int_1 + " blocks"); return successCount; } - private static int scriptFill(CommandContext context, BlockPos origin, BlockPos a, BlockPos b, String expr, - BlockInput block, Predicate replacement, String mode) throws CommandSyntaxException + private static int scriptFill(final CommandContext context, final BlockPos origin, final BlockPos a, final BlockPos b, final String expr, + final BlockInput block, final Predicate replacement, final String mode) throws CommandSyntaxException { - CommandSourceStack source = context.getSource(); - CarpetScriptHost host = getHost(context); - BoundingBox area = BoundingBox.fromCorners(a, b); - CarpetExpression cexpr = new CarpetExpression(host.main, expr, source, origin); - int int_1 = area.getXSpan() * area.getYSpan() * area.getZSpan(); - if (int_1 > Math.max(source.getServer().getGameRules().getInt(GameRules.RULE_COMMAND_MODIFICATION_BLOCK_LIMIT), CarpetSettings.fillLimit)) + final CommandSourceStack source = context.getSource(); + final CarpetScriptHost host = getHost(context); + final BoundingBox area = BoundingBox.fromCorners(a, b); + final CarpetExpression cexpr = new CarpetExpression(host.main, expr, source, origin); + final int int_1 = area.getXSpan() * area.getYSpan() * area.getZSpan(); + if (int_1 > Vanilla.MinecraftServer_getFillLimit(source.getServer())) { - Messenger.m(source, "r too many blocks to evaluate: "+ int_1); + Carpet.Messenger_message(source, "r too many blocks to evaluate: " + int_1); return 1; } boolean[][][] volume = new boolean[area.getXSpan()][area.getYSpan()][area.getZSpan()]; //X then Y then Z got messedup - BlockPos.MutableBlockPos mbpos = origin.mutable(); - ServerLevel world = source.getLevel(); + final BlockPos.MutableBlockPos mbpos = origin.mutable(); + final ServerLevel world = source.getLevel(); for (int x = area.minX(); x <= area.maxX(); x++) { @@ -587,26 +616,26 @@ public class ScriptCommand { if (cexpr.fillAndScanCommand(host, x, y, z)) { - volume[x-area.minX()][y-area.minY()][z-area.minZ()]=true; + volume[x - area.minX()][y - area.minY()][z - area.minZ()] = true; } } - catch (CarpetExpressionException e) + catch (final CarpetExpressionException e) { host.handleErrorWithStack("Exception while filling the area", e); return 0; } - catch (ArithmeticException e) + catch (final ArithmeticException e) { } } } } - final int maxx = area.getXSpan()-1; - final int maxy = area.getYSpan()-1; - final int maxz = area.getZSpan()-1; + final int maxx = area.getXSpan() - 1; + final int maxy = area.getYSpan() - 1; + final int maxz = area.getZSpan() - 1; if ("outline".equalsIgnoreCase(mode)) { - boolean[][][] newVolume = new boolean[area.getXSpan()][area.getYSpan()][area.getZSpan()]; + final boolean[][][] newVolume = new boolean[area.getXSpan()][area.getYSpan()][area.getZSpan()]; for (int x = 0; x <= maxx; x++) { for (int y = 0; y <= maxy; y++) @@ -615,12 +644,12 @@ public class ScriptCommand { if (volume[x][y][z]) { - if ( ( (x != 0 && !volume[x-1][y ][z ]) || - (x != maxx && !volume[x+1][y ][z ]) || - (y != 0 && !volume[x ][y-1][z ]) || - (y != maxy && !volume[x ][y+1][z ]) || - (z != 0 && !volume[x ][y ][z-1]) || - (z != maxz && !volume[x ][y ][z+1]) + if (((x != 0 && !volume[x - 1][y][z]) || + (x != maxx && !volume[x + 1][y][z]) || + (y != 0 && !volume[x][y - 1][z]) || + (y != maxy && !volume[x][y + 1][z]) || + (z != 0 && !volume[x][y][z - 1]) || + (z != maxz && !volume[x][y][z + 1]) )) { newVolume[x][y][z] = true; @@ -633,7 +662,7 @@ public class ScriptCommand } int affected = 0; - CarpetSettings.impendingFillSkipUpdates.set(!CarpetSettings.fillUpdates); + Carpet.getImpendingFillSkipUpdates().set(!Carpet.getFillUpdates()); for (int x = 0; x <= maxx; x++) { for (int y = 0; y <= maxy; y++) @@ -642,14 +671,14 @@ public class ScriptCommand { if (volume[x][y][z]) { - mbpos.set(x+area.minX(), y+area.minY(), z+area.minZ()); + mbpos.set(x + area.minX(), y + area.minY(), z + area.minZ()); if (replacement == null || replacement.test( - new BlockInWorld( world, mbpos, true))) + new BlockInWorld(world, mbpos, true))) { - BlockEntity tileentity = world.getBlockEntity(mbpos); + final BlockEntity tileentity = world.getBlockEntity(mbpos); Clearable.tryClear(tileentity); - - if (block.place(world, mbpos,2)) + + if (block.place(world, mbpos, 2)) { ++affected; } @@ -658,9 +687,9 @@ public class ScriptCommand } } } - CarpetSettings.impendingFillSkipUpdates.set(false); + Carpet.getImpendingFillSkipUpdates().set(false); - if (CarpetSettings.fillUpdates && block != null) + if (Carpet.getFillUpdates() && block != null) { for (int x = 0; x <= maxx; x++) { @@ -670,15 +699,15 @@ public class ScriptCommand { if (volume[x][y][z]) { - mbpos.set(x+area.minX(), y+area.minY(), z+area.minZ()); - Block blokc = world.getBlockState(mbpos).getBlock(); + mbpos.set(x + area.minX(), y + area.minY(), z + area.minZ()); + final Block blokc = world.getBlockState(mbpos).getBlock(); world.blockUpdated(mbpos, blokc); } } } } } - Messenger.m(source, "gi Affected "+affected+" blocks in "+area.getXSpan() * area.getYSpan() * area.getZSpan()+" block volume"); + Carpet.Messenger_message(source, "gi Affected " + affected + " blocks in " + area.getXSpan() * area.getYSpan() * area.getZSpan() + " block volume"); return 1; } } diff --git a/src/main/java/carpet/script/ScriptHost.java b/src/main/java/carpet/script/ScriptHost.java index 6737be00..7364eeb4 100644 --- a/src/main/java/carpet/script/ScriptHost.java +++ b/src/main/java/carpet/script/ScriptHost.java @@ -10,6 +10,7 @@ import it.unimi.dsi.fastutil.objects.Object2ObjectOpenHashMap; import org.slf4j.Logger; import org.slf4j.LoggerFactory; +import java.nio.file.Path; import java.util.HashMap; import java.util.HashSet; import java.util.List; @@ -52,6 +53,11 @@ public abstract class ScriptHost return randomizers.remove(aLong) != null; } + public Path resolveScriptFile(final String suffix) + { + return scriptServer.resolveResource(suffix); + } + public static class ModuleData { Module parent; diff --git a/src/main/java/carpet/script/ScriptServer.java b/src/main/java/carpet/script/ScriptServer.java index 5d13d024..c176c9b0 100644 --- a/src/main/java/carpet/script/ScriptServer.java +++ b/src/main/java/carpet/script/ScriptServer.java @@ -1,12 +1,15 @@ package carpet.script; +import java.nio.file.Path; import java.util.Map; import java.util.concurrent.ConcurrentHashMap; import carpet.script.value.Value; // WIP -public class ScriptServer +public abstract class ScriptServer { public final Map systemGlobals = new ConcurrentHashMap<>(); + + public abstract Path resolveResource(final String suffix); } diff --git a/src/main/java/carpet/script/api/Auxiliary.java b/src/main/java/carpet/script/api/Auxiliary.java index 4faa92fb..00d273cf 100644 --- a/src/main/java/carpet/script/api/Auxiliary.java +++ b/src/main/java/carpet/script/api/Auxiliary.java @@ -1,10 +1,7 @@ package carpet.script.api; -import carpet.CarpetServer; -import carpet.fakes.MinecraftServerInterface; -import carpet.fakes.ThreadedAnvilChunkStorageInterface; -import carpet.helpers.FeatureGenerator; -import carpet.logging.HUDController; +import carpet.script.external.Vanilla; +import carpet.script.utils.FeatureGenerator; import carpet.script.argument.FileArgument; import carpet.script.CarpetContext; import carpet.script.CarpetEventServer; @@ -19,6 +16,7 @@ import carpet.script.exception.ExitStatement; import carpet.script.exception.InternalExpressionException; import carpet.script.exception.ThrowStatement; import carpet.script.exception.Throwables; +import carpet.script.external.Carpet; import carpet.script.utils.SnoopyCommandSource; import carpet.script.utils.SystemInfo; import carpet.script.utils.InputValidator; @@ -36,7 +34,6 @@ import carpet.script.value.NumericValue; import carpet.script.value.StringValue; import carpet.script.value.Value; import carpet.script.value.ValueConversions; -import carpet.utils.Messenger; import com.google.common.collect.Lists; import net.minecraft.SharedConstants; import net.minecraft.commands.CommandSourceStack; @@ -73,7 +70,6 @@ import net.minecraft.world.entity.Entity; import net.minecraft.world.entity.EntityType; import net.minecraft.world.entity.EquipmentSlot; import net.minecraft.world.entity.decoration.ArmorStand; -import net.minecraft.world.entity.player.Player; import net.minecraft.world.item.ItemStack; import net.minecraft.world.level.ChunkPos; import net.minecraft.world.level.Level; @@ -613,11 +609,11 @@ public class Auxiliary final Map map; if (actionString.equals("player_list_header")) { - map = HUDController.scarpet_headers; + map = Carpet.getScarpetHeaders(); } else { - map = HUDController.scarpet_footers; + map = Carpet.getScarpetFooters(); } final AtomicInteger total = new AtomicInteger(0); @@ -636,7 +632,7 @@ public class Auxiliary total.getAndIncrement(); }); } - HUDController.update_hud(((CarpetContext) c).server(), targetList); + Carpet.updateScarpetHUDs(((CarpetContext) c).server(), targetList); return NumericValue.of(total.get()); } final ClientboundSetTitlesAnimationPacket timesPacket; // TimesPacket @@ -678,7 +674,7 @@ public class Auxiliary { values = list.getItems(); } - return new FormattedTextValue(Messenger.c(values.stream().map(Value::getString).toArray())); + return new FormattedTextValue(Carpet.Messenger_compose(values.stream().map(Value::getString).toArray())); }); expression.addContextFunction("run", 1, (c, t, lv) -> @@ -750,7 +746,8 @@ public class Auxiliary expression.addContextFunction("game_tick", -1, (c, t, lv) -> { final CarpetContext cc = (CarpetContext) c; final MinecraftServer server = cc.server(); - if (CarpetServer.scriptServer == null) + final CarpetScriptServer scriptServer = (CarpetScriptServer) c.host.scriptServer(); + if (scriptServer == null) { return Value.NULL; } @@ -758,18 +755,18 @@ public class Auxiliary { throw new InternalExpressionException("Unable to run ticks from threads"); } - if (CarpetServer.scriptServer.tickDepth > 16) + if (scriptServer.tickDepth > 16) { throw new InternalExpressionException("'game_tick' function caused other 'game_tick' functions to run. You should not allow that."); } try { - CarpetServer.scriptServer.tickDepth++; - ((MinecraftServerInterface) server).forceTick(() -> System.nanoTime() - CarpetServer.scriptServer.tickStart < 50000000L); + scriptServer.tickDepth++; + Vanilla.MinecraftServer_forceTick(server, () -> System.nanoTime() - scriptServer.tickStart < 50000000L); if (lv.size() > 0) { final long ms_total = NumericValue.asNumber(lv.get(0)).getLong(); - final long end_expected = CarpetServer.scriptServer.tickStart + ms_total * 1000000L; + final long end_expected = scriptServer.tickStart + ms_total * 1000000L; final long wait = end_expected - System.nanoTime(); if (wait > 0L) { @@ -782,17 +779,17 @@ public class Auxiliary } } } - CarpetServer.scriptServer.tickStart = System.nanoTime(); // for the next tick + scriptServer.tickStart = System.nanoTime(); // for the next tick Thread.yield(); } finally { - if (CarpetServer.scriptServer != null) + if (scriptServer != null) { - CarpetServer.scriptServer.tickDepth--; + scriptServer.tickDepth--; } } - if (CarpetServer.scriptServer != null && CarpetServer.scriptServer.stopAll) + if (scriptServer != null && scriptServer.stopAll) { throw new ExitStatement(Value.NULL); } @@ -811,7 +808,7 @@ public class Auxiliary final BlockArgument locator = BlockArgument.findIn(cc, lv, 0); final BlockPos pos = locator.block.getPos(); final ServerLevel world = cc.level(); - ((ThreadedAnvilChunkStorageInterface) world.getChunkSource().chunkMap).relightChunk(new ChunkPos(pos)); + Vanilla.ChunkMap_relightChunk(world.getChunkSource().chunkMap, new ChunkPos(pos)); WorldTools.forceChunkUpdate(pos, world); return Value.TRUE; }); @@ -896,7 +893,7 @@ public class Auxiliary final long delay = NumericValue.asNumber(lv.get(0)).getLong(); final FunctionArgument functionArgument = FunctionArgument.findIn(c, expression.module, lv, 1, false, false); - CarpetServer.scriptServer.events.scheduleCall( + ((CarpetScriptServer)c.host.scriptServer()).events.scheduleCall( (CarpetContext) c, functionArgument.function, functionArgument.checkedArgs(), @@ -938,14 +935,14 @@ public class Auxiliary expression.addContextFunction("list_files", 2, (c, t, lv) -> { - final FileArgument fdesc = FileArgument.from(lv, true, FileArgument.Reason.READ); + final FileArgument fdesc = FileArgument.from(c, lv, true, FileArgument.Reason.READ); final Stream files = ((CarpetScriptHost) c.host).listFolder(fdesc); return files == null ? Value.NULL : ListValue.wrap(files.map(StringValue::of)); }); expression.addContextFunction("read_file", 2, (c, t, lv) -> { - final FileArgument fdesc = FileArgument.from(lv, false, FileArgument.Reason.READ); + final FileArgument fdesc = FileArgument.from(c, lv, false, FileArgument.Reason.READ); if (fdesc.type == FileArgument.Type.NBT) { final Tag state = ((CarpetScriptHost) c.host).readFileTag(fdesc); @@ -966,14 +963,14 @@ public class Auxiliary }); expression.addContextFunction("delete_file", 2, (c, t, lv) -> - BooleanValue.of(((CarpetScriptHost) c.host).removeResourceFile(FileArgument.from(lv, false, FileArgument.Reason.DELETE)))); + BooleanValue.of(((CarpetScriptHost) c.host).removeResourceFile(FileArgument.from(c, lv, false, FileArgument.Reason.DELETE)))); expression.addContextFunction("write_file", -1, (c, t, lv) -> { if (lv.size() < 3) { throw new InternalExpressionException("'write_file' requires three or more arguments"); } - final FileArgument fdesc = FileArgument.from(lv, false, FileArgument.Reason.CREATE); + final FileArgument fdesc = FileArgument.from(c, lv, false, FileArgument.Reason.CREATE); final boolean success; if (fdesc.type == FileArgument.Type.NBT) @@ -1021,13 +1018,13 @@ public class Auxiliary expression.addContextFunction("load_app_data", -1, (c, t, lv) -> { - FileArgument fdesc = new FileArgument(null, FileArgument.Type.NBT, null, false, false, FileArgument.Reason.READ); + FileArgument fdesc = new FileArgument(null, FileArgument.Type.NBT, null, false, false, FileArgument.Reason.READ, c.host); if (lv.size() > 0) { c.host.issueDeprecation("load_app_data(...) with arguments"); final String resource = recognizeResource(lv.get(0), false); final boolean shared = lv.size() > 1 && lv.get(1).getBoolean(); - fdesc = new FileArgument(resource, FileArgument.Type.NBT, null, false, shared, FileArgument.Reason.READ); + fdesc = new FileArgument(resource, FileArgument.Type.NBT, null, false, shared, FileArgument.Reason.READ, c.host); } return NBTSerializableValue.of(((CarpetScriptHost) c.host).readFileTag(fdesc)); }); @@ -1039,13 +1036,13 @@ public class Auxiliary throw new InternalExpressionException("'store_app_data' needs NBT tag and an optional file"); } final Value val = lv.get(0); - FileArgument fdesc = new FileArgument(null, FileArgument.Type.NBT, null, false, false, FileArgument.Reason.CREATE); + FileArgument fdesc = new FileArgument(null, FileArgument.Type.NBT, null, false, false, FileArgument.Reason.CREATE, c.host); if (lv.size() > 1) { c.host.issueDeprecation("store_app_data(...) with more than one argument"); final String resource = recognizeResource(lv.get(1), false); final boolean shared = lv.size() > 2 && lv.get(2).getBoolean(); - fdesc = new FileArgument(resource, FileArgument.Type.NBT, null, false, shared, FileArgument.Reason.CREATE); + fdesc = new FileArgument(resource, FileArgument.Type.NBT, null, false, shared, FileArgument.Reason.CREATE, c.host); } final NBTSerializableValue tagValue = (val instanceof final NBTSerializableValue nbtsv) ? nbtsv diff --git a/src/main/java/carpet/script/api/Inventories.java b/src/main/java/carpet/script/api/Inventories.java index 93450aea..f4aecd84 100644 --- a/src/main/java/carpet/script/api/Inventories.java +++ b/src/main/java/carpet/script/api/Inventories.java @@ -1,13 +1,12 @@ package carpet.script.api; -import carpet.fakes.IngredientInterface; -import carpet.fakes.RecipeManagerInterface; import carpet.script.CarpetContext; import carpet.script.Expression; import carpet.script.argument.FunctionArgument; import carpet.script.exception.InternalExpressionException; import carpet.script.exception.ThrowStatement; import carpet.script.exception.Throwables; +import carpet.script.external.Vanilla; import carpet.script.utils.InputValidator; import carpet.script.value.BooleanValue; import carpet.script.value.EntityValue; @@ -111,7 +110,7 @@ public class Inventories final String recipeType = lv.get(1).getString(); type = cc.registry(Registries.RECIPE_TYPE).get(InputValidator.identifierOf(recipeType)); } - final List> recipes = ((RecipeManagerInterface) cc.server().getRecipeManager()).getAllMatching(type, InputValidator.identifierOf(recipeName), cc.registryAccess()); + final List> recipes = Vanilla.RecipeManager_getAllMatching(cc.server().getRecipeManager(), type, InputValidator.identifierOf(recipeName), cc.registryAccess()); if (recipes.isEmpty()) { return Value.NULL; @@ -126,7 +125,7 @@ public class Inventories // I am flattening ingredient lists per slot. // consider recipe_data('wooden_sword','crafting') and ('iron_nugget', 'blasting') and notice difference // in depths of lists. - final List> stacks = ((IngredientInterface) (Object) ingredient).getRecipeStacks(); + final List> stacks = Vanilla.Ingredient_getRecipeStacks(ingredient); if (stacks.isEmpty()) { ingredientValue.add(Value.NULL); diff --git a/src/main/java/carpet/script/api/Monitoring.java b/src/main/java/carpet/script/api/Monitoring.java index e32674a2..8acd1f93 100644 --- a/src/main/java/carpet/script/api/Monitoring.java +++ b/src/main/java/carpet/script/api/Monitoring.java @@ -3,13 +3,13 @@ package carpet.script.api; import carpet.script.CarpetContext; import carpet.script.Expression; import carpet.script.exception.InternalExpressionException; +import carpet.script.external.Vanilla; import carpet.script.utils.SystemInfo; import carpet.script.value.ListValue; import carpet.script.value.MapValue; import carpet.script.value.NumericValue; import carpet.script.value.StringValue; import carpet.script.value.Value; -import carpet.utils.SpawnReporter; import it.unimi.dsi.fastutil.objects.Object2IntMap; import java.util.Arrays; @@ -64,7 +64,7 @@ public class Monitoring final Map retDict = new HashMap<>(); for (final MobCategory category : mobcounts.keySet()) { - final int currentCap = category.getMaxInstancesPerChunk() * chunks / SpawnReporter.MAGIC_NUMBER; + final int currentCap = category.getMaxInstancesPerChunk() * chunks / Vanilla.NaturalSpawner_MAGIC_NUMBER(); retDict.put( new StringValue(category.getSerializedName().toLowerCase(Locale.ROOT)), ListValue.of( @@ -82,7 +82,7 @@ public class Monitoring } return ListValue.of( new NumericValue(mobcounts.getInt(cat)), - new NumericValue((int) (cat.getMaxInstancesPerChunk() * chunks / SpawnReporter.MAGIC_NUMBER)) + new NumericValue((int) (cat.getMaxInstancesPerChunk() * chunks / Vanilla.NaturalSpawner_MAGIC_NUMBER())) ); }); } diff --git a/src/main/java/carpet/script/api/Scoreboards.java b/src/main/java/carpet/script/api/Scoreboards.java index f1030d43..2055c831 100644 --- a/src/main/java/carpet/script/api/Scoreboards.java +++ b/src/main/java/carpet/script/api/Scoreboards.java @@ -1,12 +1,11 @@ package carpet.script.api; -import carpet.mixins.Objective_scarpetMixin; -import carpet.mixins.Scoreboard_scarpetMixin; import carpet.script.CarpetContext; import carpet.script.Expression; import carpet.script.exception.InternalExpressionException; import carpet.script.exception.ThrowStatement; import carpet.script.exception.Throwables; +import carpet.script.external.Vanilla; import carpet.script.utils.InputValidator; import carpet.script.value.BooleanValue; import carpet.script.value.EntityValue; @@ -164,9 +163,9 @@ public class Scoreboards { return Value.NULL; } - ((Scoreboard_scarpetMixin) scoreboard).getObjectivesByCriterion().get(objective.getCriteria()).remove(objective); - ((Objective_scarpetMixin) objective).setCriterion(criterion); - (((Scoreboard_scarpetMixin) scoreboard).getObjectivesByCriterion().computeIfAbsent(criterion, (criterion1) -> Lists.newArrayList())).add(objective); + Vanilla.Scoreboard_getObjectivesByCriterion(scoreboard).get(objective.getCriteria()).remove(objective); + Vanilla.Objective_setCriterion(objective, criterion); + (Vanilla.Scoreboard_getObjectivesByCriterion(scoreboard).computeIfAbsent(criterion, (criterion1) -> Lists.newArrayList())).add(objective); scoreboard.onObjectiveAdded(objective); return Value.FALSE; } @@ -209,9 +208,9 @@ public class Scoreboards { return Value.FALSE; } - ((Scoreboard_scarpetMixin) scoreboard).getObjectivesByCriterion().get(objective.getCriteria()).remove(objective); - ((Objective_scarpetMixin) objective).setCriterion(criterion); - (((Scoreboard_scarpetMixin) scoreboard).getObjectivesByCriterion().computeIfAbsent(criterion, (criterion1) -> Lists.newArrayList())).add(objective); + Vanilla.Scoreboard_getObjectivesByCriterion(scoreboard).get(objective.getCriteria()).remove(objective); + Vanilla.Objective_setCriterion(objective, criterion); + (Vanilla.Scoreboard_getObjectivesByCriterion(scoreboard).computeIfAbsent(criterion, (criterion1) -> Lists.newArrayList())).add(objective); scoreboard.onObjectiveAdded(objective); return Value.TRUE; } diff --git a/src/main/java/carpet/script/api/WorldAccess.java b/src/main/java/carpet/script/api/WorldAccess.java index 5900a3ee..4e7112d9 100644 --- a/src/main/java/carpet/script/api/WorldAccess.java +++ b/src/main/java/carpet/script/api/WorldAccess.java @@ -1,21 +1,14 @@ package carpet.script.api; -import carpet.CarpetSettings; -import carpet.fakes.ChunkGeneratorInterface; -import carpet.fakes.ChunkTicketManagerInterface; -import carpet.fakes.RandomStateVisitorAccessor; -import carpet.fakes.ServerChunkManagerInterface; -import carpet.fakes.ServerWorldInterface; -import carpet.fakes.SpawnHelperInnerInterface; -import carpet.fakes.ThreadedAnvilChunkStorageInterface; -import carpet.helpers.FeatureGenerator; -import carpet.mixins.PoiRecord_scarpetMixin; import carpet.script.CarpetContext; +import carpet.script.CarpetScriptServer; import carpet.script.Context; import carpet.script.Expression; import carpet.script.Fluff; -import carpet.script.annotation.Locator; -import carpet.script.annotation.ScarpetFunction; +import carpet.script.external.Carpet; +import carpet.script.external.Vanilla; +import carpet.script.utils.FeatureGenerator; +import carpet.mixins.PoiRecord_scarpetMixin; import carpet.script.argument.BlockArgument; import carpet.script.argument.Vector3Argument; import carpet.script.exception.InternalExpressionException; @@ -34,7 +27,6 @@ import carpet.script.value.NumericValue; import carpet.script.value.StringValue; import carpet.script.value.Value; import carpet.script.value.ValueConversions; -import carpet.utils.BlockInfo; import com.mojang.brigadier.exceptions.CommandSyntaxException; import it.unimi.dsi.fastutil.longs.Long2ObjectOpenHashMap; @@ -48,6 +40,11 @@ import net.minecraft.core.QuartPos; import net.minecraft.core.Registry; import net.minecraft.core.registries.Registries; import net.minecraft.resources.ResourceKey; +import net.minecraft.server.level.DistanceManager; +import net.minecraft.server.level.ServerLevel; +import net.minecraft.server.level.ServerPlayer; +import net.minecraft.server.level.Ticket; +import net.minecraft.server.level.TicketType; import net.minecraft.tags.TagKey; import net.minecraft.world.level.chunk.ChunkGenerator; import net.minecraft.world.level.chunk.PalettedContainer; @@ -59,7 +56,6 @@ import net.minecraft.world.level.levelgen.RandomState; import net.minecraft.world.level.levelgen.structure.Structure; import net.minecraft.world.level.levelgen.structure.StructureType; import org.apache.commons.lang3.tuple.Pair; -import org.jetbrains.annotations.Nullable; import java.util.ArrayList; import java.util.Arrays; @@ -82,10 +78,6 @@ import net.minecraft.nbt.CompoundTag; import net.minecraft.nbt.Tag; import net.minecraft.network.protocol.game.ClientboundExplodePacket; import net.minecraft.resources.ResourceLocation; -import net.minecraft.server.level.ServerLevel; -import net.minecraft.server.level.ServerPlayer; -import net.minecraft.server.level.Ticket; -import net.minecraft.server.level.TicketType; import net.minecraft.sounds.SoundSource; import net.minecraft.util.Mth; import net.minecraft.util.SortedArraySet; @@ -135,6 +127,8 @@ import net.minecraft.world.level.pathfinder.PathComputationType; import net.minecraft.world.level.storage.ServerLevelData; import net.minecraft.world.phys.Vec3; +import javax.annotation.Nullable; + import static carpet.script.utils.WorldTools.canHasChunk; public class WorldAccess @@ -256,7 +250,7 @@ public class WorldAccess { synchronized (level) { - ((ChunkGeneratorInterface) level.getChunkSource().getGenerator()).initStrongholds(level); + level.getChunkSource().getGeneratorState().ensureStructuresGenerated(); } } @@ -444,7 +438,7 @@ public class WorldAccess } final Value weather = lv.get(0); - final ServerLevelData worldProperties = ((ServerWorldInterface) world).getWorldPropertiesCM(); + final ServerLevelData worldProperties = Vanilla.ServerLevel_getWorldProperties(world); if (lv.size() == 1) { return new NumericValue(switch (weather.getString().toLowerCase(Locale.ROOT)) @@ -644,10 +638,9 @@ public class WorldAccess expression.addContextFunction("chunk_tickets", -1, (c, t, lv) -> { final ServerLevel world = ((CarpetContext) c).level(); - final Long2ObjectOpenHashMap>> levelTickets = ( - (ChunkTicketManagerInterface) ((ServerChunkManagerInterface) world.getChunkSource()) - .getCMTicketManager() - ).getTicketsByPosition(); + DistanceManager foo = Vanilla.ServerChunkCache_getCMTicketManager(world.getChunkSource()); + final Long2ObjectOpenHashMap>> levelTickets = Vanilla.ChunkTicketManager_getTicketsByPosition(foo); + final List res = new ArrayList<>(); if (lv.size() == 0) { @@ -723,22 +716,23 @@ public class WorldAccess // lazy cause its parked execution expression.addLazyFunction("without_updates", 1, (c, t, lv) -> { - final boolean previous = CarpetSettings.impendingFillSkipUpdates.get(); - if (previous) + if (Carpet.getImpendingFillSkipUpdates().get()) { return lv.get(0); } final Value[] result = new Value[]{Value.NULL}; ((CarpetContext) c).server().executeBlocking(() -> { + final ThreadLocal skipUpdates = Carpet.getImpendingFillSkipUpdates(); + final boolean previous = skipUpdates.get(); try { - CarpetSettings.impendingFillSkipUpdates.set(true); + skipUpdates.set(true); result[0] = lv.get(0).evalValue(c, t); } finally { - CarpetSettings.impendingFillSkipUpdates.set(false); + skipUpdates.set(previous); } }); return (cc, tt) -> result[0]; @@ -1080,7 +1074,9 @@ public class WorldAccess final Explosion explosion = new Explosion(cc.level(), source, null, null, pos.x, pos.y, pos.z, powah, createFire, mode) { @Override - public @Nullable LivingEntity getIndirectSourceEntity() + @Nullable + public + LivingEntity getIndirectSourceEntity() { return theAttacker; } @@ -1168,15 +1164,15 @@ public class WorldAccess expression.addContextFunction("block_sound", -1, (c, t, lv) -> stateStringQuery(c, "block_sound", lv, (s, p) -> - BlockInfo.soundName.get(s.getSoundType()))); + Carpet.getSoundTypeNames().get(s.getSoundType()))); expression.addContextFunction("material", -1, (c, t, lv) -> stateStringQuery(c, "material", lv, (s, p) -> - BlockInfo.materialName.get(s.getMaterial()))); + Carpet.getMaterialNames().get(s.getMaterial()))); expression.addContextFunction("map_colour", -1, (c, t, lv) -> stateStringQuery(c, "map_colour", lv, (s, p) -> - BlockInfo.mapColourName.get(s.getMapColor(((CarpetContext) c).level(), p)))); + Carpet.getMapColorNames().get(s.getMapColor(((CarpetContext) c).level(), p)))); // Deprecated for block_state() @@ -1485,7 +1481,7 @@ public class WorldAccess } catch (final NullPointerException npe) { - CarpetSettings.LOG.error("Failed to detect structure: " + reg.getKey(str)); + CarpetScriptServer.LOG.error("Failed to detect structure: " + reg.getKey(str)); start = null; } @@ -1649,7 +1645,7 @@ public class WorldAccess final Value[] result = new Value[]{Value.NULL}; ((CarpetContext) c).server().executeBlocking(() -> { - final Map report = ((ThreadedAnvilChunkStorageInterface) world.getChunkSource().chunkMap).regenerateChunkRegion(requestedChunks); + final Map report = Vanilla.ChunkMap_regenerateChunkRegion(world.getChunkSource().chunkMap, requestedChunks); result[0] = MapValue.wrap(report.entrySet().stream().collect(Collectors.toMap( e -> new StringValue(e.getKey()), e -> new NumericValue(e.getValue()) @@ -1677,9 +1673,7 @@ public class WorldAccess required_charge = NumericValue.asNumber(lv.get(locator.offset)).getDouble(); } final NaturalSpawner.SpawnState charger = cc.level().getChunkSource().getLastSpawnState(); - return charger == null ? Value.NULL : new NumericValue( - ((SpawnHelperInnerInterface) charger).getPotentialCalculator(). - getPotentialEnergyChange(pos, required_charge) + return charger == null ? Value.NULL : new NumericValue(Vanilla.SpawnState_getPotentialCalculator(charger).getPotentialEnergyChange(pos, required_charge) ); }); @@ -1809,7 +1803,7 @@ public class WorldAccess noiseBasedChunkGenerator.generatorSettings().value(), level.registryAccess().lookupOrThrow(Registries.NOISE), level.getSeed() ); - DensityFunction.Visitor visitor = ((RandomStateVisitorAccessor) (Object) randomState).getVisitor(); + DensityFunction.Visitor visitor = Vanilla.RandomState_getVisitor(randomState); return densityFunction.mapAll(visitor); } diff --git a/src/main/java/carpet/script/argument/FileArgument.java b/src/main/java/carpet/script/argument/FileArgument.java index 835c61ab..57e75f88 100644 --- a/src/main/java/carpet/script/argument/FileArgument.java +++ b/src/main/java/carpet/script/argument/FileArgument.java @@ -1,8 +1,9 @@ package carpet.script.argument; -import carpet.CarpetServer; import carpet.script.CarpetScriptServer; +import carpet.script.Context; import carpet.script.Module; +import carpet.script.ScriptHost; import carpet.script.exception.InternalExpressionException; import carpet.script.exception.ThrowStatement; import carpet.script.exception.Throwables; @@ -18,7 +19,6 @@ import net.minecraft.nbt.NbtAccounter; import net.minecraft.nbt.NbtIo; import net.minecraft.nbt.Tag; import net.minecraft.nbt.TagTypes; -import net.minecraft.world.level.storage.LevelResource; import org.apache.commons.io.FilenameUtils; import org.apache.commons.lang3.tuple.Pair; @@ -58,6 +58,7 @@ public class FileArgument public Reason reason; private FileSystem zfs; private Path zipPath; + private ScriptHost host; public static final Object writeIOSync = new Object(); @@ -103,7 +104,7 @@ public class FileArgument READ, CREATE, DELETE } - public FileArgument(final String resource, final Type type, final String zipContainer, final boolean isFolder, final boolean isShared, final Reason reason) + public FileArgument(final String resource, final Type type, final String zipContainer, final boolean isFolder, final boolean isShared, final Reason reason, final ScriptHost host) { this.resource = resource; this.type = type; @@ -113,6 +114,7 @@ public class FileArgument this.reason = reason; this.zfs = null; this.zipPath = null; + this.host = host; } @Override @@ -121,7 +123,7 @@ public class FileArgument return "path: " + resource + " zip: " + zipContainer + " type: " + type.id + " folder: " + isFolder + " shared: " + isShared + " reason: " + reason.toString(); } - public static FileArgument from(final List lv, final boolean isFolder, final Reason reason) + public static FileArgument from(final Context context, final List lv, final boolean isFolder, final Reason reason) { if (lv.size() < 2) { @@ -140,14 +142,14 @@ public class FileArgument { throw new InternalExpressionException("Folder types are no supported for this IO function"); } - return new FileArgument(resource.getLeft(), type, resource.getRight(), isFolder, shared, reason); + return new FileArgument(resource.getLeft(), type, resource.getRight(), isFolder, shared, reason, context.host); } - public static FileArgument resourceFromPath(final String path, final Reason reason, final boolean shared) + public static FileArgument resourceFromPath(final ScriptHost host, final String path, final Reason reason, final boolean shared) { final Pair resource = recognizeResource(path, false, Type.ANY); - return new FileArgument(resource.getLeft(), Type.ANY, resource.getRight(), false, shared, reason); + return new FileArgument(resource.getLeft(), Type.ANY, resource.getRight(), false, shared, reason, host); } public static Pair recognizeResource(final String origfile, final boolean isFolder, final Type type) @@ -196,11 +198,7 @@ public class FileArgument private Path resolve(final String suffix) { - if (CarpetServer.minecraft_server == null) - { - throw new InternalExpressionException("Accessing world files without server running"); - } - return CarpetServer.minecraft_server.getWorldPath(LevelResource.ROOT).resolve("scripts/" + suffix); + return host.resolveScriptFile(suffix); } private Path toPath(final Module module) diff --git a/src/main/java/carpet/script/command/CommandArgument.java b/src/main/java/carpet/script/command/CommandArgument.java index f0619c74..e6d2a307 100644 --- a/src/main/java/carpet/script/command/CommandArgument.java +++ b/src/main/java/carpet/script/command/CommandArgument.java @@ -1,9 +1,10 @@ package carpet.script.command; -import carpet.CarpetServer; -import carpet.fakes.BlockStateArgumentInterface; import carpet.script.CarpetScriptHost; +import carpet.script.CarpetScriptServer; import carpet.script.argument.FunctionArgument; +import carpet.script.external.Carpet; +import carpet.script.external.Vanilla; import carpet.script.value.BlockValue; import carpet.script.value.BooleanValue; import carpet.script.value.EntityValue; @@ -15,8 +16,6 @@ import carpet.script.value.NumericValue; import carpet.script.value.StringValue; import carpet.script.value.Value; import carpet.script.value.ValueConversions; -import carpet.utils.CarpetProfiler; -import com.mojang.brigadier.exceptions.DynamicCommandExceptionType; import com.mojang.datafixers.util.Either; import it.unimi.dsi.fastutil.ints.IntOpenHashSet; import it.unimi.dsi.fastutil.ints.IntSet; @@ -134,7 +133,7 @@ public abstract class CommandArgument new VanillaUnconfigurableArgument("block", BlockStateArgument::block, (c, p) -> { BlockInput result = BlockStateArgument.getBlock(c, p); - return new BlockValue(result.getState(), c.getSource().getLevel(), null, ((BlockStateArgumentInterface) result).getCMTag()); + return new BlockValue(result.getState(), c.getSource().getLevel(), null, Vanilla.BlockInput_getTag(result)); }, param -> (ctx, builder) -> ctx.getArgument(param, BlockStateArgument.class).listSuggestions(ctx, builder) ), @@ -318,8 +317,9 @@ public abstract class CommandArgument return argument(param, arg.getArgumentType(host)); } final String hostName = host.getName(); + final CarpetScriptServer scriptServer = host.scriptServer(); return argument(param, arg.getArgumentType(host)).suggests((ctx, b) -> { - final CarpetScriptHost cHost = CarpetServer.scriptServer.modules.get(hostName).retrieveOwnForExecution(ctx.getSource()); + final CarpetScriptHost cHost = scriptServer.modules.get(hostName).retrieveOwnForExecution(ctx.getSource()); return arg.suggest(ctx, b, cHost); }); } @@ -426,7 +426,7 @@ public abstract class CommandArgument { if (customSuggester != null) { - final CarpetProfiler.ProfilerToken currentSection = CarpetProfiler.start_section(null, "Scarpet command", CarpetProfiler.TYPE.GENERAL); + final Runnable currentSection = Carpet.startProfilerSection("Scarpet command"); final Map params = new HashMap<>(); for (final ParsedCommandNode pnode : context.getNodes()) { @@ -445,7 +445,7 @@ public abstract class CommandArgument throw error("Custom suggester should return a list of options" + " for custom type " + suffix); } final Collection res = ((ListValue) response).getItems().stream().map(Value::getString).collect(Collectors.toList()); - CarpetProfiler.end_current_section(currentSection); + currentSection.run(); return res; } return needsMatching ? examples : Collections.singletonList("... " + getTypeSuffix()); diff --git a/src/main/java/carpet/script/exception/CarpetExpressionException.java b/src/main/java/carpet/script/exception/CarpetExpressionException.java index 4ca5d115..8e541754 100644 --- a/src/main/java/carpet/script/exception/CarpetExpressionException.java +++ b/src/main/java/carpet/script/exception/CarpetExpressionException.java @@ -1,7 +1,7 @@ package carpet.script.exception; +import carpet.script.external.Carpet; import carpet.script.value.FunctionValue; -import carpet.utils.Messenger; import java.util.List; @@ -23,7 +23,7 @@ public class CarpetExpressionException extends StacklessRuntimeException impleme { for (final FunctionValue fun : stack) { - Messenger.m(source, "e ... in " + fun.fullName(), "e /" + (fun.getToken().lineno + 1) + ":" + (fun.getToken().linepos + 1)); + Carpet.Messenger_message(source, "e ... in " + fun.fullName(), "e /" + (fun.getToken().lineno + 1) + ":" + (fun.getToken().linepos + 1)); } } } diff --git a/src/main/java/carpet/script/exception/ExpressionException.java b/src/main/java/carpet/script/exception/ExpressionException.java index 71048589..6a2cb1f4 100644 --- a/src/main/java/carpet/script/exception/ExpressionException.java +++ b/src/main/java/carpet/script/exception/ExpressionException.java @@ -3,8 +3,8 @@ package carpet.script.exception; import carpet.script.Context; import carpet.script.Expression; import carpet.script.Tokenizer; +import carpet.script.external.Carpet; import carpet.script.value.FunctionValue; -import carpet.utils.Messenger; import java.util.ArrayList; import java.util.Collections; @@ -22,7 +22,7 @@ public class ExpressionException extends StacklessRuntimeException implements Re public static void prepareForDoom() { - Messenger.c("foo bar"); + Carpet.Messenger_compose("foo bar"); } public ExpressionException(final Context c, final Expression e, final String message) diff --git a/src/main/java/carpet/script/exception/StacklessRuntimeException.java b/src/main/java/carpet/script/exception/StacklessRuntimeException.java index 5f0f473e..1d6b6504 100644 --- a/src/main/java/carpet/script/exception/StacklessRuntimeException.java +++ b/src/main/java/carpet/script/exception/StacklessRuntimeException.java @@ -3,7 +3,7 @@ package carpet.script.exception; /** * A type of {@link RuntimeException} that doesn't spend time producing and filling a stacktrace */ -abstract class StacklessRuntimeException extends RuntimeException +public abstract class StacklessRuntimeException extends RuntimeException { public StacklessRuntimeException() { diff --git a/src/main/java/carpet/script/external/Carpet.java b/src/main/java/carpet/script/external/Carpet.java new file mode 100644 index 00000000..1afd982a --- /dev/null +++ b/src/main/java/carpet/script/external/Carpet.java @@ -0,0 +1,181 @@ +package carpet.script.external; + +import carpet.CarpetServer; +import carpet.CarpetSettings; +import carpet.api.settings.CarpetRule; +import carpet.api.settings.RuleHelper; +import carpet.api.settings.SettingsManager; +import carpet.api.settings.Validator; +import carpet.fakes.MinecraftServerInterface; +import carpet.helpers.TickSpeed; +import carpet.logging.HUDController; +import carpet.network.ServerNetworkHandler; +import carpet.patches.EntityPlayerMPFake; +import carpet.script.CarpetExpression; +import carpet.script.CarpetScriptServer; +import carpet.script.utils.AppStoreManager; +import carpet.script.value.MapValue; +import carpet.script.value.StringValue; +import carpet.utils.BlockInfo; +import carpet.utils.CarpetProfiler; +import carpet.utils.Messenger; +import net.minecraft.commands.CommandSourceStack; +import net.minecraft.network.chat.Component; +import net.minecraft.server.MinecraftServer; +import net.minecraft.server.level.ServerPlayer; +import net.minecraft.world.entity.player.Player; +import net.minecraft.world.level.block.SoundType; +import net.minecraft.world.level.material.Material; +import net.minecraft.world.level.material.MaterialColor; + +import javax.annotation.Nullable; +import java.util.Collection; +import java.util.Collections; +import java.util.List; +import java.util.Map; + +public class Carpet +{ + public static Map getScarpetHeaders() + { + return HUDController.scarpet_headers; + } + + public static Map getScarpetFooters() + { + return HUDController.scarpet_footers; + } + + public static void updateScarpetHUDs(final MinecraftServer server, final List players) + { + HUDController.update_hud(server, players); + } + + public static Component Messenger_compose(final Object... messages) + { + return Messenger.c(messages); + } + + public static void Messenger_message(final CommandSourceStack source, final Object... messages) + { + Messenger.m(source, messages); + } + + public static ThreadLocal getImpendingFillSkipUpdates() + { + return CarpetSettings.impendingFillSkipUpdates; + } + + public static Map getSoundTypeNames() + { + return BlockInfo.soundName; + } + + public static Map getMapColorNames() + { + return BlockInfo.mapColourName; + } + + public static Map getMaterialNames() + { + return BlockInfo.materialName; + } + + public static Runnable startProfilerSection(final String name) + { + final CarpetProfiler.ProfilerToken token = CarpetProfiler.start_section(null, name, CarpetProfiler.TYPE.GENERAL); + return () -> CarpetProfiler.end_current_section(token); + } + + public static void MinecraftServer_addScriptServer(final MinecraftServer server, final CarpetScriptServer scriptServer) + { + ((MinecraftServerInterface) server).addScriptServer(scriptServer); + } + + public static boolean isValidCarpetPlayer(final ServerPlayer player) + { + return ServerNetworkHandler.isValidCarpetPlayer(player); + } + + public static String getPlayerStatus(final ServerPlayer player) + { + return ServerNetworkHandler.getPlayerStatus(player); + } + + public static MapValue getAllCarpetRules() + { + final Collection> rules = CarpetServer.settingsManager.getCarpetRules(); + final MapValue carpetRules = new MapValue(Collections.emptyList()); + rules.forEach(rule -> carpetRules.put(new StringValue(rule.name()), new StringValue(RuleHelper.toRuleString(rule.value())))); + CarpetServer.extensions.forEach(e -> { + final SettingsManager manager = e.extensionSettingsManager(); + if (manager == null) + { + return; + } + manager.getCarpetRules().forEach(rule -> carpetRules.put(new StringValue(manager.identifier() + ":" + rule.name()), new StringValue(RuleHelper.toRuleString(rule.value())))); + }); + return carpetRules; + } + + public static String getCarpetVersion() + { + return CarpetSettings.carpetVersion; + } + + @Nullable + public static String isModdedPlayer(final Player p) + { + if (p instanceof final EntityPlayerMPFake fake) + { + return fake.isAShadow ? "shadow" : "fake"; + } + return null; + } + + public static boolean isTickProcessingPaused() + { + return !TickSpeed.process_entities; + } + + public static void handleExtensionsAPI(final CarpetExpression expression) + { + CarpetServer.extensions.forEach(e -> e.scarpetApi(expression)); + } + + public static boolean getFillUpdates() + { + return CarpetSettings.fillUpdates; + } + + public static class ScarpetAppStoreValidator extends Validator + { + @Override + public String validate(final CommandSourceStack source, final CarpetRule currentRule, String newValue, final String stringInput) + { + if (newValue.equals(currentRule.value())) + { + // Don't refresh the local repo if it's the same (world change), helps preventing hitting rate limits from github when + // getting suggestions. Pending is a way to invalidate the cache when it gets old, and investigating api usage further + return newValue; + } + if (newValue.equalsIgnoreCase("none")) + { + AppStoreManager.setScarpetRepoLink(null); + return newValue; + } + if (newValue.endsWith("/")) + { + newValue = newValue.replaceAll("/$", ""); + } + AppStoreManager.setScarpetRepoLink("https://api.github.com/repos/" + newValue + "/"); + return newValue; + } + + @Override + public String description() + { + return "Appstore link should point to a valid github repository"; + } + } +} diff --git a/src/main/java/carpet/script/external/Vanilla.java b/src/main/java/carpet/script/external/Vanilla.java new file mode 100644 index 00000000..64585200 --- /dev/null +++ b/src/main/java/carpet/script/external/Vanilla.java @@ -0,0 +1,364 @@ +package carpet.script.external; + +import carpet.CarpetSettings; +import carpet.fakes.BiomeInterface; +import carpet.fakes.BlockPredicateInterface; +import carpet.fakes.BlockStateArgumentInterface; +import carpet.fakes.ChunkTicketManagerInterface; +import carpet.fakes.CommandDispatcherInterface; +import carpet.fakes.EntityInterface; +import carpet.fakes.IngredientInterface; +import carpet.fakes.InventoryBearerInterface; +import carpet.fakes.ItemEntityInterface; +import carpet.fakes.LivingEntityInterface; +import carpet.fakes.MinecraftServerInterface; +import carpet.fakes.MobEntityInterface; +import carpet.fakes.RandomStateVisitorAccessor; +import carpet.fakes.RecipeManagerInterface; +import carpet.fakes.AbstractContainerMenuInterface; +import carpet.fakes.ServerChunkManagerInterface; +import carpet.fakes.ServerPlayerInterface; +import carpet.fakes.ServerPlayerInteractionManagerInterface; +import carpet.fakes.ServerWorldInterface; +import carpet.fakes.SpawnHelperInnerInterface; +import carpet.fakes.ThreadedAnvilChunkStorageInterface; +import carpet.mixins.Objective_scarpetMixin; +import carpet.mixins.Scoreboard_scarpetMixin; +import carpet.network.ServerNetworkHandler; +import carpet.script.CarpetScriptServer; +import carpet.script.EntityEventsGroup; +import carpet.script.value.MapValue; +import carpet.script.value.StringValue; +import carpet.script.value.Value; +import carpet.utils.CommandHelper; +import carpet.utils.SpawnReporter; +import com.mojang.brigadier.CommandDispatcher; +import it.unimi.dsi.fastutil.longs.Long2ObjectOpenHashMap; +import net.fabricmc.loader.api.FabricLoader; +import net.fabricmc.loader.api.ModContainer; +import net.minecraft.commands.CommandSourceStack; +import net.minecraft.commands.arguments.blocks.BlockInput; +import net.minecraft.core.BlockPos; +import net.minecraft.core.RegistryAccess; +import net.minecraft.nbt.CompoundTag; +import net.minecraft.nbt.Tag; +import net.minecraft.resources.ResourceLocation; +import net.minecraft.server.MinecraftServer; +import net.minecraft.server.level.ChunkMap; +import net.minecraft.server.level.DistanceManager; +import net.minecraft.server.level.ServerChunkCache; +import net.minecraft.server.level.ServerLevel; +import net.minecraft.server.level.ServerPlayer; +import net.minecraft.server.level.ServerPlayerGameMode; +import net.minecraft.server.level.Ticket; +import net.minecraft.tags.TagKey; +import net.minecraft.util.SortedArraySet; +import net.minecraft.world.Container; +import net.minecraft.world.entity.Entity; +import net.minecraft.world.entity.LivingEntity; +import net.minecraft.world.entity.Mob; +import net.minecraft.world.entity.ai.goal.Goal; +import net.minecraft.world.entity.ai.goal.GoalSelector; +import net.minecraft.world.entity.animal.horse.AbstractHorse; +import net.minecraft.world.entity.item.ItemEntity; +import net.minecraft.world.inventory.AbstractContainerMenu; +import net.minecraft.world.inventory.DataSlot; +import net.minecraft.world.item.ItemStack; +import net.minecraft.world.item.crafting.Ingredient; +import net.minecraft.world.item.crafting.Recipe; +import net.minecraft.world.item.crafting.RecipeManager; +import net.minecraft.world.item.crafting.RecipeType; +import net.minecraft.world.level.ChunkPos; +import net.minecraft.world.level.GameRules; +import net.minecraft.world.level.NaturalSpawner; +import net.minecraft.world.level.PotentialCalculator; +import net.minecraft.world.level.biome.Biome; +import net.minecraft.world.level.block.Block; +import net.minecraft.world.level.block.state.BlockState; +import net.minecraft.world.level.block.state.pattern.BlockInWorld; +import net.minecraft.world.level.levelgen.DensityFunction; +import net.minecraft.world.level.levelgen.RandomState; +import net.minecraft.world.level.storage.LevelStorageSource; +import net.minecraft.world.level.storage.ServerLevelData; +import net.minecraft.world.scores.Objective; +import net.minecraft.world.scores.Scoreboard; +import net.minecraft.world.scores.criteria.ObjectiveCriteria; + +import java.util.Collection; +import java.util.HashMap; +import java.util.List; +import java.util.Map; +import java.util.function.BooleanSupplier; +import java.util.function.Predicate; + +public class Vanilla +{ + public static void MinecraftServer_forceTick(final MinecraftServer server, final BooleanSupplier sup) + { + ((MinecraftServerInterface) server).forceTick(sup); + } + + public static void ChunkMap_relightChunk(final ChunkMap chunkMap, final ChunkPos pos) + { + ((ThreadedAnvilChunkStorageInterface) chunkMap).relightChunk(pos); + } + + public static Map ChunkMap_regenerateChunkRegion(final ChunkMap chunkMap, final List requestedChunks) + { + return ((ThreadedAnvilChunkStorageInterface) chunkMap).regenerateChunkRegion(requestedChunks); + } + + public static List> Ingredient_getRecipeStacks(final Ingredient ingredient) + { + return ((IngredientInterface) (Object) ingredient).getRecipeStacks(); + } + + public static List> RecipeManager_getAllMatching(final RecipeManager recipeManager, final RecipeType type, final ResourceLocation output, final RegistryAccess registryAccess) + { + return ((RecipeManagerInterface) recipeManager).getAllMatching(type, output, registryAccess); + } + + public static int NaturalSpawner_MAGIC_NUMBER() + { + return SpawnReporter.MAGIC_NUMBER; + } + + public static PotentialCalculator SpawnState_getPotentialCalculator(final NaturalSpawner.SpawnState spawnState) + { + return ((SpawnHelperInnerInterface) spawnState).getPotentialCalculator(); + } + + public static void Objective_setCriterion(final Objective objective, final ObjectiveCriteria criterion) + { + ((Objective_scarpetMixin) objective).setCriterion(criterion); + } + + public static Map> Scoreboard_getObjectivesByCriterion(final Scoreboard scoreboard) + { + return ((Scoreboard_scarpetMixin) scoreboard).getObjectivesByCriterion(); + } + + public static ServerLevelData ServerLevel_getWorldProperties(final ServerLevel world) + { + return ((ServerWorldInterface) world).getWorldPropertiesCM(); + } + + public static DistanceManager ServerChunkCache_getCMTicketManager(final ServerChunkCache chunkCache) + { + return ((ServerChunkManagerInterface) chunkCache).getCMTicketManager(); + } + + public static Long2ObjectOpenHashMap>> ChunkTicketManager_getTicketsByPosition(final DistanceManager ticketManager) + { + return ((ChunkTicketManagerInterface) ticketManager).getTicketsByPosition(); + } + + public static DensityFunction.Visitor RandomState_getVisitor(final RandomState randomState) + { + return ((RandomStateVisitorAccessor) (Object) randomState).getVisitor(); + } + + public static CompoundTag BlockInput_getTag(final BlockInput blockInput) + { + return ((BlockStateArgumentInterface) blockInput).getCMTag(); + } + + public static CarpetScriptServer MinecraftServer_getScriptServer(final MinecraftServer server) + { + return ((MinecraftServerInterface) server).getScriptServer(); + } + + public static Biome.ClimateSettings Biome_getClimateSettings(final Biome biome) + { + return ((BiomeInterface) (Object) biome).getClimateSettings(); + } + + public static ThreadLocal skipGenerationChecks(final ServerLevel level) + { // not sure does vanilla care at all - needs checking + return CarpetSettings.skipGenerationChecks; + } + + public static void sendScarpetShapesDataToPlayer(final ServerPlayer player, final Tag data) + { // dont forget to add the packet to vanilla packed handler and call ShapesRenderer.addShape to handle on client + ServerNetworkHandler.sendCustomCommand(player, "scShapes", data); + } + + public static int MinecraftServer_getRunPermissionLevel(final MinecraftServer server) + { + return CarpetSettings.runPermissionLevel; + } + + public static String MinecraftServer_getReleaseTarget(final MinecraftServer server) + { + return CarpetSettings.releaseTarget; + } + + public static boolean isDevelopmentEnvironment() + { + return FabricLoader.getInstance().isDevelopmentEnvironment(); + } + + public static MapValue getServerMods(final MinecraftServer server) + { + final Map ret = new HashMap<>(); + for (final ModContainer mod : FabricLoader.getInstance().getAllMods()) + { + ret.put(new StringValue(mod.getMetadata().getId()), new StringValue(mod.getMetadata().getVersion().getFriendlyString())); + } + return MapValue.wrap(ret); + } + + public static LevelStorageSource.LevelStorageAccess MinecraftServer_storageSource(final MinecraftServer server) + { + return ((MinecraftServerInterface) server).getCMSession(); + } + + public static BlockPos ServerPlayerGameMode_getCurrentBlockPosition(final ServerPlayerGameMode gameMode) + { + return ((ServerPlayerInteractionManagerInterface) gameMode).getCurrentBreakingBlock(); + } + + public static int ServerPlayerGameMode_getCurrentBlockBreakingProgress(final ServerPlayerGameMode gameMode) + { + return ((ServerPlayerInteractionManagerInterface) gameMode).getCurrentBlockBreakingProgress(); + } + + public static void ServerPlayerGameMode_setBlockBreakingProgress(final ServerPlayerGameMode gameMode, final int progress) + { + ((ServerPlayerInteractionManagerInterface) gameMode).setBlockBreakingProgress(progress); + } + + public static boolean ServerPlayer_isInvalidEntityObject(final ServerPlayer player) + { + return ((ServerPlayerInterface) player).isInvalidEntityObject(); + } + + public static String ServerPlayer_getLanguage(final ServerPlayer player) + { + return ((ServerPlayerInterface) player).getLanguage(); + } + + public static GoalSelector Mob_getAI(final Mob mob, final boolean target) + { + return ((MobEntityInterface) mob).getAI(target); + } + + public static Map Mob_getTemporaryTasks(final Mob mob) + { + return ((MobEntityInterface) mob).getTemporaryTasks(); + } + + public static void Mob_setPersistence(final Mob mob, final boolean what) + { + ((MobEntityInterface) mob).setPersistence(what); + } + + public static EntityEventsGroup Entity_getEventContainer(final Entity entity) + { + return ((EntityInterface) entity).getEventContainer(); + } + + public static boolean Entity_isPermanentVehicle(final Entity entity) + { + return ((EntityInterface) entity).isPermanentVehicle(); + } + + public static void Entity_setPermanentVehicle(final Entity entity, final boolean permanent) + { + ((EntityInterface) entity).setPermanentVehicle(permanent); + } + + public static int Entity_getPortalTimer(final Entity entity) + { + return ((EntityInterface) entity).getPortalTimer(); + } + + public static void Entity_setPortalTimer(final Entity entity, final int amount) + { + ((EntityInterface) entity).setPortalTimer(amount); + } + + public static int Entity_getPublicNetherPortalCooldown(final Entity entity) + { + return ((EntityInterface) entity).getPublicNetherPortalCooldown(); + } + + public static void Entity_setPublicNetherPortalCooldown(final Entity entity, final int what) + { + ((EntityInterface) entity).setPublicNetherPortalCooldown(what); + } + + public static int ItemEntity_getPickupDelay(final ItemEntity entity) + { + return ((ItemEntityInterface) entity).getPickupDelayCM(); + } + + public static boolean LivingEntity_isJumping(final LivingEntity entity) + { + return ((LivingEntityInterface) entity).isJumpingCM(); + } + + public static void LivingEntity_setJumping(final LivingEntity entity) + { + ((LivingEntityInterface) entity).doJumpCM(); + } + + public static Container AbstractHorse_getInventory(final AbstractHorse horse) + { + return ((InventoryBearerInterface) horse).getCMInventory(); + } + + public static DataSlot AbstractContainerMenu_getDataSlot(final AbstractContainerMenu handler, final int index) + { + return ((AbstractContainerMenuInterface) handler).getDataSlot(index); + } + + public static void CommandDispatcher_unregisterCommand(final CommandDispatcher dispatcher, final String name) + { + ((CommandDispatcherInterface) dispatcher).carpet$unregister(name); + } + + public static boolean MinecraftServer_doScriptsAutoload(final MinecraftServer server) + { + return CarpetSettings.scriptsAutoload; + } + + public static void MinecraftServer_notifyPlayersCommandsChanged(final MinecraftServer server) + { + CommandHelper.notifyPlayersCommandsChanged(server); + } + + public static boolean ScriptServer_scriptOptimizations(final MinecraftServer scriptServer) + { + return CarpetSettings.scriptsOptimization; + } + + public static boolean ScriptServer_scriptDebugging(final MinecraftServer server) + { + return CarpetSettings.scriptsDebugging; + } + + public static boolean ServerPlayer_canScriptACE(final CommandSourceStack player) + { + return CommandHelper.canUseCommand(player, CarpetSettings.commandScriptACE); + } + + public static boolean ServerPlayer_canScriptGeneral(final CommandSourceStack player) + { + return CommandHelper.canUseCommand(player, CarpetSettings.commandScript); + } + + public static int MinecraftServer_getFillLimit(final MinecraftServer server) + { + return Math.max(server.getGameRules().getInt(GameRules.RULE_COMMAND_MODIFICATION_BLOCK_LIMIT), CarpetSettings.fillLimit); + } + + public record BlockPredicatePayload(BlockState state, TagKey tagKey, Map properties, CompoundTag tag) { + public static BlockPredicatePayload of(final Predicate blockPredicate) + { + final BlockPredicateInterface predicateData = (BlockPredicateInterface) blockPredicate; + return new BlockPredicatePayload(predicateData.getCMBlockState(), predicateData.getCMBlockTagKey(), predicateData.getCMProperties(), predicateData.getCMDataTag()); + } + } + +} diff --git a/src/main/java/carpet/script/external/VanillaClient.java b/src/main/java/carpet/script/external/VanillaClient.java new file mode 100644 index 00000000..5c7f1a17 --- /dev/null +++ b/src/main/java/carpet/script/external/VanillaClient.java @@ -0,0 +1,13 @@ +package carpet.script.external; + +import carpet.mixins.ShulkerBoxAccessMixin; +import net.minecraft.client.model.ShulkerModel; +import net.minecraft.client.renderer.blockentity.BlockEntityRenderer; +import net.minecraft.world.level.block.entity.ShulkerBoxBlockEntity; + +public class VanillaClient +{ + public static ShulkerModel ShulkerBoxRenderer_model(final BlockEntityRenderer shulkerBoxRenderer) { + return ((ShulkerBoxAccessMixin)shulkerBoxRenderer).getModel(); + } +} diff --git a/src/main/java/carpet/script/external/package-info.java b/src/main/java/carpet/script/external/package-info.java new file mode 100644 index 00000000..2e80a817 --- /dev/null +++ b/src/main/java/carpet/script/external/package-info.java @@ -0,0 +1,8 @@ +@ParametersAreNonnullByDefault +@FieldsAreNonnullByDefault +@MethodsReturnNonnullByDefault +package carpet.script.external; + +import net.minecraft.FieldsAreNonnullByDefault; +import net.minecraft.MethodsReturnNonnullByDefault; +import javax.annotation.ParametersAreNonnullByDefault; \ No newline at end of file diff --git a/src/main/java/carpet/script/utils/AppStoreManager.java b/src/main/java/carpet/script/utils/AppStoreManager.java index 1f331476..ab5b0bf0 100644 --- a/src/main/java/carpet/script/utils/AppStoreManager.java +++ b/src/main/java/carpet/script/utils/AppStoreManager.java @@ -1,15 +1,13 @@ package carpet.script.utils; -import carpet.CarpetServer; -import carpet.api.settings.CarpetRule; -import carpet.api.settings.Validator; import carpet.script.CarpetScriptHost; import carpet.script.CarpetScriptServer; import carpet.script.exception.InternalExpressionException; +import carpet.script.external.Carpet; +import carpet.script.external.Vanilla; import carpet.script.value.MapValue; import carpet.script.value.StringValue; import carpet.script.value.Value; -import carpet.utils.Messenger; import com.google.gson.JsonArray; import com.google.gson.JsonElement; import com.google.gson.JsonObject; @@ -36,6 +34,8 @@ import java.util.stream.Collectors; import org.apache.commons.io.IOUtils; +import javax.annotation.Nullable; + /** * A class used to save scarpet app store scripts to disk */ @@ -52,40 +52,15 @@ public class AppStoreManager */ private static String scarpetRepoLink = "https://api.github.com/repos/gnembon/scarpet/contents/programs/"; - private record AppInfo(String name, String url, StoreNode source) + public static void setScarpetRepoLink(@Nullable final String link) { + APP_STORE_ROOT = AppStoreManager.StoreNode.folder(null, ""); + scarpetRepoLink = link; } - public static class ScarpetAppStoreValidator extends Validator - { - @Override - public String validate(final CommandSourceStack source, final CarpetRule currentRule, String newValue, final String stringInput) - { - if (newValue.equals(currentRule.value())) - { - // Don't refresh the local repo if it's the same (world change), helps preventing hitting rate limits from github when - // getting suggestions. Pending is a way to invalidate the cache when it gets old, and investigating api usage further - return newValue; - } - APP_STORE_ROOT = StoreNode.folder(null, ""); - if (newValue.equalsIgnoreCase("none")) - { - scarpetRepoLink = null; - return newValue; - } - if (newValue.endsWith("/")) - { - newValue = newValue.replaceAll("/$", ""); - } - scarpetRepoLink = "https://api.github.com/repos/" + newValue + "/"; - return newValue; - } - @Override - public String description() - { - return "Appstore link should point to a valid github repository"; - } + private record AppInfo(String name, String url, StoreNode source) + { } public static class StoreNode @@ -291,13 +266,13 @@ public class AppStoreManager } catch (final IOException e) { - throw new CommandRuntimeException(Messenger.c("rb Failed to obtain app file content: " + e.getMessage())); + throw new CommandRuntimeException(Carpet.Messenger_compose("rb Failed to obtain app file content: " + e.getMessage())); } if (!saveScriptToFile(source, path, nodeInfo.name(), code, false, useTrash)) { return 0; } - final boolean success = CarpetServer.scriptServer.addScriptHost(source, nodeInfo.name().replaceFirst("\\.sc$", ""), null, true, false, false, nodeInfo.source()); + final boolean success = Vanilla.MinecraftServer_getScriptServer(source.getServer()).addScriptHost(source, nodeInfo.name().replaceFirst("\\.sc$", ""), null, true, false, false, nodeInfo.source()); return success ? 1 : 0; } @@ -328,7 +303,7 @@ public class AppStoreManager } catch (final IOException e) { - throw new CommandRuntimeException(Messenger.c("rb '" + appPath + "' is not a valid path to a scarpet app: " + e.getMessage())); + throw new CommandRuntimeException(Carpet.Messenger_compose("rb '" + appPath + "' is not a valid path to a scarpet app: " + e.getMessage())); } } @@ -363,7 +338,7 @@ public class AppStoreManager } Files.move(scriptLocation, trashPath); } - Messenger.m(source, String.format("gi Note: replaced existing app '%s'" + (useTrash ? " (old moved to /trash folder)" : ""), appFileName)); + Carpet.Messenger_message(source, String.format("gi Note: replaced existing app '%s'" + (useTrash ? " (old moved to /trash folder)" : ""), appFileName)); } final BufferedWriter writer = Files.newBufferedWriter(scriptLocation); writer.write(code); @@ -371,7 +346,7 @@ public class AppStoreManager } catch (final IOException e) { - Messenger.m(source, "r Error while downloading app: " + e); + Carpet.Messenger_message(source, "r Error while downloading app: " + e); CarpetScriptServer.LOG.warn("Error while downloading app", e); return false; } diff --git a/src/main/java/carpet/script/utils/BiomeInfo.java b/src/main/java/carpet/script/utils/BiomeInfo.java index 5870848c..d1322398 100644 --- a/src/main/java/carpet/script/utils/BiomeInfo.java +++ b/src/main/java/carpet/script/utils/BiomeInfo.java @@ -1,6 +1,6 @@ package carpet.script.utils; -import carpet.fakes.BiomeInterface; +import carpet.script.external.Vanilla; import carpet.script.value.ListValue; import carpet.script.value.NumericValue; import carpet.script.value.StringValue; @@ -30,7 +30,7 @@ public class BiomeInfo put("sky_color", (w, b) -> ValueConversions.ofRGB(b.getSpecialEffects().getSkyColor())); put("water_color", (w, b) -> ValueConversions.ofRGB(b.getSpecialEffects().getWaterColor())); put("water_fog_color", (w, b) -> ValueConversions.ofRGB(b.getSpecialEffects().getWaterFogColor())); - put("humidity", (w, b) -> NumericValue.of(((BiomeInterface) (Object) b).getClimateSettings().downfall())); + put("humidity", (w, b) -> NumericValue.of(Vanilla.Biome_getClimateSettings(b).downfall())); put("precipitation", (w, b) -> StringValue.of(b.getPrecipitationAt(new BlockPos(0, w.getSeaLevel(), 0)).name().toLowerCase(Locale.ROOT))); put("features", (w, b) -> { final Registry> registry = w.registryAccess().registryOrThrow(Registries.CONFIGURED_FEATURE); diff --git a/src/main/java/carpet/script/utils/EntityTools.java b/src/main/java/carpet/script/utils/EntityTools.java new file mode 100644 index 00000000..c3a63660 --- /dev/null +++ b/src/main/java/carpet/script/utils/EntityTools.java @@ -0,0 +1,34 @@ +package carpet.script.utils; + +import net.minecraft.core.BlockPos; +import net.minecraft.util.Mth; +import net.minecraft.world.entity.Entity; +import net.minecraft.world.phys.Vec3; + +public class EntityTools +{ + /** + * Not a replacement for living entity jump() - this barely is to allow other entities that can't jump in vanilla to 'jump' + * + * @param e + */ + public static void genericJump(final Entity e) + { + if (!e.isOnGround() && !e.isInWaterOrBubble() && !e.isInLava()) + { + return; + } + final float m = e.level.getBlockState(e.blockPosition()).getBlock().getJumpFactor(); + final float g = e.level.getBlockState(new BlockPos(e.getX(), e.getBoundingBox().minY - 0.5000001D, e.getZ())).getBlock().getJumpFactor(); + final float jumpVelocityMultiplier = m == 1.0D ? g : m; + final float jumpStrength = (0.42F * jumpVelocityMultiplier); + final Vec3 vec3d = e.getDeltaMovement(); + e.setDeltaMovement(vec3d.x, jumpStrength, vec3d.z); + if (e.isSprinting()) + { + final float u = e.getYRot() * 0.017453292F; // yaw + e.setDeltaMovement(e.getDeltaMovement().add((-Mth.sin(g) * 0.2F), 0.0D, (Mth.cos(u) * 0.2F))); + } + e.hasImpulse = true; + } +} diff --git a/src/main/java/carpet/script/utils/Experimental.java b/src/main/java/carpet/script/utils/Experimental.java index b8ab2e79..79d42834 100644 --- a/src/main/java/carpet/script/utils/Experimental.java +++ b/src/main/java/carpet/script/utils/Experimental.java @@ -1,7 +1,7 @@ package carpet.script.utils; -import carpet.fakes.MinecraftServerInterface; -import carpet.fakes.ServerWorldInterface; +//import carpet.fakes.MinecraftServerInterface; +//import carpet.fakes.ServerWorldInterface; import carpet.script.CarpetScriptServer; import carpet.script.value.ListValue; import carpet.script.value.Value; diff --git a/src/main/java/carpet/helpers/FeatureGenerator.java b/src/main/java/carpet/script/utils/FeatureGenerator.java similarity index 67% rename from src/main/java/carpet/helpers/FeatureGenerator.java rename to src/main/java/carpet/script/utils/FeatureGenerator.java index 8ba56c40..8252489c 100644 --- a/src/main/java/carpet/helpers/FeatureGenerator.java +++ b/src/main/java/carpet/script/utils/FeatureGenerator.java @@ -1,9 +1,8 @@ -package carpet.helpers; +package carpet.script.utils; -import carpet.CarpetSettings; -import carpet.fakes.ChunkGeneratorInterface; +import carpet.script.CarpetScriptServer; +import carpet.script.external.Vanilla; import com.google.common.collect.ImmutableList; -import com.mojang.datafixers.util.Pair; import java.util.HashMap; import java.util.List; @@ -13,19 +12,19 @@ import java.util.Optional; import java.util.OptionalInt; import java.util.function.Function; +import com.mojang.datafixers.util.Pair; import net.minecraft.core.BlockPos; import net.minecraft.core.Holder; import net.minecraft.core.HolderGetter; import net.minecraft.core.HolderSet; -import net.minecraft.core.QuartPos; import net.minecraft.core.Registry; import net.minecraft.core.RegistryAccess; -import net.minecraft.core.registries.BuiltInRegistries; import net.minecraft.core.registries.Registries; import net.minecraft.data.worldgen.Pools; import net.minecraft.data.worldgen.ProcessorLists; import net.minecraft.data.worldgen.placement.PlacementUtils; import net.minecraft.resources.ResourceLocation; +import net.minecraft.server.level.ServerChunkCache; import net.minecraft.server.level.ServerLevel; import net.minecraft.tags.BiomeTags; import net.minecraft.util.RandomSource; @@ -35,6 +34,7 @@ import net.minecraft.world.level.biome.Biome; import net.minecraft.world.level.block.Block; import net.minecraft.world.level.block.Blocks; import net.minecraft.world.level.chunk.ChunkGenerator; +import net.minecraft.world.level.chunk.ChunkGeneratorStructureState; import net.minecraft.world.level.levelgen.GenerationStep; import net.minecraft.world.level.levelgen.RandomState; import net.minecraft.world.level.levelgen.VerticalAnchor; @@ -63,75 +63,88 @@ import net.minecraft.world.level.levelgen.structure.placement.StructurePlacement import net.minecraft.world.level.levelgen.structure.structures.JigsawStructure; import net.minecraft.world.level.levelgen.structure.templatesystem.StructureProcessorList; +import javax.annotation.Nullable; + public class FeatureGenerator { - synchronized public static Boolean plop(String featureName, ServerLevel world, BlockPos pos) + @Nullable + public static synchronized Boolean plop(final String featureName, final ServerLevel world, final BlockPos pos) { - Function custom = featureMap.get(featureName); + final Function custom = featureMap.get(featureName); if (custom != null) { return custom.apply(world).plop(world, pos); } - ResourceLocation id = new ResourceLocation(featureName); - Structure structure = world.registryAccess().registryOrThrow(Registries.STRUCTURE).get(id); + final ResourceLocation id = new ResourceLocation(featureName); + final Structure structure = world.registryAccess().registryOrThrow(Registries.STRUCTURE).get(id); if (structure != null) { - return plopAnywhere( structure, world, pos, world.getChunkSource().getGenerator(), false); + return plopAnywhere(structure, world, pos, world.getChunkSource().getGenerator(), false); } - ConfiguredFeature configuredFeature = world.registryAccess().registryOrThrow(Registries.CONFIGURED_FEATURE).get(id); + final ConfiguredFeature configuredFeature = world.registryAccess().registryOrThrow(Registries.CONFIGURED_FEATURE).get(id); if (configuredFeature != null) { - CarpetSettings.skipGenerationChecks.set(true); + final ThreadLocal checks = Vanilla.skipGenerationChecks(world); + checks.set(true); try { return configuredFeature.place(world, world.getChunkSource().getGenerator(), world.random, pos); } finally { - CarpetSettings.skipGenerationChecks.set(false); + checks.set(false); } } - Optional> structureType = world.registryAccess().registryOrThrow(Registries.STRUCTURE_TYPE).getOptional(id); + final Optional> structureType = world.registryAccess().registryOrThrow(Registries.STRUCTURE_TYPE).getOptional(id); if (structureType.isPresent()) { - Structure configuredStandard = getDefaultFeature(structureType.get(), world, pos); - if (configuredStandard != null) - return plopAnywhere(configuredStandard, world, pos, world.getChunkSource().getGenerator(), false); - } - Feature feature = world.registryAccess().registryOrThrow(Registries.FEATURE).get(id); - if (feature != null) - { - ConfiguredFeature configuredStandard = getDefaultFeature(feature, world, pos, true); + final Structure configuredStandard = getDefaultFeature(structureType.get(), world, pos); if (configuredStandard != null) { - CarpetSettings.skipGenerationChecks.set(true); + return plopAnywhere(configuredStandard, world, pos, world.getChunkSource().getGenerator(), false); + } + } + final Feature feature = world.registryAccess().registryOrThrow(Registries.FEATURE).get(id); + if (feature != null) + { + final ConfiguredFeature configuredStandard = getDefaultFeature(feature, world, pos, true); + if (configuredStandard != null) + { + final ThreadLocal checks = Vanilla.skipGenerationChecks(world); + checks.set(true); try { return configuredStandard.place(world, world.getChunkSource().getGenerator(), world.random, pos); } finally { - CarpetSettings.skipGenerationChecks.set(false); + checks.set(false); } } } return null; } - public static Structure resolveConfiguredStructure(String name, ServerLevel world, BlockPos pos) + public static Structure resolveConfiguredStructure(final String name, final ServerLevel world, final BlockPos pos) { - ResourceLocation id = new ResourceLocation(name); - Structure configuredStructureFeature = world.registryAccess().registryOrThrow(Registries.STRUCTURE).get(id); - if (configuredStructureFeature != null) return configuredStructureFeature; - StructureType structureFeature = world.registryAccess().registryOrThrow(Registries.STRUCTURE_TYPE).get(id); - if (structureFeature == null) return null; + final ResourceLocation id = new ResourceLocation(name); + final Structure configuredStructureFeature = world.registryAccess().registryOrThrow(Registries.STRUCTURE).get(id); + if (configuredStructureFeature != null) + { + return configuredStructureFeature; + } + final StructureType structureFeature = world.registryAccess().registryOrThrow(Registries.STRUCTURE_TYPE).get(id); + if (structureFeature == null) + { + return null; + } return getDefaultFeature(structureFeature, world, pos); } - synchronized public static Boolean plopGrid(Structure structureFeature, ServerLevel world, BlockPos pos) + public static synchronized Boolean plopGrid(final Structure structureFeature, final ServerLevel world, final BlockPos pos) { - return plopAnywhere( structureFeature, world, pos, world.getChunkSource().getGenerator(), true); + return plopAnywhere(structureFeature, world, pos, world.getChunkSource().getGenerator(), true); } @FunctionalInterface @@ -139,85 +152,102 @@ public class FeatureGenerator { Boolean plop(ServerLevel world, BlockPos pos); } - private static Thing simplePlop(ConfiguredFeature feature) + + private static Thing simplePlop(final ConfiguredFeature feature) { return (w, p) -> { - CarpetSettings.skipGenerationChecks.set(true); + final ThreadLocal checks = Vanilla.skipGenerationChecks(w); + checks.set(true); try { return feature.place(w, w.getChunkSource().getGenerator(), w.random, p); } finally { - CarpetSettings.skipGenerationChecks.set(false); + checks.set(false); } }; } - private static > Thing simplePlop(F feature, FC config) + private static > Thing simplePlop(final F feature, final FC config) { return simplePlop(new ConfiguredFeature<>(feature, config)); } - private static Thing simpleTree(TreeConfiguration config) + private static Thing simpleTree(final TreeConfiguration config) { //config.ignoreFluidCheck(); return simplePlop(new ConfiguredFeature<>(Feature.TREE, config)); } - private static Thing spawnCustomStructure(Structure structure) + private static Thing spawnCustomStructure(final Structure structure) { - return setupCustomStructure(structure,false); + return setupCustomStructure(structure, false); } - private static Thing setupCustomStructure(Structure structure, boolean wireOnly) - { + + private static Thing setupCustomStructure(final Structure structure, final boolean wireOnly) + { return (w, p) -> plopAnywhere(structure, w, p, w.getChunkSource().getGenerator(), wireOnly); } - private static Structure getDefaultFeature(StructureType structure, ServerLevel world, BlockPos pos) + private static Structure getDefaultFeature(final StructureType structure, final ServerLevel world, final BlockPos pos) { // would be nice to have a way to grab structures of this type for position // TODO allow old types, like vaillage, or bastion - Holder existingBiome = world.getBiome(pos); + final Holder existingBiome = world.getBiome(pos); Structure result = null; - for (Structure confstr : world.registryAccess().registryOrThrow(Registries.STRUCTURE).entrySet().stream(). - filter(cS -> cS.getValue().type() == structure).map(Map.Entry::getValue).toList()) + for (final Structure confstr : world.registryAccess().registryOrThrow(Registries.STRUCTURE).entrySet().stream(). + filter(cS -> cS.getValue().type() == structure).map(Map.Entry::getValue).toList()) { result = confstr; - if (confstr.biomes().contains(existingBiome)) return result; + if (confstr.biomes().contains(existingBiome)) + { + return result; + } } return result; } - private static ConfiguredFeature getDefaultFeature(Feature feature, ServerLevel world, BlockPos pos, boolean tryHard) + private static ConfiguredFeature getDefaultFeature(final Feature feature, final ServerLevel world, final BlockPos pos, final boolean tryHard) { - List> configuredStepFeatures = world.getBiome(pos).value().getGenerationSettings().features(); - for (HolderSet step: configuredStepFeatures) - for (Holder provider: step) + final List> configuredStepFeatures = world.getBiome(pos).value().getGenerationSettings().features(); + for (final HolderSet step : configuredStepFeatures) + { + for (final Holder provider : step) { if (provider.value().feature().value().feature() == feature) + { return provider.value().feature().value(); + } } - if (!tryHard) return null; + } + if (!tryHard) + { + return null; + } return world.registryAccess().registryOrThrow(Registries.CONFIGURED_FEATURE).entrySet().stream(). filter(cS -> cS.getValue().feature() == feature). findFirst().map(Map.Entry::getValue).orElse(null); } - public static StructureStart shouldStructureStartAt(ServerLevel world, BlockPos pos, Structure structure, boolean computeBox) + public static StructureStart shouldStructureStartAt(final ServerLevel world, final BlockPos pos, final Structure structure, final boolean computeBox) { - //long seed = world.getSeed(); - RandomState seed = world.getChunkSource().randomState(); - ChunkGenerator generator = world.getChunkSource().getGenerator(); - ChunkGeneratorInterface cgi = (ChunkGeneratorInterface) generator; - List structureConfig = cgi.getPlacementsForFeatureCM(world, structure); - ChunkPos chunkPos = new ChunkPos(pos); - boolean couldPlace = structureConfig.stream().anyMatch(p -> p.isStructureChunk(world.getChunkSource().getGeneratorState(), chunkPos.x, chunkPos.z)); - if (!couldPlace) return null; + final ServerChunkCache chunkSource = world.getChunkSource(); + final RandomState seed = chunkSource.randomState(); + final ChunkGenerator generator = chunkSource.getGenerator(); + final ChunkGeneratorStructureState structureState = chunkSource.getGeneratorState(); + final List structureConfig = structureState.getPlacementsForStructure(Holder.direct(structure)); + final ChunkPos chunkPos = new ChunkPos(pos); + final boolean couldPlace = structureConfig.stream().anyMatch(p -> p.isStructureChunk(structureState, chunkPos.x, chunkPos.z)); + if (!couldPlace) + { + return null; + } final HolderSet structureBiomes = structure.biomes(); - if (!computeBox) { + if (!computeBox) + { //Holder genBiome = generator.getBiomeSource().getNoiseBiome(QuartPos.fromBlock(pos.getX()), QuartPos.fromBlock(pos.getY()), QuartPos.fromBlock(pos.getZ()), seed.sampler()); if (structure.findValidGenerationPoint(new Structure.GenerationContext( world.registryAccess(), generator, generator.getBiomeSource(), @@ -227,26 +257,30 @@ public class FeatureGenerator return StructureStart.INVALID_START; } } - else { + else + { final StructureStart filledStructure = structure.generate( world.registryAccess(), generator, generator.getBiomeSource(), seed, world.getStructureManager(), world.getSeed(), chunkPos, 0, world, structureBiomes::contains); - if (filledStructure != null && filledStructure.isValid()) { + if (filledStructure != null && filledStructure.isValid()) + { return filledStructure; } } return null; } - private static TreeConfiguration.TreeConfigurationBuilder createTree(Block block, Block block2, int i, int j, int k, int l) { + private static TreeConfiguration.TreeConfigurationBuilder createTree(final Block block, final Block block2, final int i, final int j, final int k, final int l) + { return new TreeConfiguration.TreeConfigurationBuilder(BlockStateProvider.simple(block), new StraightTrunkPlacer(i, j, k), BlockStateProvider.simple(block2), new BlobFoliagePlacer(ConstantInt.of(l), ConstantInt.of(0), 3), new TwoLayersFeatureSize(1, 0, 1)); } - public static final Map> featureMap = new HashMap<>() {{ + public static final Map> featureMap = new HashMap<>() + {{ - put("oak_bees", l -> simpleTree( createTree(Blocks.OAK_LOG, Blocks.OAK_LEAVES, 4, 2, 0, 2).ignoreVines().decorators(List.of(new BeehiveDecorator(1.00F))).build())); - put("fancy_oak_bees", l -> simpleTree( (new TreeConfiguration.TreeConfigurationBuilder(BlockStateProvider.simple(Blocks.OAK_LOG), new FancyTrunkPlacer(3, 11, 0), BlockStateProvider.simple(Blocks.OAK_LEAVES), new FancyFoliagePlacer(ConstantInt.of(2), ConstantInt.of(4), 4), new TwoLayersFeatureSize(0, 0, 0, OptionalInt.of(4)))).ignoreVines().decorators(List.of(new BeehiveDecorator(1.00F))).build())); - put("birch_bees", l -> simpleTree( createTree(Blocks.BIRCH_LOG, Blocks.BIRCH_LEAVES, 5, 2, 0, 2).ignoreVines().decorators(List.of(new BeehiveDecorator(1.00F))).build())); + put("oak_bees", l -> simpleTree(createTree(Blocks.OAK_LOG, Blocks.OAK_LEAVES, 4, 2, 0, 2).ignoreVines().decorators(List.of(new BeehiveDecorator(1.00F))).build())); + put("fancy_oak_bees", l -> simpleTree((new TreeConfiguration.TreeConfigurationBuilder(BlockStateProvider.simple(Blocks.OAK_LOG), new FancyTrunkPlacer(3, 11, 0), BlockStateProvider.simple(Blocks.OAK_LEAVES), new FancyFoliagePlacer(ConstantInt.of(2), ConstantInt.of(4), 4), new TwoLayersFeatureSize(0, 0, 0, OptionalInt.of(4)))).ignoreVines().decorators(List.of(new BeehiveDecorator(1.00F))).build())); + put("birch_bees", l -> simpleTree(createTree(Blocks.BIRCH_LOG, Blocks.BIRCH_LEAVES, 5, 2, 0, 2).ignoreVines().decorators(List.of(new BeehiveDecorator(1.00F))).build())); put("coral_tree", l -> simplePlop(Feature.CORAL_TREE, FeatureConfiguration.NONE)); @@ -258,7 +292,7 @@ public class FeatureGenerator PlacementUtils.inlinePlaced(Feature.CORAL_MUSHROOM, FeatureConfiguration.NONE) )))); put("bastion_remnant_units", l -> { - RegistryAccess regs = l.registryAccess(); + final RegistryAccess regs = l.registryAccess(); final HolderGetter processorLists = regs.lookupOrThrow(Registries.PROCESSOR_LIST); final Holder bastionGenericDegradation = processorLists.getOrThrow(ProcessorLists.BASTION_GENERIC_DEGRADATION); @@ -288,7 +322,7 @@ public class FeatureGenerator ); }); put("bastion_remnant_hoglin_stable", l -> { - RegistryAccess regs = l.registryAccess(); + final RegistryAccess regs = l.registryAccess(); final HolderGetter processorLists = regs.lookupOrThrow(Registries.PROCESSOR_LIST); final Holder bastionGenericDegradation = processorLists.getOrThrow(ProcessorLists.BASTION_GENERIC_DEGRADATION); @@ -317,7 +351,7 @@ public class FeatureGenerator ); }); put("bastion_remnant_treasure", l -> { - RegistryAccess regs = l.registryAccess(); + final RegistryAccess regs = l.registryAccess(); final HolderGetter processorLists = regs.lookupOrThrow(Registries.PROCESSOR_LIST); final Holder bastionGenericDegradation = processorLists.getOrThrow(ProcessorLists.BASTION_GENERIC_DEGRADATION); @@ -346,7 +380,7 @@ public class FeatureGenerator ); }); put("bastion_remnant_bridge", l -> { - RegistryAccess regs = l.registryAccess(); + final RegistryAccess regs = l.registryAccess(); final HolderGetter processorLists = regs.lookupOrThrow(Registries.PROCESSOR_LIST); final Holder bastionGenericDegradation = processorLists.getOrThrow(ProcessorLists.BASTION_GENERIC_DEGRADATION); @@ -377,28 +411,29 @@ public class FeatureGenerator }}; - public static boolean plopAnywhere(Structure structure, ServerLevel world, BlockPos pos, ChunkGenerator generator, boolean wireOnly) + public static boolean plopAnywhere(final Structure structure, final ServerLevel world, final BlockPos pos, final ChunkGenerator generator, final boolean wireOnly) { - CarpetSettings.skipGenerationChecks.set(true); + final ThreadLocal checks = Vanilla.skipGenerationChecks(world); + checks.set(true); try { - StructureStart start = structure.generate(world.registryAccess(), generator, generator.getBiomeSource(), world.getChunkSource().randomState(), world.getStructureManager(), world.getSeed(), new ChunkPos(pos), 0, world, b -> true ); + final StructureStart start = structure.generate(world.registryAccess(), generator, generator.getBiomeSource(), world.getChunkSource().randomState(), world.getStructureManager(), world.getSeed(), new ChunkPos(pos), 0, world, b -> true); if (start == StructureStart.INVALID_START) { return false; } - RandomSource rand = RandomSource.create(world.getRandom().nextInt()); - int j = pos.getX() >> 4; - int k = pos.getZ() >> 4; - long chId = ChunkPos.asLong(j, k); + final RandomSource rand = RandomSource.create(world.getRandom().nextInt()); + final int j = pos.getX() >> 4; + final int k = pos.getZ() >> 4; + final long chId = ChunkPos.asLong(j, k); world.getChunk(j, k).setStartForStructure(structure, start); world.getChunk(j, k).addReferenceForStructure(structure, chId); - BoundingBox box = start.getBoundingBox(); + final BoundingBox box = start.getBoundingBox(); if (!wireOnly) { - Registry registry3 = world.registryAccess().registryOrThrow(Registries.STRUCTURE); + final Registry registry3 = world.registryAccess().registryOrThrow(Registries.STRUCTURE); world.setCurrentlyGenerating(() -> { Objects.requireNonNull(structure); return registry3.getResourceKey(structure).map(Object::toString).orElseGet(structure::toString); @@ -406,29 +441,32 @@ public class FeatureGenerator start.placeInChunk(world, world.structureManager(), generator, rand, box, new ChunkPos(j, k)); } //structurestart.notifyPostProcessAt(new ChunkPos(j, k)); - int i = Math.max(box.getXSpan(),box.getZSpan())/16+1; + final int i = Math.max(box.getXSpan(), box.getZSpan()) / 16 + 1; //int i = getRadius(); for (int k1 = j - i; k1 <= j + i; ++k1) { for (int l1 = k - i; l1 <= k + i; ++l1) { - if (k1 == j && l1 == k) continue; - if (box.intersects(k1<<4, l1<<4, (k1<<4) + 15, (l1<<4) + 15)) + if (k1 == j && l1 == k) + { + continue; + } + if (box.intersects(k1 << 4, l1 << 4, (k1 << 4) + 15, (l1 << 4) + 15)) { world.getChunk(k1, l1).addReferenceForStructure(structure, chId); } } } } - catch (Exception booboo) + catch (final Exception booboo) { - CarpetSettings.LOG.error("Unknown Exception while plopping structure: "+booboo, booboo); + CarpetScriptServer.LOG.error("Unknown Exception while plopping structure: " + booboo, booboo); return false; } finally { - CarpetSettings.skipGenerationChecks.set(false); + checks.set(false); } return true; } diff --git a/src/main/java/carpet/script/utils/ParticleParser.java b/src/main/java/carpet/script/utils/ParticleParser.java new file mode 100644 index 00000000..6ca6b558 --- /dev/null +++ b/src/main/java/carpet/script/utils/ParticleParser.java @@ -0,0 +1,42 @@ +package carpet.script.utils; + +import com.mojang.brigadier.StringReader; +import com.mojang.brigadier.exceptions.CommandSyntaxException; +import net.minecraft.commands.arguments.ParticleArgument; +import net.minecraft.core.HolderLookup; +import net.minecraft.core.particles.ParticleOptions; +import net.minecraft.core.particles.ParticleType; + +import java.util.HashMap; +import java.util.Map; + +public class ParticleParser +{ + private static final Map particleCache = new HashMap<>(); // we reset this on reloads, but probably need something better + + private static ParticleOptions parseParticle(final String name, final HolderLookup> lookup) + { + try + { + return ParticleArgument.readParticle(new StringReader(name), lookup); + } + catch (final CommandSyntaxException e) + { + throw new IllegalArgumentException("No such particle: " + name); + } + } + + public static ParticleOptions getEffect(final String name, final HolderLookup> lookup) + { + if (name == null) + { + return null; + } + return particleCache.computeIfAbsent(name, particle -> parseParticle(particle, lookup)); + } + + public static void resetCache() + { + particleCache.clear(); + } +} diff --git a/src/main/java/carpet/script/utils/ShapeDispatcher.java b/src/main/java/carpet/script/utils/ShapeDispatcher.java index 7bf3ffa0..308b7cb9 100644 --- a/src/main/java/carpet/script/utils/ShapeDispatcher.java +++ b/src/main/java/carpet/script/utils/ShapeDispatcher.java @@ -1,11 +1,11 @@ package carpet.script.utils; -import carpet.CarpetSettings; -import carpet.helpers.ParticleDisplay; -import carpet.network.ServerNetworkHandler; +import carpet.script.CarpetScriptServer; import carpet.script.exception.InternalExpressionException; import carpet.script.exception.ThrowStatement; import carpet.script.exception.Throwables; +import carpet.script.external.Carpet; +import carpet.script.external.Vanilla; import carpet.script.language.Sys; import carpet.script.utils.shapes.ShapeDirection; import carpet.script.value.AbstractListValue; @@ -149,7 +149,7 @@ public class ShapeDispatcher final List alternativePlayers = new ArrayList<>(); for (final ServerPlayer player : players) { - (ServerNetworkHandler.isValidCarpetPlayer(player) ? clientPlayers : alternativePlayers).add(player); + (Carpet.isValidCarpetPlayer(player) ? clientPlayers : alternativePlayers).add(player); } if (!clientPlayers.isEmpty()) { @@ -162,14 +162,14 @@ public class ShapeDispatcher { tagcount = 0; final Tag finalTag = tag; - clientPlayers.forEach(p -> ServerNetworkHandler.sendCustomCommand(p, "scShapes", finalTag)); + clientPlayers.forEach(p -> Vanilla.sendScarpetShapesDataToPlayer(p, finalTag)); tag = new ListTag(); } } final Tag finalTag = tag; if (!tag.isEmpty()) { - clientPlayers.forEach(p -> ServerNetworkHandler.sendCustomCommand(p, "scShapes", finalTag)); + clientPlayers.forEach(p -> Vanilla.sendScarpetShapesDataToPlayer(p, finalTag)); } } if (!alternativePlayers.isEmpty()) @@ -184,7 +184,7 @@ public class ShapeDispatcher { try { - return ParticleDisplay.getEffect(name, regs.lookupOrThrow(Registries.PARTICLE_TYPE)); + return ParticleParser.getEffect(name, regs.lookupOrThrow(Registries.PARTICLE_TYPE)); } catch (final IllegalArgumentException e) { @@ -239,7 +239,7 @@ public class ShapeDispatcher final Param decoder = Param.of.get(key); if (decoder == null) { - CarpetSettings.LOG.info("Unknown parameter for shape: " + key); + CarpetScriptServer.LOG.info("Unknown parameter for shape: " + key); return null; } final Value decodedValue = decoder.decode(tag.get(key), level); @@ -248,13 +248,13 @@ public class ShapeDispatcher final Value shapeValue = options.get("shape"); if (shapeValue == null) { - CarpetSettings.LOG.info("Shape id missing in " + String.join(", ", tag.getAllKeys())); + CarpetScriptServer.LOG.info("Shape id missing in " + String.join(", ", tag.getAllKeys())); return null; } final BiFunction, RegistryAccess, ExpiringShape> factory = ExpiringShape.shapeProviders.get(shapeValue.getString()); if (factory == null) { - CarpetSettings.LOG.info("Unknown shape: " + shapeValue.getString()); + CarpetScriptServer.LOG.info("Unknown shape: " + shapeValue.getString()); return null; } try @@ -263,7 +263,7 @@ public class ShapeDispatcher } catch (final InternalExpressionException exc) { - CarpetSettings.LOG.info(exc.getMessage()); + CarpetScriptServer.LOG.info(exc.getMessage()); } return null; } @@ -2022,7 +2022,7 @@ public class ShapeDispatcher new NumericValue(e.getZ()) ); } - CarpetSettings.LOG.error("Value: " + value.getString()); + CarpetScriptServer.LOG.error("Value: " + value.getString()); throw new InternalExpressionException("'" + p.id + "' requires a triple, block or entity to indicate position"); } diff --git a/src/main/java/carpet/script/utils/ShapesRenderer.java b/src/main/java/carpet/script/utils/ShapesRenderer.java index 24a82e3e..3505513f 100644 --- a/src/main/java/carpet/script/utils/ShapesRenderer.java +++ b/src/main/java/carpet/script/utils/ShapesRenderer.java @@ -1,9 +1,9 @@ package carpet.script.utils; -import carpet.CarpetSettings; -import carpet.mixins.ShulkerBoxAccessMixin; +import carpet.script.CarpetScriptServer; +import carpet.script.external.Carpet; +import carpet.script.external.VanillaClient; import carpet.script.utils.shapes.ShapeDirection; -import carpet.utils.CarpetProfiler; import com.mojang.blaze3d.systems.RenderSystem; import com.mojang.blaze3d.vertex.BufferBuilder; @@ -82,7 +82,7 @@ public class ShapesRenderer public void render(final PoseStack matrices, final Camera camera, final float partialTick) { - final CarpetProfiler.ProfilerToken token = CarpetProfiler.start_section(null, "Scarpet client", CarpetProfiler.TYPE.GENERAL); + final Runnable token = Carpet.startProfilerSection("Scarpet client"); //Camera camera = this.client.gameRenderer.getCamera(); final ClientLevel iWorld = this.client.level; final ResourceKey dimensionType = iWorld.dimension(); @@ -163,17 +163,17 @@ public class ShapesRenderer RenderSystem.depthMask(true); RenderSystem.enableBlend(); RenderSystem.defaultBlendFunc(); - CarpetProfiler.end_current_section(token); + token.run(); } public void addShapes(final ListTag tag) { - final CarpetProfiler.ProfilerToken token = CarpetProfiler.start_section(null, "Scarpet client", CarpetProfiler.TYPE.GENERAL); + final Runnable token = Carpet.startProfilerSection("Scarpet client"); for (int i = 0, count = tag.size(); i < count; i++) { addShape(tag.getCompound(i)); } - CarpetProfiler.end_current_section(token); + token.run(); } public void addShape(final CompoundTag tag) @@ -187,7 +187,7 @@ public class ShapesRenderer shapeFactory = renderedShapes.get(tag.getString("shape")); if (shapeFactory == null) { - CarpetSettings.LOG.info("Unrecognized shape: " + tag.getString("shape")); + CarpetScriptServer.LOG.info("Unrecognized shape: " + tag.getString("shape")); } else { @@ -217,11 +217,11 @@ public class ShapesRenderer public void renewShapes() { - final CarpetProfiler.ProfilerToken token = CarpetProfiler.start_section(null, "Scarpet client", CarpetProfiler.TYPE.GENERAL); + final Runnable token = Carpet.startProfilerSection("Scarpet client"); shapes.values().forEach(el -> el.values().forEach(shape -> shape.expiryTick++)); labels.values().forEach(el -> el.values().forEach(shape -> shape.expiryTick++)); - CarpetProfiler.end_current_section(token); + token.run(); } public abstract static class RenderedShape @@ -468,7 +468,7 @@ public class ShapesRenderer poseStack.mulPose(direction.getRotation()); poseStack.scale(1.0F, -1.0F, -1.0F); poseStack.translate(0.0, -1.0, 0.0); - final ShulkerModel model = ((ShulkerBoxAccessMixin) client.getBlockEntityRenderDispatcher().getRenderer(BlockEntity)).getModel(); + final ShulkerModel model = VanillaClient.ShulkerBoxRenderer_model(client.getBlockEntityRenderDispatcher().getRenderer(shulkerBoxBlockEntity)); final ModelPart modelPart = model.getLid(); modelPart.setPos(0.0F, 24.0F - shulkerBoxBlockEntity.getProgress(f) * 0.5F * 16.0F, 0.0F); modelPart.yRot = 270.0F * shulkerBoxBlockEntity.getProgress(f) * (float) (Math.PI / 180.0); @@ -561,7 +561,7 @@ public class ShapesRenderer } catch (final ClassCastException ignored) { - CarpetSettings.LOG.error("shape " + rshape.shape.getClass() + " cannot cast to a Label"); + CarpetScriptServer.LOG.error("shape " + rshape.shape.getClass() + " cannot cast to a Label"); } } } diff --git a/src/main/java/carpet/script/utils/SnoopyCommandSource.java b/src/main/java/carpet/script/utils/SnoopyCommandSource.java index 03f5bec3..a462bce5 100644 --- a/src/main/java/carpet/script/utils/SnoopyCommandSource.java +++ b/src/main/java/carpet/script/utils/SnoopyCommandSource.java @@ -1,6 +1,6 @@ package carpet.script.utils; -import carpet.CarpetSettings; +import carpet.script.external.Vanilla; import com.mojang.brigadier.ResultConsumer; import net.minecraft.commands.CommandSigningContext; import net.minecraft.commands.CommandSource; @@ -42,14 +42,14 @@ public class SnoopyCommandSource extends CommandSourceStack public SnoopyCommandSource(final CommandSourceStack original, final Component[] error, final List chatOutput) { - super(CommandSource.NULL, original.getPosition(), original.getRotation(), original.getLevel(), CarpetSettings.runPermissionLevel, + super(CommandSource.NULL, original.getPosition(), original.getRotation(), original.getLevel(), Vanilla.MinecraftServer_getRunPermissionLevel(original.getServer()), original.getTextName(), original.getDisplayName(), original.getServer(), original.getEntity(), false, (ctx, succ, res) -> { }, EntityAnchorArgument.Anchor.FEET, CommandSigningContext.ANONYMOUS, TaskChainer.immediate(original.getServer())); this.output = CommandSource.NULL; this.position = original.getPosition(); this.world = original.getLevel(); - this.level = CarpetSettings.runPermissionLevel; + this.level = Vanilla.MinecraftServer_getRunPermissionLevel(original.getServer()); this.simpleName = original.getTextName(); this.name = original.getDisplayName(); this.server = original.getServer(); diff --git a/src/main/java/carpet/script/utils/SystemInfo.java b/src/main/java/carpet/script/utils/SystemInfo.java index dabf7240..fafa59e1 100644 --- a/src/main/java/carpet/script/utils/SystemInfo.java +++ b/src/main/java/carpet/script/utils/SystemInfo.java @@ -1,11 +1,9 @@ package carpet.script.utils; -import carpet.CarpetServer; -import carpet.CarpetSettings; -import carpet.api.settings.CarpetRule; -import carpet.api.settings.RuleHelper; import carpet.script.CarpetContext; import carpet.script.CarpetScriptHost; +import carpet.script.external.Carpet; +import carpet.script.external.Vanilla; import carpet.script.value.BooleanValue; import carpet.script.value.EntityValue; import carpet.script.value.ListValue; @@ -14,10 +12,7 @@ import carpet.script.value.NumericValue; import carpet.script.value.StringValue; import carpet.script.value.Value; import carpet.script.value.ValueConversions; -import carpet.api.settings.SettingsManager; import com.sun.management.OperatingSystemMXBean; -import net.fabricmc.loader.api.FabricLoader; -import net.fabricmc.loader.api.ModContainer; import net.minecraft.SharedConstants; import net.minecraft.server.packs.PackType; import net.minecraft.world.level.GameRules; @@ -29,7 +24,6 @@ import net.minecraft.world.phys.Vec2; import java.lang.management.ManagementFactory; import java.nio.file.Path; import java.util.ArrayList; -import java.util.Collection; import java.util.Collections; import java.util.HashMap; import java.util.List; @@ -93,14 +87,14 @@ public class SystemInfo put("game_view_distance", c -> new NumericValue(c.server().getPlayerList().getViewDistance())); put("game_mod_name", c -> StringValue.of(c.server().getServerModName())); put("game_version", c -> StringValue.of(c.server().getServerVersion())); - put("game_target", c -> StringValue.of(CarpetSettings.releaseTarget)); + put("game_target", c -> StringValue.of(Vanilla.MinecraftServer_getReleaseTarget(c.server()))); put("game_protocol", c -> NumericValue.of(SharedConstants.getProtocolVersion())); put("game_major_target", c -> { - final String[] vers = CarpetSettings.releaseTarget.split("\\."); + final String[] vers = Vanilla.MinecraftServer_getReleaseTarget(c.server()).split("\\."); return NumericValue.of((vers.length > 1) ? Integer.parseInt(vers[1]) : 0); }); put("game_minor_target", c -> { - final String[] vers = CarpetSettings.releaseTarget.split("\\."); + final String[] vers = Vanilla.MinecraftServer_getReleaseTarget(c.server()).split("\\."); return NumericValue.of((vers.length > 2) ? Integer.parseInt(vers[2]) : 0); }); put("game_stable", c -> BooleanValue.of(SharedConstants.getCurrentVersion().isStable())); @@ -133,15 +127,8 @@ public class SystemInfo } return whitelist; }); - put("server_dev_environment", c -> BooleanValue.of(FabricLoader.getInstance().isDevelopmentEnvironment())); - put("server_mods", c -> { - final Map ret = new HashMap<>(); - for (final ModContainer mod : FabricLoader.getInstance().getAllMods()) - { - ret.put(new StringValue(mod.getMetadata().getId()), new StringValue(mod.getMetadata().getVersion().getFriendlyString())); - } - return MapValue.wrap(ret); - }); + put("server_dev_environment", c -> BooleanValue.of(Vanilla.isDevelopmentEnvironment())); + put("server_mods", c -> Vanilla.getServerMods(c.server())); put("server_last_tick_times", c -> { //assuming we are in the tick world section // might be off one tick when run in the off tasks or asynchronously. @@ -181,20 +168,7 @@ public class SystemInfo OperatingSystemMXBean.class); return new NumericValue(osBean.getProcessCpuLoad()); }); - put("world_carpet_rules", c -> { - final Collection> rules = CarpetServer.settingsManager.getCarpetRules(); - final MapValue carpetRules = new MapValue(Collections.emptyList()); - rules.forEach(rule -> carpetRules.put(new StringValue(rule.name()), new StringValue(RuleHelper.toRuleString(rule.value())))); - CarpetServer.extensions.forEach(e -> { - final SettingsManager manager = e.extensionSettingsManager(); - if (manager == null) - { - return; - } - manager.getCarpetRules().forEach(rule -> carpetRules.put(new StringValue(manager.identifier() + ":" + rule.name()), new StringValue(RuleHelper.toRuleString(rule.value())))); - }); - return carpetRules; - }); + put("world_carpet_rules", c -> Carpet.getAllCarpetRules()); put("world_gamerules", c -> { final Map rules = new HashMap<>(); final GameRules gameRules = c.level().getGameRules(); @@ -217,9 +191,7 @@ public class SystemInfo final Vec2 rotation = c.source().getRotation(); return ListValue.of(new NumericValue(rotation.x), new NumericValue(rotation.y)); }); - - put("scarpet_version", c -> StringValue.of(CarpetSettings.carpetVersion)); - + put("scarpet_version", c -> StringValue.of(Carpet.getCarpetVersion())); }}; public static Value get(final String what, final CarpetContext cc) diff --git a/src/main/java/carpet/helpers/Tracer.java b/src/main/java/carpet/script/utils/Tracer.java similarity index 55% rename from src/main/java/carpet/helpers/Tracer.java rename to src/main/java/carpet/script/utils/Tracer.java index 6eed3486..396e6645 100644 --- a/src/main/java/carpet/helpers/Tracer.java +++ b/src/main/java/carpet/script/utils/Tracer.java @@ -1,7 +1,8 @@ -package carpet.helpers; +package carpet.script.utils; import java.util.Optional; import java.util.function.Predicate; + import net.minecraft.world.entity.Entity; import net.minecraft.world.level.ClipContext; import net.minecraft.world.level.Level; @@ -13,45 +14,45 @@ import net.minecraft.world.phys.Vec3; public class Tracer { - public static HitResult rayTrace(Entity source, float partialTicks, double reach, boolean fluids) + public static HitResult rayTrace(final Entity source, final float partialTicks, final double reach, final boolean fluids) { - BlockHitResult blockHit = rayTraceBlocks(source, partialTicks, reach, fluids); + final BlockHitResult blockHit = rayTraceBlocks(source, partialTicks, reach, fluids); double maxSqDist = reach * reach; if (blockHit != null) { maxSqDist = blockHit.getLocation().distanceToSqr(source.getEyePosition(partialTicks)); } - EntityHitResult entityHit = rayTraceEntities(source, partialTicks, reach, maxSqDist); + final EntityHitResult entityHit = rayTraceEntities(source, partialTicks, reach, maxSqDist); return entityHit == null ? blockHit : entityHit; } - public static BlockHitResult rayTraceBlocks(Entity source, float partialTicks, double reach, boolean fluids) + public static BlockHitResult rayTraceBlocks(final Entity source, final float partialTicks, final double reach, final boolean fluids) { - Vec3 pos = source.getEyePosition(partialTicks); - Vec3 rotation = source.getViewVector(partialTicks); - Vec3 reachEnd = pos.add(rotation.x * reach, rotation.y * reach, rotation.z * reach); + final Vec3 pos = source.getEyePosition(partialTicks); + final Vec3 rotation = source.getViewVector(partialTicks); + final Vec3 reachEnd = pos.add(rotation.x * reach, rotation.y * reach, rotation.z * reach); return source.level.clip(new ClipContext(pos, reachEnd, ClipContext.Block.OUTLINE, fluids ? ClipContext.Fluid.ANY : ClipContext.Fluid.NONE, source)); } - public static EntityHitResult rayTraceEntities(Entity source, float partialTicks, double reach, double maxSqDist) + public static EntityHitResult rayTraceEntities(final Entity source, final float partialTicks, final double reach, final double maxSqDist) { - Vec3 pos = source.getEyePosition(partialTicks); - Vec3 reachVec = source.getViewVector(partialTicks).scale(reach); - AABB box = source.getBoundingBox().expandTowards(reachVec).inflate(1); + final Vec3 pos = source.getEyePosition(partialTicks); + final Vec3 reachVec = source.getViewVector(partialTicks).scale(reach); + final AABB box = source.getBoundingBox().expandTowards(reachVec).inflate(1); return rayTraceEntities(source, pos, pos.add(reachVec), box, e -> !e.isSpectator() && e.isPickable(), maxSqDist); } - public static EntityHitResult rayTraceEntities(Entity source, Vec3 start, Vec3 end, AABB box, Predicate predicate, double maxSqDistance) + public static EntityHitResult rayTraceEntities(final Entity source, final Vec3 start, final Vec3 end, final AABB box, final Predicate predicate, final double maxSqDistance) { - Level world = source.level; + final Level world = source.level; double targetDistance = maxSqDistance; Entity target = null; Vec3 targetHitPos = null; - for (Entity current : world.getEntities(source, box, predicate)) + for (final Entity current : world.getEntities(source, box, predicate)) { - AABB currentBox = current.getBoundingBox().inflate(current.getPickRadius()); - Optional currentHit = currentBox.clip(start, end); + final AABB currentBox = current.getBoundingBox().inflate(current.getPickRadius()); + final Optional currentHit = currentBox.clip(start, end); if (currentBox.contains(start)) { if (targetDistance >= 0) @@ -63,8 +64,8 @@ public class Tracer } else if (currentHit.isPresent()) { - Vec3 currentHitPos = currentHit.get(); - double currentDistance = start.distanceToSqr(currentHitPos); + final Vec3 currentHitPos = currentHit.get(); + final double currentDistance = start.distanceToSqr(currentHitPos); if (currentDistance < targetDistance || targetDistance == 0) { if (current.getRootVehicle() == source.getRootVehicle()) @@ -84,7 +85,6 @@ public class Tracer } } } - if (target == null) return null; - return new EntityHitResult(target, targetHitPos); + return target == null ? null : new EntityHitResult(target, targetHitPos); } } diff --git a/src/main/java/carpet/script/utils/WorldTools.java b/src/main/java/carpet/script/utils/WorldTools.java index 4235d43e..fc246cb4 100644 --- a/src/main/java/carpet/script/utils/WorldTools.java +++ b/src/main/java/carpet/script/utils/WorldTools.java @@ -1,8 +1,9 @@ package carpet.script.utils; -import carpet.fakes.MinecraftServerInterface; -import net.fabricmc.api.EnvType; -import net.fabricmc.api.Environment; +//import carpet.fakes.MinecraftServerInterface; +import carpet.script.external.Vanilla; +//import net.fabricmc.api.EnvType; +//import net.fabricmc.api.Environment; import net.minecraft.Util; import net.minecraft.core.BlockPos; import net.minecraft.core.Holder; @@ -59,7 +60,7 @@ public class WorldTools } return region.hasChunk(chpos); } - final Path regionsFolder = ((MinecraftServerInterface) world.getServer()).getCMSession().getDimensionPath(world.dimension()).resolve("region"); + final Path regionsFolder = Vanilla.MinecraftServer_storageSource(world.getServer()).getDimensionPath(world.dimension()).resolve("region"); final Path regionPath = regionsFolder.resolve(currentRegionName); if (!regionPath.toFile().exists()) { @@ -169,7 +170,7 @@ public class WorldTools } } - +/* private static class NoopWorldGenerationProgressListener implements ChunkProgressListener { @Override @@ -182,7 +183,7 @@ public class WorldTools { } - @Environment(EnvType.CLIENT) + //@Environment(EnvType.CLIENT) @Override public void start() { @@ -195,4 +196,6 @@ public class WorldTools } public static final ChunkProgressListener NOOP_LISTENER = new NoopWorldGenerationProgressListener(); + + */ } diff --git a/src/main/java/carpet/script/value/AbstractListValue.java b/src/main/java/carpet/script/value/AbstractListValue.java index b8e60d08..cb6a7ab8 100644 --- a/src/main/java/carpet/script/value/AbstractListValue.java +++ b/src/main/java/carpet/script/value/AbstractListValue.java @@ -3,7 +3,6 @@ package carpet.script.value; import carpet.script.exception.InternalExpressionException; import com.google.common.collect.Lists; -import java.util.Iterator; import java.util.List; public abstract class AbstractListValue extends Value implements Iterable diff --git a/src/main/java/carpet/script/value/BlockValue.java b/src/main/java/carpet/script/value/BlockValue.java index c4ec4df3..6d7e8563 100644 --- a/src/main/java/carpet/script/value/BlockValue.java +++ b/src/main/java/carpet/script/value/BlockValue.java @@ -21,7 +21,6 @@ import net.minecraft.core.Direction; import net.minecraft.core.Direction.Axis; import net.minecraft.core.GlobalPos; import net.minecraft.core.Registry; -import net.minecraft.core.registries.BuiltInRegistries; import net.minecraft.core.registries.Registries; import net.minecraft.nbt.CompoundTag; import net.minecraft.nbt.StringTag; @@ -38,7 +37,6 @@ import net.minecraft.world.level.block.state.properties.Property; import net.minecraft.world.level.chunk.LevelChunk; import net.minecraft.world.phys.BlockHitResult; import net.minecraft.world.phys.Vec3; -import org.jetbrains.annotations.NotNull; import static carpet.script.value.NBTSerializableValue.nameFromRegistryId; @@ -46,7 +44,6 @@ public class BlockValue extends Value { private BlockState blockState; private final BlockPos pos; - @NotNull private final Level world; private CompoundTag data; @@ -143,7 +140,7 @@ public class BlockValue extends Value } - public BlockValue(final BlockState state, @NotNull final Level world, final BlockPos position) + public BlockValue(final BlockState state, final Level world, final BlockPos position) { this.world = world; blockState = state; @@ -151,7 +148,7 @@ public class BlockValue extends Value data = null; } - public BlockValue(final BlockState state, @NotNull final Level world, final BlockPos position, final CompoundTag nbt) + public BlockValue(final BlockState state, final Level world, final BlockPos position, final CompoundTag nbt) { this.world = world; blockState = state; diff --git a/src/main/java/carpet/script/value/EntityValue.java b/src/main/java/carpet/script/value/EntityValue.java index c2a262e1..38c44f90 100644 --- a/src/main/java/carpet/script/value/EntityValue.java +++ b/src/main/java/carpet/script/value/EntityValue.java @@ -1,19 +1,14 @@ package carpet.script.value; -import carpet.fakes.EntityInterface; -import carpet.fakes.ItemEntityInterface; -import carpet.fakes.LivingEntityInterface; -import carpet.fakes.MobEntityInterface; -import carpet.fakes.ServerPlayerEntityInterface; -import carpet.fakes.ServerPlayerInteractionManagerInterface; -import carpet.helpers.Tracer; -import carpet.network.ServerNetworkHandler; -import carpet.patches.EntityPlayerMPFake; +import carpet.script.external.Vanilla; +import carpet.script.utils.Tracer; import carpet.script.CarpetContext; import carpet.script.CarpetScriptServer; import carpet.script.EntityEventsGroup; import carpet.script.argument.Vector3Argument; import carpet.script.exception.InternalExpressionException; +import carpet.script.external.Carpet; +import carpet.script.utils.EntityTools; import carpet.script.utils.InputValidator; import com.mojang.brigadier.StringReader; import com.mojang.brigadier.exceptions.CommandSyntaxException; @@ -96,7 +91,6 @@ import java.util.stream.Collectors; import java.util.stream.Stream; import static carpet.script.value.NBTSerializableValue.nameFromRegistryId; -import static carpet.utils.MobAI.genericJump; // TODO: decide whether copy(entity) should duplicate entity in the world. public class EntityValue extends Value @@ -136,7 +130,7 @@ public class EntityValue extends Value public Entity getEntity() { - if (entity instanceof ServerPlayer && ((ServerPlayerEntityInterface) entity).isInvalidEntityObject()) + if (entity instanceof final ServerPlayer serverPlayer && Vanilla.ServerPlayer_isInvalidEntityObject(serverPlayer)) { final ServerPlayer newPlayer = entity.getServer().getPlayerList().getPlayer(entity.getUUID()); if (newPlayer != null) @@ -449,7 +443,7 @@ public class EntityValue extends Value put("is_ridden", (e, a) -> BooleanValue.of(e.isVehicle())); put("passengers", (e, a) -> ListValue.wrap(e.getPassengers().stream().map(EntityValue::new))); put("mount", (e, a) -> (e.getVehicle() != null) ? new EntityValue(e.getVehicle()) : Value.NULL); - put("unmountable", (e, a) -> BooleanValue.of(((EntityInterface) e).isPermanentVehicle())); + put("unmountable", (e, a) -> BooleanValue.of(Vanilla.Entity_isPermanentVehicle(e))); // deprecated put("tags", (e, a) -> ListValue.wrap(e.getTags().stream().map(StringValue::new))); @@ -505,9 +499,9 @@ public class EntityValue extends Value put("offering_flower", (e, a) -> e instanceof final IronGolem ig ? BooleanValue.of(ig.getOfferFlowerTick() > 0) : Value.NULL); put("item", (e, a) -> e instanceof final ItemEntity ie ? ValueConversions.of(ie.getItem(), e.getServer().registryAccess()) : e instanceof final ItemFrame frame ? ValueConversions.of(frame.getItem(), e.getServer().registryAccess()) : Value.NULL); put("count", (e, a) -> (e instanceof final ItemEntity ie) ? new NumericValue(ie.getItem().getCount()) : Value.NULL); - put("pickup_delay", (e, a) -> (e instanceof ItemEntity) ? new NumericValue(((ItemEntityInterface) e).getPickupDelayCM()) : Value.NULL); - put("portal_cooldown", (e, a) -> new NumericValue(((EntityInterface) e).getPublicNetherPortalCooldown())); - put("portal_timer", (e, a) -> new NumericValue(((EntityInterface) e).getPortalTimer())); + put("pickup_delay", (e, a) -> (e instanceof final ItemEntity ie) ? new NumericValue(Vanilla.ItemEntity_getPickupDelay(ie)) : Value.NULL); + put("portal_cooldown", (e, a) -> new NumericValue(Vanilla.Entity_getPublicNetherPortalCooldown(e))); + put("portal_timer", (e, a) -> new NumericValue(Vanilla.Entity_getPortalTimer(e))); // ItemEntity -> despawn timer via ssGetAge put("is_baby", (e, a) -> (e instanceof final LivingEntity le) ? BooleanValue.of(le.isBaby()) : Value.NULL); put("target", (e, a) -> { @@ -544,7 +538,7 @@ public class EntityValue extends Value put("swimming", (e, a) -> e.isSwimming() ? Value.TRUE : Value.FALSE); put("swinging", (e, a) -> e instanceof final LivingEntity le ? BooleanValue.of(le.swinging) : Value.NULL); put("air", (e, a) -> new NumericValue(e.getAirSupply())); - put("language", (e, a) -> !(e instanceof ServerPlayer) ? NULL : StringValue.of(((ServerPlayerEntityInterface) e).getLanguage())); + put("language", (e, a) -> !(e instanceof final ServerPlayer p) ? NULL : StringValue.of(Vanilla.ServerPlayer_getLanguage(p))); put("persistence", (e, a) -> e instanceof final Mob mob ? BooleanValue.of(mob.isPersistenceRequired()) : Value.NULL); put("hunger", (e, a) -> e instanceof final Player player ? new NumericValue(player.getFoodData().getFoodLevel()) : Value.NULL); put("saturation", (e, a) -> e instanceof final Player player ? new NumericValue(player.getFoodData().getSaturationLevel()) : Value.NULL); @@ -554,7 +548,7 @@ public class EntityValue extends Value put("xp_level", (e, a) -> e instanceof final Player player ? new NumericValue(player.experienceLevel) : Value.NULL); put("xp_progress", (e, a) -> e instanceof final Player player ? new NumericValue(player.experienceProgress) : Value.NULL); put("score", (e, a) -> e instanceof final Player player ? new NumericValue(player.getScore()) : Value.NULL); - put("jumping", (e, a) -> e instanceof LivingEntity ? ((LivingEntityInterface) e).isJumpingCM() ? Value.TRUE : Value.FALSE : Value.NULL); + put("jumping", (e, a) -> e instanceof final LivingEntity le ? Vanilla.LivingEntity_isJumping(le) ? Value.TRUE : Value.FALSE : Value.NULL); put("gamemode", (e, a) -> e instanceof final ServerPlayer sp ? new StringValue(sp.gameMode.getGameModeForPlayer().getName()) : Value.NULL); put("path", (e, a) -> { if (e instanceof final Mob mob) @@ -610,9 +604,10 @@ public class EntityValue extends Value put("player_type", (e, a) -> { if (e instanceof final Player p) { - if (e instanceof final EntityPlayerMPFake fake) + final String moddedType = Carpet.isModdedPlayer(p); + if (moddedType != null) { - return new StringValue(fake.isAShadow ? "shadow" : "fake"); + return StringValue.of(moddedType); } final MinecraftServer server = p.getCommandSenderWorld().getServer(); if (server.isDedicatedServer()) @@ -635,7 +630,7 @@ public class EntityValue extends Value return Value.NULL; }); - put("client_brand", (e, a) -> e instanceof final ServerPlayer sp ? StringValue.of(ServerNetworkHandler.getPlayerStatus(sp)) : Value.NULL); + put("client_brand", (e, a) -> e instanceof final ServerPlayer sp ? StringValue.of(Carpet.getPlayerStatus(sp)) : Value.NULL); put("team", (e, a) -> e.getTeam() == null ? Value.NULL : new StringValue(e.getTeam().getName())); put("ping", (e, a) -> e instanceof final ServerPlayer sp ? new NumericValue(sp.latency) : Value.NULL); @@ -703,8 +698,7 @@ public class EntityValue extends Value put("active_block", (e, a) -> { if (e instanceof final ServerPlayer sp) { - final ServerPlayerInteractionManagerInterface manager = (ServerPlayerInteractionManagerInterface) (sp.gameMode); - final BlockPos pos = manager.getCurrentBreakingBlock(); + final BlockPos pos = Vanilla.ServerPlayerGameMode_getCurrentBlockPosition(sp.gameMode); if (pos == null) { return Value.NULL; @@ -717,8 +711,7 @@ public class EntityValue extends Value put("breaking_progress", (e, a) -> { if (e instanceof final ServerPlayer sp) { - final ServerPlayerInteractionManagerInterface manager = (ServerPlayerInteractionManagerInterface) (sp.gameMode); - final int progress = manager.getCurrentBlockBreakingProgress(); + final int progress = Vanilla.ServerPlayerGameMode_getCurrentBlockBreakingProgress (sp.gameMode); return progress < 0 ? Value.NULL : new NumericValue(progress); } return Value.NULL; @@ -1204,7 +1197,7 @@ public class EntityValue extends Value put("persistence", (e, v) -> { - if (!(e instanceof Mob)) + if (!(e instanceof final Mob mob)) { return; } @@ -1212,7 +1205,7 @@ public class EntityValue extends Value { v = Value.TRUE; } - ((MobEntityInterface) e).setPersistence(v.getBoolean()); + Vanilla.Mob_setPersistence(mob, v.getBoolean()); }); put("dismount", (e, v) -> e.stopRiding()); @@ -1226,7 +1219,7 @@ public class EntityValue extends Value sp.connection.send(new ClientboundSetPassengersPacket(e)); } }); - put("unmountable", (e, v) -> ((EntityInterface) e).setPermanentVehicle(v == null || v.getBoolean())); + put("unmountable", (e, v) -> Vanilla.Entity_setPermanentVehicle(e, v == null || v.getBoolean())); put("drop_passengers", (e, v) -> e.ejectPassengers()); put("mount_passengers", (e, v) -> { if (v == null) @@ -1316,8 +1309,8 @@ public class EntityValue extends Value if (v.isNull()) { ec.restrictTo(BlockPos.ZERO, -1); - final Map tasks = ((MobEntityInterface) ec).getTemporaryTasks(); - ((MobEntityInterface) ec).getAI(false).removeGoal(tasks.get("home")); + final Map tasks = Vanilla.Mob_getTemporaryTasks(ec); + Vanilla.Mob_getAI(ec, false).removeGoal(tasks.get("home")); tasks.remove("home"); return; } @@ -1349,12 +1342,12 @@ public class EntityValue extends Value } ec.restrictTo(pos, distance); - final Map tasks = ((MobEntityInterface) ec).getTemporaryTasks(); + final Map tasks = Vanilla.Mob_getTemporaryTasks(ec); if (!tasks.containsKey("home")) { final Goal task = new MoveTowardsRestrictionGoal(ec, 1.0D); tasks.put("home", task); - ((MobEntityInterface) ec).getAI(false).addGoal(10, task); + Vanilla.Mob_getAI(ec, false).addGoal(10, task); } }); //requires mixing @@ -1430,7 +1423,7 @@ public class EntityValue extends Value { throw new InternalExpressionException("'portal_cooldown' requires a value to set"); } - ((EntityInterface) e).setPublicNetherPortalCooldown(NumericValue.asNumber(v).getInt()); + Vanilla.Entity_setPublicNetherPortalCooldown(e, NumericValue.asNumber(v).getInt()); }); put("portal_timer", (e, v) -> @@ -1439,7 +1432,7 @@ public class EntityValue extends Value { throw new InternalExpressionException("'portal_timer' requires a value to set"); } - ((EntityInterface) e).setPortalTimer(NumericValue.asNumber(v).getInt()); + Vanilla.Entity_setPortalTimer(e, NumericValue.asNumber(v).getInt()); }); put("ai", (e, v) -> @@ -1555,13 +1548,13 @@ public class EntityValue extends Value }); put("jump", (e, v) -> { - if (e instanceof LivingEntity) + if (e instanceof final LivingEntity le) { - ((LivingEntityInterface) e).doJumpCM(); + Vanilla.LivingEntity_setJumping(le); } else { - genericJump(e); + EntityTools.genericJump(e); } }); @@ -1671,8 +1664,7 @@ public class EntityValue extends Value if (e instanceof final ServerPlayer sp) { final int progress = (a == null || a.isNull()) ? -1 : NumericValue.asNumber(a).getInt(); - final ServerPlayerInteractionManagerInterface manager = (ServerPlayerInteractionManagerInterface) (sp.gameMode); - manager.setBlockBreakingProgress(progress); + Vanilla.ServerPlayerGameMode_setBlockBreakingProgress(sp.gameMode, progress); } }); @@ -1740,7 +1732,7 @@ public class EntityValue extends Value { throw new InternalExpressionException("Unknown entity event: " + eventName); } - ((EntityInterface) getEntity()).getEventContainer().addEvent(event, cc.host, fun, args); + Vanilla.Entity_getEventContainer(getEntity()).addEvent(event, cc.host, fun, args); } @Override diff --git a/src/main/java/carpet/script/value/FunctionValue.java b/src/main/java/carpet/script/value/FunctionValue.java index 8ee3780d..566471e9 100644 --- a/src/main/java/carpet/script/value/FunctionValue.java +++ b/src/main/java/carpet/script/value/FunctionValue.java @@ -1,6 +1,6 @@ package carpet.script.value; -import carpet.CarpetSettings; +import carpet.script.CarpetScriptServer; import carpet.script.Context; import carpet.script.Expression; import carpet.script.Fluff; @@ -18,7 +18,6 @@ import java.util.Collections; import java.util.List; import java.util.Map; import java.util.function.Consumer; -import java.util.stream.Collectors; import net.minecraft.nbt.StringTag; import net.minecraft.nbt.Tag; @@ -200,7 +199,7 @@ public class FunctionValue extends Value implements Fluff.ILazyFunction final Value param = lv.evalValue(c, Context.NONE); if (param instanceof FunctionUnpackedArgumentsValue) { - CarpetSettings.LOG.error("How did we get here?"); + CarpetScriptServer.LOG.error("How did we get here?"); params.addAll(((ListValue) param).getItems()); } else diff --git a/src/main/java/carpet/script/value/NBTSerializableValue.java b/src/main/java/carpet/script/value/NBTSerializableValue.java index 32cce9dd..cfd8eb2a 100644 --- a/src/main/java/carpet/script/value/NBTSerializableValue.java +++ b/src/main/java/carpet/script/value/NBTSerializableValue.java @@ -1,10 +1,10 @@ package carpet.script.value; -import carpet.fakes.InventoryBearerInterface; import carpet.script.CarpetContext; import carpet.script.exception.InternalExpressionException; import carpet.script.exception.ThrowStatement; import carpet.script.exception.Throwables; +import carpet.script.external.Vanilla; import carpet.script.utils.EquipmentInventory; import com.mojang.brigadier.StringReader; import com.mojang.brigadier.exceptions.CommandSyntaxException; @@ -44,6 +44,7 @@ import net.minecraft.world.WorldlyContainerHolder; import net.minecraft.world.entity.Entity; import net.minecraft.world.entity.EntitySelector; import net.minecraft.world.entity.LivingEntity; +import net.minecraft.world.entity.animal.horse.AbstractHorse; import net.minecraft.world.entity.npc.InventoryCarrier; import net.minecraft.world.entity.player.Player; import net.minecraft.world.item.ItemStack; @@ -280,9 +281,9 @@ public class NBTSerializableValue extends Value implements ContainerValueInterfa { inv = io.getInventory(); } - else if (e instanceof final InventoryBearerInterface ibi) + else if (e instanceof final AbstractHorse ibi) { - inv = ibi.getCMInventory(); // horse only + inv = Vanilla.AbstractHorse_getInventory(ibi); // horse only } else if (e instanceof final LivingEntity le) { diff --git a/src/main/java/carpet/script/value/ScreenValue.java b/src/main/java/carpet/script/value/ScreenValue.java index 0c144c52..b24d290d 100644 --- a/src/main/java/carpet/script/value/ScreenValue.java +++ b/src/main/java/carpet/script/value/ScreenValue.java @@ -1,9 +1,5 @@ package carpet.script.value; -import carpet.CarpetServer; -import carpet.CarpetSettings; -import carpet.fakes.ScreenHandlerInterface; - import carpet.script.CarpetScriptHost; import carpet.script.CarpetScriptServer; import carpet.script.Context; @@ -12,6 +8,7 @@ import carpet.script.exception.InternalExpressionException; import carpet.script.exception.InvalidCallbackException; import carpet.script.exception.ThrowStatement; import carpet.script.exception.Throwables; +import carpet.script.external.Vanilla; import java.util.Arrays; import java.util.HashMap; @@ -31,7 +28,32 @@ import net.minecraft.world.SimpleContainer; import net.minecraft.world.SimpleMenuProvider; import net.minecraft.world.entity.player.Inventory; import net.minecraft.world.entity.player.Player; -import net.minecraft.world.inventory.*; +import net.minecraft.world.inventory.AbstractContainerMenu; +import net.minecraft.world.inventory.AbstractFurnaceMenu; +import net.minecraft.world.inventory.AnvilMenu; +import net.minecraft.world.inventory.BeaconMenu; +import net.minecraft.world.inventory.BlastFurnaceMenu; +import net.minecraft.world.inventory.BrewingStandMenu; +import net.minecraft.world.inventory.CartographyTableMenu; +import net.minecraft.world.inventory.ChestMenu; +import net.minecraft.world.inventory.ClickType; +import net.minecraft.world.inventory.ContainerListener; +import net.minecraft.world.inventory.CraftingMenu; +import net.minecraft.world.inventory.DataSlot; +import net.minecraft.world.inventory.EnchantmentMenu; +import net.minecraft.world.inventory.FurnaceMenu; +import net.minecraft.world.inventory.GrindstoneMenu; +import net.minecraft.world.inventory.HopperMenu; +import net.minecraft.world.inventory.LecternMenu; +import net.minecraft.world.inventory.LegacySmithingMenu; +import net.minecraft.world.inventory.LoomMenu; +import net.minecraft.world.inventory.MerchantMenu; +import net.minecraft.world.inventory.ShulkerBoxMenu; +import net.minecraft.world.inventory.SimpleContainerData; +import net.minecraft.world.inventory.Slot; +import net.minecraft.world.inventory.SmithingMenu; +import net.minecraft.world.inventory.SmokerMenu; +import net.minecraft.world.inventory.StonecutterMenu; import net.minecraft.world.item.ItemStack; import net.minecraft.world.item.crafting.Recipe; @@ -47,6 +69,7 @@ public class ScreenValue extends Value private final FunctionValue callback; private final String hostname; private final ServerPlayer player; + private final CarpetScriptServer scriptServer; public static Map screenHandlerFactories; @@ -96,6 +119,7 @@ public class ScreenValue extends Value } this.callback = callback; this.hostname = c.host.getName(); + this.scriptServer = (CarpetScriptServer) c.host.scriptServer(); this.player = player; final MenuProvider factory = this.createScreenHandlerFactory(); if (factory == null) @@ -167,18 +191,19 @@ public class ScreenValue extends Value final Value actionValue = StringValue.of(action); final Value dataValue = MapValue.wrap(data); final List args = Arrays.asList(this, playerValue, actionValue, dataValue); - final CarpetScriptHost appHost = CarpetServer.scriptServer.getAppHostByName(this.hostname); + final CarpetScriptHost appHost = scriptServer.getAppHostByName(this.hostname); if (appHost == null) { this.close(); this.screenHandler = null; return false; } - final CommandSourceStack source = player.createCommandSourceStack().withPermission(CarpetSettings.runPermissionLevel); + final int runPermissionLevel = Vanilla.MinecraftServer_getRunPermissionLevel(player.server); + final CommandSourceStack source = player.createCommandSourceStack().withPermission(runPermissionLevel); final CarpetScriptHost executingHost = appHost.retrieveForExecution(source, player); try { - final Value cancelValue = executingHost.callUDF(source.withPermission(CarpetSettings.runPermissionLevel), callback, args); + final Value cancelValue = executingHost.callUDF(source, callback, args); return cancelValue.getString().equals("cancel"); } catch (final NullPointerException | InvalidCallbackException | IntegrityException error) @@ -255,7 +280,7 @@ public class ScreenValue extends Value { if (screenHandlerClass.isInstance(this.screenHandler)) { - return ((ScreenHandlerInterface) this.screenHandler).getProperty(propertyIndex); + return Vanilla.AbstractContainerMenu_getDataSlot(this.screenHandler, propertyIndex); } if (!this.isOpen()) { diff --git a/src/main/java/carpet/script/value/Value.java b/src/main/java/carpet/script/value/Value.java index cc0cab1d..f29b5342 100644 --- a/src/main/java/carpet/script/value/Value.java +++ b/src/main/java/carpet/script/value/Value.java @@ -1,6 +1,6 @@ package carpet.script.value; -import carpet.CarpetSettings; +import carpet.script.CarpetScriptServer; import carpet.script.exception.InternalExpressionException; import com.google.gson.JsonElement; import com.google.gson.JsonPrimitive; @@ -46,7 +46,7 @@ public abstract class Value implements Comparable, Cloneable catch (final CloneNotSupportedException e) { // should not happen - CarpetSettings.LOG.error("Failed to clone variable", e); + CarpetScriptServer.LOG.error("Failed to clone variable", e); throw new InternalExpressionException("Variable of type " + getTypeString() + " is not cloneable. Tell gnembon about it, this shoudn't happen"); } copy.boundVariable = value; diff --git a/src/main/java/carpet/script/value/ValueConversions.java b/src/main/java/carpet/script/value/ValueConversions.java index 98ddd780..9ffcaff7 100644 --- a/src/main/java/carpet/script/value/ValueConversions.java +++ b/src/main/java/carpet/script/value/ValueConversions.java @@ -1,10 +1,10 @@ package carpet.script.value; -import carpet.fakes.BlockPredicateInterface; import carpet.script.exception.InternalExpressionException; import carpet.script.exception.ThrowStatement; import carpet.script.exception.Throwables; -import carpet.utils.BlockInfo; +import carpet.script.external.Carpet; +import carpet.script.external.Vanilla; import it.unimi.dsi.fastutil.ints.Int2ObjectMap; import it.unimi.dsi.fastutil.ints.Int2ObjectOpenHashMap; import net.minecraft.advancements.critereon.MinMaxBounds; @@ -83,7 +83,7 @@ public class ValueConversions public static Value of(final MaterialColor color) { - return ListValue.of(StringValue.of(BlockInfo.mapColourName.get(color)), ofRGB(color.col)); + return ListValue.of(StringValue.of(Carpet.getMapColorNames().get(color)), ofRGB(color.col)); } public static Value of(final MinMaxBounds range) @@ -451,13 +451,13 @@ public class ValueConversions public static Value ofBlockPredicate(final RegistryAccess registryAccess, final Predicate blockPredicate) { - final BlockPredicateInterface predicateData = (BlockPredicateInterface) blockPredicate; + final Vanilla.BlockPredicatePayload payload = Vanilla.BlockPredicatePayload.of(blockPredicate); final Registry blocks = registryAccess.registryOrThrow(Registries.BLOCK); return ListValue.of( - predicateData.getCMBlockState() == null ? Value.NULL : of(blocks.getKey(predicateData.getCMBlockState().getBlock())), - predicateData.getCMBlockTagKey() == null ? Value.NULL : of(blocks.getTag(predicateData.getCMBlockTagKey()).get().key()), - MapValue.wrap(predicateData.getCMProperties()), - predicateData.getCMDataTag() == null ? Value.NULL : new NBTSerializableValue(predicateData.getCMDataTag()) + payload.state() == null ? Value.NULL : of(blocks.getKey(payload.state().getBlock())), + payload.tagKey() == null ? Value.NULL : of(blocks.getTag(payload.tagKey()).get().key()), + MapValue.wrap(payload.properties()), + payload.tag() == null ? Value.NULL : new NBTSerializableValue(payload.tag()) ); } diff --git a/src/main/java/carpet/utils/MobAI.java b/src/main/java/carpet/utils/MobAI.java index c13fd594..80208dd2 100644 --- a/src/main/java/carpet/utils/MobAI.java +++ b/src/main/java/carpet/utils/MobAI.java @@ -13,6 +13,7 @@ import net.minecraft.commands.CommandSourceStack; import net.minecraft.core.BlockPos; import net.minecraft.core.registries.BuiltInRegistries; import net.minecraft.core.registries.Registries; +import net.minecraft.server.MinecraftServer; import net.minecraft.server.level.ServerLevel; import net.minecraft.util.Mth; import net.minecraft.world.entity.Entity; @@ -38,10 +39,10 @@ public class MobAI return currentTrackers.contains(type); } - public static void clearTracking(EntityType etype) + public static void clearTracking(final MinecraftServer server, EntityType etype) { aiTrackers.remove(etype); - for(ServerLevel world : CarpetServer.minecraft_server.getAllLevels() ) + for(ServerLevel world : server.getAllLevels() ) { for (Entity e: world.getEntities(etype, Entity::hasCustomName)) { @@ -86,26 +87,4 @@ public class MobAI types = applicableTypes; } } - - /** - * Not a replacement for living entity jump() - this barely is to allow other entities that can't jump in vanilla to 'jump' - * @param e - */ - public static void genericJump(Entity e) - { - if (!e.isOnGround() && !e.isInWaterOrBubble() && !e.isInLava()) return; - float m = e.level.getBlockState(e.blockPosition()).getBlock().getJumpFactor(); - float g = e.level.getBlockState(new BlockPos(e.getX(), e.getBoundingBox().minY - 0.5000001D, e.getZ())).getBlock().getJumpFactor(); - float jumpVelocityMultiplier = (double) m == 1.0D ? g : m; - float jumpStrength = (0.42F * jumpVelocityMultiplier); - Vec3 vec3d = e.getDeltaMovement(); - e.setDeltaMovement(vec3d.x, jumpStrength, vec3d.z); - if (e.isSprinting()) - { - float u = e.getYRot() * 0.017453292F; // yaw - e.setDeltaMovement(e.getDeltaMovement().add((-Mth.sin(g) * 0.2F), 0.0D, (Mth.cos(u) * 0.2F))); - } - e.hasImpulse = true; - } - } diff --git a/src/main/resources/carpet.mixins.json b/src/main/resources/carpet.mixins.json index aae9683c..dc971d3b 100644 --- a/src/main/resources/carpet.mixins.json +++ b/src/main/resources/carpet.mixins.json @@ -88,7 +88,6 @@ "Player_parrotMixin", "SaplingBlock_desertShrubsMixin", "EntityMixin", - "ChunkGenerator_scarpetMixin", "Guardian_renewableSpongesMixin", "Husk_templesMixin", "ChunkGenerator_customMobSpawnsMixin",