From c3c787bc9aac22f2bb6bf5fa7863ae5c0a344300 Mon Sep 17 00:00:00 2001 From: Wyatt Childers Date: Tue, 2 Feb 2016 18:14:30 -0500 Subject: [PATCH] Fixed the command system --- ...ommandWrapper.java => CommandAdapter.java} | 34 ++-- .../worldedit/sponge/SpongeCommandSender.java | 158 ++++++++++++++++++ .../worldedit/sponge/SpongePlatform.java | 46 +++-- .../worldedit/sponge/SpongeWorldEdit.java | 45 +++-- 4 files changed, 232 insertions(+), 51 deletions(-) rename worldedit-sponge/src/main/java/com/sk89q/worldedit/sponge/{CommandWrapper.java => CommandAdapter.java} (70%) create mode 100644 worldedit-sponge/src/main/java/com/sk89q/worldedit/sponge/SpongeCommandSender.java diff --git a/worldedit-sponge/src/main/java/com/sk89q/worldedit/sponge/CommandWrapper.java b/worldedit-sponge/src/main/java/com/sk89q/worldedit/sponge/CommandAdapter.java similarity index 70% rename from worldedit-sponge/src/main/java/com/sk89q/worldedit/sponge/CommandWrapper.java rename to worldedit-sponge/src/main/java/com/sk89q/worldedit/sponge/CommandAdapter.java index 62b0dadd6..00cfdd1c0 100644 --- a/worldedit-sponge/src/main/java/com/sk89q/worldedit/sponge/CommandWrapper.java +++ b/worldedit-sponge/src/main/java/com/sk89q/worldedit/sponge/CommandAdapter.java @@ -25,43 +25,43 @@ import org.spongepowered.api.command.CommandException; import org.spongepowered.api.command.CommandResult; import org.spongepowered.api.command.CommandSource; import org.spongepowered.api.text.Text; -import org.spongepowered.api.text.Texts; -import javax.annotation.Nullable; -import java.util.Arrays; import java.util.List; import java.util.Optional; -public class CommandWrapper implements CommandCallable { +public abstract class CommandAdapter implements CommandCallable { private CommandMapping command; - protected CommandWrapper(CommandMapping command) { + protected CommandAdapter(CommandMapping command) { this.command = command; } - @Override - public CommandResult process(CommandSource source, String arguments) throws CommandException { - return null; - } - - @Override - public List getSuggestions(CommandSource source, String arguments) throws CommandException { - return null; - } - @Override public boolean testPermission(CommandSource source) { + for (String perm : command.getDescription().getPermissions()) { + if (!source.hasPermission(perm)) { + return false; + } + } return true; } @Override public Optional getShortDescription(CommandSource source) { - return null; + String description = command.getDescription().getDescription(); + if (description != null && !description.isEmpty()) { + return Optional.of(Text.of(description)); + } + return Optional.empty(); } @Override public Optional getHelp(CommandSource source) { - return null; + String help = command.getDescription().getHelp(); + if (help != null && !help.isEmpty()) { + return Optional.of(Text.of(help)); + } + return Optional.empty(); } @Override diff --git a/worldedit-sponge/src/main/java/com/sk89q/worldedit/sponge/SpongeCommandSender.java b/worldedit-sponge/src/main/java/com/sk89q/worldedit/sponge/SpongeCommandSender.java new file mode 100644 index 000000000..f9986101f --- /dev/null +++ b/worldedit-sponge/src/main/java/com/sk89q/worldedit/sponge/SpongeCommandSender.java @@ -0,0 +1,158 @@ +/* + * WorldEdit, a Minecraft world manipulation toolkit + * Copyright (C) sk89q + * Copyright (C) WorldEdit team and contributors + * + * This program is free software: you can redistribute it and/or modify it + * under the terms of the GNU Lesser General Public License as published by the + * Free Software Foundation, either version 3 of the License, or + * (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, but WITHOUT + * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + * FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License + * for more details. + * + * You should have received a copy of the GNU Lesser General Public License + * along with this program. If not, see . + */ + +package com.sk89q.worldedit.sponge; + +import com.sk89q.worldedit.extension.platform.Actor; +import com.sk89q.worldedit.internal.cui.CUIEvent; +import com.sk89q.worldedit.session.SessionKey; +import com.sk89q.worldedit.util.auth.AuthorizationException; +import org.spongepowered.api.command.CommandSource; +import org.spongepowered.api.entity.living.player.Player; +import org.spongepowered.api.text.Text; +import org.spongepowered.api.text.format.TextColors; + +import javax.annotation.Nullable; +import java.io.File; +import java.util.UUID; + +import static com.google.common.base.Preconditions.checkArgument; +import static com.google.common.base.Preconditions.checkNotNull; + +public class SpongeCommandSender implements Actor { + + /** + * One time generated ID. + */ + private static final UUID DEFAULT_ID = UUID.fromString("a233eb4b-4cab-42cd-9fd9-7e7b9a3f74be"); + + private CommandSource sender; + private SpongeWorldEdit plugin; + + public SpongeCommandSender(SpongeWorldEdit plugin, CommandSource sender) { + checkNotNull(plugin); + checkNotNull(sender); + checkArgument(!(sender instanceof Player), "Cannot wrap a player"); + + this.plugin = plugin; + this.sender = sender; + } + + @Override + public UUID getUniqueId() { + return DEFAULT_ID; + } + + @Override + public String getName() { + return sender.getName(); + } + + @Override + public void printRaw(String msg) { + for (String part : msg.split("\n")) { + sender.sendMessage(Text.of(part)); + } + } + + @Override + public void print(String msg) { + for (String part : msg.split("\n")) { + sender.sendMessage(Text.of(TextColors.LIGHT_PURPLE, part)); + } + } + + @Override + public void printDebug(String msg) { + for (String part : msg.split("\n")) { + sender.sendMessage(Text.of(TextColors.GRAY, part)); + } + } + + @Override + public void printError(String msg) { + for (String part : msg.split("\n")) { + sender.sendMessage(Text.of(TextColors.RED, part)); + } + } + + @Override + public boolean canDestroyBedrock() { + return true; + } + + @Override + public String[] getGroups() { + return new String[0]; + } + + @Override + public boolean hasPermission(String perm) { + return true; + } + + @Override + public void checkPermission(String permission) throws AuthorizationException { + } + + @Override + public boolean isPlayer() { + return false; + } + + @Override + public File openFileOpenDialog(String[] extensions) { + return null; + } + + @Override + public File openFileSaveDialog(String[] extensions) { + return null; + } + + @Override + public void dispatchCUIEvent(CUIEvent event) { + } + + @Override + public SessionKey getSessionKey() { + return new SessionKey() { + @Nullable + @Override + public String getName() { + return null; + } + + @Override + public boolean isActive() { + return false; + } + + @Override + public boolean isPersistent() { + return false; + } + + @Override + public UUID getUniqueId() { + return DEFAULT_ID; + } + }; + } +} diff --git a/worldedit-sponge/src/main/java/com/sk89q/worldedit/sponge/SpongePlatform.java b/worldedit-sponge/src/main/java/com/sk89q/worldedit/sponge/SpongePlatform.java index 6790ccc61..746077905 100644 --- a/worldedit-sponge/src/main/java/com/sk89q/worldedit/sponge/SpongePlatform.java +++ b/worldedit-sponge/src/main/java/com/sk89q/worldedit/sponge/SpongePlatform.java @@ -19,23 +19,33 @@ package com.sk89q.worldedit.sponge; +import com.google.common.base.Joiner; +import com.google.common.collect.Lists; +import com.sk89q.minecraft.util.commands.CommandException; +import com.sk89q.minecraft.util.commands.CommandLocals; +import com.sk89q.worldedit.EditSession; +import com.sk89q.worldedit.LocalConfiguration; +import com.sk89q.worldedit.LocalSession; +import com.sk89q.worldedit.WorldEdit; import com.sk89q.worldedit.entity.Player; -import com.sk89q.worldedit.extension.platform.AbstractPlatform; -import com.sk89q.worldedit.extension.platform.Actor; -import com.sk89q.worldedit.extension.platform.Capability; -import com.sk89q.worldedit.extension.platform.MultiUserPlatform; -import com.sk89q.worldedit.extension.platform.Preference; +import com.sk89q.worldedit.event.platform.CommandEvent; +import com.sk89q.worldedit.event.platform.CommandSuggestionEvent; +import com.sk89q.worldedit.extension.platform.*; import com.sk89q.worldedit.util.command.CommandMapping; import com.sk89q.worldedit.util.command.Dispatcher; +import com.sk89q.worldedit.util.command.InvalidUsageException; import com.sk89q.worldedit.world.World; - +import net.minecraft.entity.player.EntityPlayerMP; import org.spongepowered.api.Sponge; +import org.spongepowered.api.command.CommandResult; +import org.spongepowered.api.command.CommandSource; import org.spongepowered.api.entity.EntityType; import org.spongepowered.api.item.ItemType; import org.spongepowered.api.scheduler.Task; +import org.spongepowered.api.text.Text; +import org.spongepowered.api.text.format.TextColors; import javax.annotation.Nullable; - import java.util.*; class SpongePlatform extends AbstractPlatform implements MultiUserPlatform { @@ -119,8 +129,23 @@ class SpongePlatform extends AbstractPlatform implements MultiUserPlatform { @Override public void registerCommands(Dispatcher dispatcher) { - for (final CommandMapping command : dispatcher.getCommands()) { - Sponge.getCommandManager().register(SpongeWorldEdit.inst, new CommandWrapper(command), command.getAllAliases()); + for (CommandMapping command : dispatcher.getCommands()) { + CommandAdapter adapter = new CommandAdapter(command) { + @Override + public CommandResult process(CommandSource source, String arguments) throws org.spongepowered.api.command.CommandException { + CommandEvent weEvent = new CommandEvent(SpongeWorldEdit.inst.wrapCommandSource(source), command.getPrimaryAlias() + " " + arguments); + WorldEdit.getInstance().getEventBus().post(weEvent); + return weEvent.isCancelled() ? CommandResult.success() : CommandResult.empty(); + } + + @Override + public List getSuggestions(CommandSource source, String arguments) throws org.spongepowered.api.command.CommandException { + CommandSuggestionEvent weEvent = new CommandSuggestionEvent(SpongeWorldEdit.inst.wrapCommandSource(source), command.getPrimaryAlias() + " " + arguments); + WorldEdit.getInstance().getEventBus().post(weEvent); + return weEvent.getSuggestions(); + } + }; + Sponge.getCommandManager().register(SpongeWorldEdit.inst, adapter, command.getAllAliases()); } } @@ -154,8 +179,7 @@ class SpongePlatform extends AbstractPlatform implements MultiUserPlatform { public Map getCapabilities() { Map capabilities = new EnumMap<>(Capability.class); capabilities.put(Capability.CONFIGURATION, Preference.PREFER_OTHERS); - // TODO WorldEditCUI Support - // capabilities.put(Capability.WORLDEDIT_CUI, Preference.NORMAL); + capabilities.put(Capability.WORLDEDIT_CUI, Preference.NORMAL); capabilities.put(Capability.GAME_HOOKS, Preference.NORMAL); capabilities.put(Capability.PERMISSIONS, Preference.NORMAL); capabilities.put(Capability.USER_COMMANDS, Preference.NORMAL); diff --git a/worldedit-sponge/src/main/java/com/sk89q/worldedit/sponge/SpongeWorldEdit.java b/worldedit-sponge/src/main/java/com/sk89q/worldedit/sponge/SpongeWorldEdit.java index 173e7e8e7..418a4aff1 100644 --- a/worldedit-sponge/src/main/java/com/sk89q/worldedit/sponge/SpongeWorldEdit.java +++ b/worldedit-sponge/src/main/java/com/sk89q/worldedit/sponge/SpongeWorldEdit.java @@ -20,9 +20,8 @@ package com.sk89q.worldedit.sponge; import com.google.inject.Inject; -import org.apache.logging.log4j.Logger; +import com.sk89q.worldedit.extension.platform.Actor; -import com.google.common.base.Joiner; import com.sk89q.worldedit.LocalSession; import com.sk89q.worldedit.WorldEdit; import com.sk89q.worldedit.WorldVector; @@ -33,13 +32,14 @@ import com.sk89q.worldedit.internal.LocalWorldAdapter; import java.io.File; import java.nio.file.Path; -import java.util.Map; import java.util.Optional; +import java.util.concurrent.TimeUnit; import org.spongepowered.api.Sponge; import org.spongepowered.api.block.BlockSnapshot; import org.spongepowered.api.block.BlockType; import org.spongepowered.api.block.BlockTypes; +import org.spongepowered.api.command.CommandSource; import org.spongepowered.api.config.ConfigManager; import org.spongepowered.api.entity.living.player.Player; import org.spongepowered.api.event.Listener; @@ -48,16 +48,16 @@ import org.spongepowered.api.event.cause.NamedCause; import org.spongepowered.api.event.game.state.*; import org.spongepowered.api.item.inventory.ItemStack; import org.spongepowered.api.plugin.Plugin; +import org.spongepowered.api.scheduler.Task; import org.spongepowered.api.world.Location; import org.spongepowered.api.world.World; -import org.spongepowered.mod.mixin.core.event.state.MixinEventServerAboutToStart; import static com.google.common.base.Preconditions.checkNotNull; /** * The Sponge implementation of WorldEdit. */ -@Plugin(id = "SpongeWorldEdit.MOD_ID", name = "WorldEdit", version = "%VERSION%") +@Plugin(id = SpongeWorldEdit.MOD_ID, name = "WorldEdit", version = "%VERSION%") public class SpongeWorldEdit { @Inject @@ -74,6 +74,10 @@ public class SpongeWorldEdit { private SpongeConfiguration config; private File workingDir; + public SpongeWorldEdit() { + inst = this; + } + @Listener public void preInit(GamePreInitializationEvent event) { // Setup working directory @@ -86,7 +90,7 @@ public class SpongeWorldEdit { config = new SpongeConfiguration(this); config.load(); - Sponge.getEventManager().registerListeners(this, ThreadSafeCache.getInstance()); + Task.builder().interval(30, TimeUnit.SECONDS).execute(ThreadSafeCache.getInstance()).submit(this); } @Listener @@ -96,7 +100,7 @@ public class SpongeWorldEdit { @Listener public void postInit(GamePostInitializationEvent event) { - logger.info("WorldEdit for Forge (version " + getInternalVersion() + ") is loaded"); + logger.info("WorldEdit for Sponge (version " + getInternalVersion() + ") is loaded"); } @Listener @@ -122,19 +126,6 @@ public class SpongeWorldEdit { WorldEdit.getInstance().getEventBus().post(new PlatformReadyEvent()); } - /*@Listener - public void onCommandEvent(CommandEvent event) { - if ((event.sender instanceof EntityPlayerMP)) { - if (((EntityPlayerMP) event.sender).worldObj.isRemote) return; - String[] split = new String[event.parameters.length + 1]; - System.arraycopy(event.parameters, 0, split, 1, event.parameters.length); - split[0] = event.command.getCommandName(); - com.sk89q.worldedit.event.platform.CommandEvent weEvent = - new com.sk89q.worldedit.event.platform.CommandEvent(wrap((EntityPlayerMP) event.sender), Joiner.on(" ").join(split)); - WorldEdit.getInstance().getEventBus().post(weEvent); - } - }*/ - @Listener public void onPlayerInteract(InteractBlockEvent event) { if (platform == null) { @@ -145,7 +136,7 @@ public class SpongeWorldEdit { WorldEdit we = WorldEdit.getInstance(); Optional optPlayer = event.getCause().get(NamedCause.SOURCE, Player.class); - SpongePlayer player = wrap(optPlayer.get()); + SpongePlayer player = wrapPlayer(optPlayer.get()); com.sk89q.worldedit.world.World world = player.getWorld(); BlockSnapshot targetBlock = event.getTargetBlock(); @@ -202,11 +193,19 @@ public class SpongeWorldEdit { * @param player the player * @return the WorldEdit player */ - public SpongePlayer wrap(Player player) { + public SpongePlayer wrapPlayer(Player player) { checkNotNull(player); return new SpongePlayer(platform, player); } + public Actor wrapCommandSource(CommandSource sender) { + if (sender instanceof Player) { + return wrapPlayer((Player) sender); + } + + return new SpongeCommandSender(this, sender); + } + /** * Get the session for a player. * @@ -215,7 +214,7 @@ public class SpongeWorldEdit { */ public LocalSession getSession(Player player) { checkNotNull(player); - return WorldEdit.getInstance().getSessionManager().get(wrap(player)); + return WorldEdit.getInstance().getSessionManager().get(wrapPlayer(player)); } /**