fabric: Implement entity/player selector argument types
This commit is contained in:
parent
2659eac93b
commit
78e7146ba3
18 changed files with 967 additions and 9 deletions
|
|
@ -28,8 +28,11 @@ import cloud.commandframework.CommandTree;
|
||||||
import cloud.commandframework.execution.AsynchronousCommandExecutionCoordinator;
|
import cloud.commandframework.execution.AsynchronousCommandExecutionCoordinator;
|
||||||
import cloud.commandframework.execution.CommandExecutionCoordinator;
|
import cloud.commandframework.execution.CommandExecutionCoordinator;
|
||||||
import cloud.commandframework.fabric.argument.FabricArgumentParsers;
|
import cloud.commandframework.fabric.argument.FabricArgumentParsers;
|
||||||
import cloud.commandframework.fabric.argument.server.MessageArgument;
|
|
||||||
import cloud.commandframework.fabric.data.Message;
|
import cloud.commandframework.fabric.data.Message;
|
||||||
|
import cloud.commandframework.fabric.data.MultipleEntitySelector;
|
||||||
|
import cloud.commandframework.fabric.data.MultiplePlayerSelector;
|
||||||
|
import cloud.commandframework.fabric.data.SingleEntitySelector;
|
||||||
|
import cloud.commandframework.fabric.data.SinglePlayerSelector;
|
||||||
import cloud.commandframework.meta.CommandMeta;
|
import cloud.commandframework.meta.CommandMeta;
|
||||||
import io.leangen.geantyref.TypeToken;
|
import io.leangen.geantyref.TypeToken;
|
||||||
import me.lucko.fabric.api.permissions.v0.Permissions;
|
import me.lucko.fabric.api.permissions.v0.Permissions;
|
||||||
|
|
@ -121,6 +124,24 @@ public final class FabricServerCommandManager<C> extends FabricCommandManager<C,
|
||||||
|
|
||||||
private void registerParsers() {
|
private void registerParsers() {
|
||||||
this.getParserRegistry().registerParserSupplier(TypeToken.get(Message.class), params -> FabricArgumentParsers.message());
|
this.getParserRegistry().registerParserSupplier(TypeToken.get(Message.class), params -> FabricArgumentParsers.message());
|
||||||
|
|
||||||
|
// Entity selectors
|
||||||
|
this.getParserRegistry().registerParserSupplier(
|
||||||
|
TypeToken.get(SinglePlayerSelector.class),
|
||||||
|
params -> FabricArgumentParsers.singlePlayerSelector()
|
||||||
|
);
|
||||||
|
this.getParserRegistry().registerParserSupplier(
|
||||||
|
TypeToken.get(MultiplePlayerSelector.class),
|
||||||
|
params -> FabricArgumentParsers.multiplePlayerSelector()
|
||||||
|
);
|
||||||
|
this.getParserRegistry().registerParserSupplier(
|
||||||
|
TypeToken.get(SingleEntitySelector.class),
|
||||||
|
params -> FabricArgumentParsers.singleEntitySelector()
|
||||||
|
);
|
||||||
|
this.getParserRegistry().registerParserSupplier(
|
||||||
|
TypeToken.get(MultipleEntitySelector.class),
|
||||||
|
params -> FabricArgumentParsers.multipleEntitySelector()
|
||||||
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
|
|
||||||
|
|
@ -28,20 +28,25 @@ import cloud.commandframework.arguments.parser.ArgumentParseResult;
|
||||||
import cloud.commandframework.arguments.parser.ArgumentParser;
|
import cloud.commandframework.arguments.parser.ArgumentParser;
|
||||||
import cloud.commandframework.brigadier.argument.WrappedBrigadierParser;
|
import cloud.commandframework.brigadier.argument.WrappedBrigadierParser;
|
||||||
import cloud.commandframework.fabric.FabricCommandContextKeys;
|
import cloud.commandframework.fabric.FabricCommandContextKeys;
|
||||||
import cloud.commandframework.fabric.argument.server.MessageArgument;
|
|
||||||
import cloud.commandframework.fabric.data.Message;
|
import cloud.commandframework.fabric.data.Message;
|
||||||
import cloud.commandframework.fabric.data.MinecraftTime;
|
import cloud.commandframework.fabric.data.MinecraftTime;
|
||||||
|
import cloud.commandframework.fabric.data.MultipleEntitySelector;
|
||||||
|
import cloud.commandframework.fabric.data.MultiplePlayerSelector;
|
||||||
|
import cloud.commandframework.fabric.data.SingleEntitySelector;
|
||||||
|
import cloud.commandframework.fabric.data.SinglePlayerSelector;
|
||||||
|
import cloud.commandframework.fabric.internal.EntitySelectorAccess;
|
||||||
import cloud.commandframework.fabric.mixin.MessageArgumentTypeMessageFormatAccess;
|
import cloud.commandframework.fabric.mixin.MessageArgumentTypeMessageFormatAccess;
|
||||||
import cloud.commandframework.fabric.mixin.MessageArgumentTypeMessageSelectorAccess;
|
import cloud.commandframework.fabric.mixin.MessageArgumentTypeMessageSelectorAccess;
|
||||||
import com.mojang.brigadier.exceptions.CommandSyntaxException;
|
import com.mojang.brigadier.exceptions.CommandSyntaxException;
|
||||||
import net.minecraft.command.CommandSource;
|
import net.minecraft.command.CommandSource;
|
||||||
import net.minecraft.command.argument.FunctionArgumentType;
|
import net.minecraft.command.EntitySelector;
|
||||||
|
import net.minecraft.command.argument.EntityArgumentType;
|
||||||
import net.minecraft.command.argument.MessageArgumentType;
|
import net.minecraft.command.argument.MessageArgumentType;
|
||||||
import net.minecraft.command.argument.TimeArgumentType;
|
import net.minecraft.command.argument.TimeArgumentType;
|
||||||
import net.minecraft.entity.Entity;
|
import net.minecraft.entity.Entity;
|
||||||
import net.minecraft.server.command.ServerCommandSource;
|
import net.minecraft.server.command.ServerCommandSource;
|
||||||
import net.minecraft.server.function.CommandFunction;
|
|
||||||
import net.minecraft.text.Text;
|
import net.minecraft.text.Text;
|
||||||
|
import org.checkerframework.checker.nullness.qual.NonNull;
|
||||||
|
|
||||||
import java.util.Collection;
|
import java.util.Collection;
|
||||||
import java.util.Collections;
|
import java.util.Collections;
|
||||||
|
|
@ -79,12 +84,88 @@ public final class FabricArgumentParsers {
|
||||||
}
|
}
|
||||||
*/
|
*/
|
||||||
|
|
||||||
|
public static <C> ArgumentParser<C, SinglePlayerSelector> singlePlayerSelector() {
|
||||||
|
return new WrappedBrigadierParser<C, EntitySelector>(EntityArgumentType.player())
|
||||||
|
.map((ctx, entitySelector) -> {
|
||||||
|
final CommandSource either = ctx.get(FabricCommandContextKeys.NATIVE_COMMAND_SOURCE);
|
||||||
|
if (!(either instanceof ServerCommandSource)) {
|
||||||
|
return ArgumentParseResult.failure(serverOnly());
|
||||||
|
}
|
||||||
|
try {
|
||||||
|
return ArgumentParseResult.success(new SinglePlayerSelector(
|
||||||
|
((EntitySelectorAccess) entitySelector).inputString(),
|
||||||
|
entitySelector,
|
||||||
|
entitySelector.getPlayer((ServerCommandSource) either)
|
||||||
|
));
|
||||||
|
} catch (final CommandSyntaxException ex) {
|
||||||
|
return ArgumentParseResult.failure(ex);
|
||||||
|
}
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
public static <C> ArgumentParser<C, MultiplePlayerSelector> multiplePlayerSelector() {
|
||||||
|
return new WrappedBrigadierParser<C, EntitySelector>(EntityArgumentType.players())
|
||||||
|
.map((ctx, entitySelector) -> {
|
||||||
|
final CommandSource either = ctx.get(FabricCommandContextKeys.NATIVE_COMMAND_SOURCE);
|
||||||
|
if (!(either instanceof ServerCommandSource)) {
|
||||||
|
return ArgumentParseResult.failure(serverOnly());
|
||||||
|
}
|
||||||
|
try {
|
||||||
|
return ArgumentParseResult.success(new MultiplePlayerSelector(
|
||||||
|
((EntitySelectorAccess) entitySelector).inputString(),
|
||||||
|
entitySelector,
|
||||||
|
entitySelector.getPlayers((ServerCommandSource) either)
|
||||||
|
));
|
||||||
|
} catch (final CommandSyntaxException ex) {
|
||||||
|
return ArgumentParseResult.failure(ex);
|
||||||
|
}
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
public static <C> ArgumentParser<C, SingleEntitySelector> singleEntitySelector() {
|
||||||
|
return new WrappedBrigadierParser<C, EntitySelector>(EntityArgumentType.entity())
|
||||||
|
.map((ctx, entitySelector) -> {
|
||||||
|
final CommandSource either = ctx.get(FabricCommandContextKeys.NATIVE_COMMAND_SOURCE);
|
||||||
|
if (!(either instanceof ServerCommandSource)) {
|
||||||
|
return ArgumentParseResult.failure(serverOnly());
|
||||||
|
}
|
||||||
|
try {
|
||||||
|
return ArgumentParseResult.success(new SingleEntitySelector(
|
||||||
|
((EntitySelectorAccess) entitySelector).inputString(),
|
||||||
|
entitySelector,
|
||||||
|
entitySelector.getEntity((ServerCommandSource) either)
|
||||||
|
));
|
||||||
|
} catch (final CommandSyntaxException ex) {
|
||||||
|
return ArgumentParseResult.failure(ex);
|
||||||
|
}
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
public static <C> ArgumentParser<C, MultipleEntitySelector> multipleEntitySelector() {
|
||||||
|
return new WrappedBrigadierParser<C, EntitySelector>(EntityArgumentType.entities())
|
||||||
|
.map((ctx, entitySelector) -> {
|
||||||
|
final CommandSource either = ctx.get(FabricCommandContextKeys.NATIVE_COMMAND_SOURCE);
|
||||||
|
if (!(either instanceof ServerCommandSource)) {
|
||||||
|
return ArgumentParseResult.failure(serverOnly());
|
||||||
|
}
|
||||||
|
try {
|
||||||
|
return ArgumentParseResult.success(new MultipleEntitySelector(
|
||||||
|
((EntitySelectorAccess) entitySelector).inputString(),
|
||||||
|
entitySelector,
|
||||||
|
Collections.unmodifiableCollection(entitySelector.getEntities((ServerCommandSource) either))
|
||||||
|
));
|
||||||
|
} catch (final CommandSyntaxException ex) {
|
||||||
|
return ArgumentParseResult.failure(ex);
|
||||||
|
}
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
public static <C> ArgumentParser<C, Message> message() {
|
public static <C> ArgumentParser<C, Message> message() {
|
||||||
return new WrappedBrigadierParser<C, MessageArgumentType.MessageFormat>(MessageArgumentType.message())
|
return new WrappedBrigadierParser<C, MessageArgumentType.MessageFormat>(MessageArgumentType.message())
|
||||||
.map((ctx, format) -> {
|
.map((ctx, format) -> {
|
||||||
final CommandSource either = ctx.get(FabricCommandContextKeys.NATIVE_COMMAND_SOURCE);
|
final CommandSource either = ctx.get(FabricCommandContextKeys.NATIVE_COMMAND_SOURCE);
|
||||||
if (!(either instanceof ServerCommandSource)) {
|
if (!(either instanceof ServerCommandSource)) {
|
||||||
return ArgumentParseResult.failure(new IllegalStateException("This argument is server-only"));
|
return ArgumentParseResult.failure(serverOnly());
|
||||||
}
|
}
|
||||||
try {
|
try {
|
||||||
return ArgumentParseResult.success(MessageImpl.from(
|
return ArgumentParseResult.success(MessageImpl.from(
|
||||||
|
|
@ -98,6 +179,10 @@ public final class FabricArgumentParsers {
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private static @NonNull IllegalStateException serverOnly() {
|
||||||
|
return new IllegalStateException("This argument is server-only");
|
||||||
|
}
|
||||||
|
|
||||||
static final class MessageImpl implements Message {
|
static final class MessageImpl implements Message {
|
||||||
private final Collection<Entity> mentionedEntities;
|
private final Collection<Entity> mentionedEntities;
|
||||||
private final Text contents;
|
private final Text contents;
|
||||||
|
|
|
||||||
|
|
@ -0,0 +1,110 @@
|
||||||
|
//
|
||||||
|
// MIT License
|
||||||
|
//
|
||||||
|
// Copyright (c) 2021 Alexander Söderberg & Contributors
|
||||||
|
//
|
||||||
|
// Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||||
|
// of this software and associated documentation files (the "Software"), to deal
|
||||||
|
// in the Software without restriction, including without limitation the rights
|
||||||
|
// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
||||||
|
// copies of the Software, and to permit persons to whom the Software is
|
||||||
|
// furnished to do so, subject to the following conditions:
|
||||||
|
//
|
||||||
|
// The above copyright notice and this permission notice shall be included in all
|
||||||
|
// copies or substantial portions of the Software.
|
||||||
|
//
|
||||||
|
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||||
|
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||||
|
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||||
|
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||||
|
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||||
|
// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
|
||||||
|
// SOFTWARE.
|
||||||
|
//
|
||||||
|
package cloud.commandframework.fabric.argument;
|
||||||
|
|
||||||
|
import cloud.commandframework.arguments.CommandArgument;
|
||||||
|
import cloud.commandframework.context.CommandContext;
|
||||||
|
import cloud.commandframework.fabric.data.MultipleEntitySelector;
|
||||||
|
import org.checkerframework.checker.nullness.qual.NonNull;
|
||||||
|
import org.checkerframework.checker.nullness.qual.Nullable;
|
||||||
|
|
||||||
|
import java.util.List;
|
||||||
|
import java.util.function.BiFunction;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* An argument for selecting multiple entities
|
||||||
|
*
|
||||||
|
* @param <C> the sender type
|
||||||
|
* @since 1.5.0
|
||||||
|
*/
|
||||||
|
public final class MultipleEntitySelectorArgument<C> extends CommandArgument<C, MultipleEntitySelector> {
|
||||||
|
|
||||||
|
MultipleEntitySelectorArgument(
|
||||||
|
final boolean required,
|
||||||
|
final @NonNull String name,
|
||||||
|
final @NonNull String defaultValue,
|
||||||
|
final @Nullable BiFunction<CommandContext<C>, String, List<String>> suggestionsProvider
|
||||||
|
) {
|
||||||
|
super(
|
||||||
|
required,
|
||||||
|
name,
|
||||||
|
FabricArgumentParsers.multipleEntitySelector(),
|
||||||
|
defaultValue,
|
||||||
|
MultipleEntitySelector.class,
|
||||||
|
suggestionsProvider
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Create a new builder.
|
||||||
|
*
|
||||||
|
* @param name Name of the argument
|
||||||
|
* @param <C> Command sender type
|
||||||
|
* @return Created builder
|
||||||
|
*/
|
||||||
|
public static <C> MultipleEntitySelectorArgument.@NonNull Builder<C> newBuilder(final @NonNull String name) {
|
||||||
|
return new MultipleEntitySelectorArgument.Builder<>(name);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Create a new required command argument.
|
||||||
|
*
|
||||||
|
* @param name Component name
|
||||||
|
* @param <C> Command sender type
|
||||||
|
* @return Created argument
|
||||||
|
*/
|
||||||
|
public static <C> @NonNull MultipleEntitySelectorArgument<C> of(final @NonNull String name) {
|
||||||
|
return MultipleEntitySelectorArgument.<C>newBuilder(name).asRequired().build();
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Create a new optional command argument
|
||||||
|
*
|
||||||
|
* @param name Component name
|
||||||
|
* @param <C> Command sender type
|
||||||
|
* @return Created argument
|
||||||
|
*/
|
||||||
|
public static <C> @NonNull MultipleEntitySelectorArgument<C> optional(final @NonNull String name) {
|
||||||
|
return MultipleEntitySelectorArgument.<C>newBuilder(name).asOptional().build();
|
||||||
|
}
|
||||||
|
|
||||||
|
public static final class Builder<C> extends TypedBuilder<C, MultipleEntitySelector, Builder<C>> {
|
||||||
|
|
||||||
|
Builder(final @NonNull String name) {
|
||||||
|
super(MultipleEntitySelector.class, name);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Build a multiple entity selector argument
|
||||||
|
*
|
||||||
|
* @return Constructed argument
|
||||||
|
*/
|
||||||
|
@Override
|
||||||
|
public @NonNull MultipleEntitySelectorArgument<C> build() {
|
||||||
|
return new MultipleEntitySelectorArgument<>(this.isRequired(), this.getName(), this.getDefaultValue(), this.getSuggestionsProvider());
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
|
@ -0,0 +1,110 @@
|
||||||
|
//
|
||||||
|
// MIT License
|
||||||
|
//
|
||||||
|
// Copyright (c) 2021 Alexander Söderberg & Contributors
|
||||||
|
//
|
||||||
|
// Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||||
|
// of this software and associated documentation files (the "Software"), to deal
|
||||||
|
// in the Software without restriction, including without limitation the rights
|
||||||
|
// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
||||||
|
// copies of the Software, and to permit persons to whom the Software is
|
||||||
|
// furnished to do so, subject to the following conditions:
|
||||||
|
//
|
||||||
|
// The above copyright notice and this permission notice shall be included in all
|
||||||
|
// copies or substantial portions of the Software.
|
||||||
|
//
|
||||||
|
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||||
|
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||||
|
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||||
|
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||||
|
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||||
|
// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
|
||||||
|
// SOFTWARE.
|
||||||
|
//
|
||||||
|
package cloud.commandframework.fabric.argument;
|
||||||
|
|
||||||
|
import cloud.commandframework.arguments.CommandArgument;
|
||||||
|
import cloud.commandframework.context.CommandContext;
|
||||||
|
import cloud.commandframework.fabric.data.MultiplePlayerSelector;
|
||||||
|
import org.checkerframework.checker.nullness.qual.NonNull;
|
||||||
|
import org.checkerframework.checker.nullness.qual.Nullable;
|
||||||
|
|
||||||
|
import java.util.List;
|
||||||
|
import java.util.function.BiFunction;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* An argument for selecting multiple players
|
||||||
|
*
|
||||||
|
* @param <C> the sender type
|
||||||
|
* @since 1.5.0
|
||||||
|
*/
|
||||||
|
public final class MultiplePlayerSelectorArgument<C> extends CommandArgument<C, MultiplePlayerSelector> {
|
||||||
|
|
||||||
|
MultiplePlayerSelectorArgument(
|
||||||
|
final boolean required,
|
||||||
|
final @NonNull String name,
|
||||||
|
final @NonNull String defaultValue,
|
||||||
|
final @Nullable BiFunction<CommandContext<C>, String, List<String>> suggestionsProvider
|
||||||
|
) {
|
||||||
|
super(
|
||||||
|
required,
|
||||||
|
name,
|
||||||
|
FabricArgumentParsers.multiplePlayerSelector(),
|
||||||
|
defaultValue,
|
||||||
|
MultiplePlayerSelector.class,
|
||||||
|
suggestionsProvider
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Create a new builder.
|
||||||
|
*
|
||||||
|
* @param name Name of the argument
|
||||||
|
* @param <C> Command sender type
|
||||||
|
* @return Created builder
|
||||||
|
*/
|
||||||
|
public static <C> MultiplePlayerSelectorArgument.@NonNull Builder<C> newBuilder(final @NonNull String name) {
|
||||||
|
return new MultiplePlayerSelectorArgument.Builder<>(name);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Create a new required command argument.
|
||||||
|
*
|
||||||
|
* @param name Component name
|
||||||
|
* @param <C> Command sender type
|
||||||
|
* @return Created argument
|
||||||
|
*/
|
||||||
|
public static <C> @NonNull MultiplePlayerSelectorArgument<C> of(final @NonNull String name) {
|
||||||
|
return MultiplePlayerSelectorArgument.<C>newBuilder(name).asRequired().build();
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Create a new optional command argument
|
||||||
|
*
|
||||||
|
* @param name Component name
|
||||||
|
* @param <C> Command sender type
|
||||||
|
* @return Created argument
|
||||||
|
*/
|
||||||
|
public static <C> @NonNull MultiplePlayerSelectorArgument<C> optional(final @NonNull String name) {
|
||||||
|
return MultiplePlayerSelectorArgument.<C>newBuilder(name).asOptional().build();
|
||||||
|
}
|
||||||
|
|
||||||
|
public static final class Builder<C> extends TypedBuilder<C, MultiplePlayerSelector, Builder<C>> {
|
||||||
|
|
||||||
|
Builder(final @NonNull String name) {
|
||||||
|
super(MultiplePlayerSelector.class, name);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Build a multiple player selector argument
|
||||||
|
*
|
||||||
|
* @return Constructed argument
|
||||||
|
*/
|
||||||
|
@Override
|
||||||
|
public @NonNull MultiplePlayerSelectorArgument<C> build() {
|
||||||
|
return new MultiplePlayerSelectorArgument<>(this.isRequired(), this.getName(), this.getDefaultValue(), this.getSuggestionsProvider());
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
|
@ -0,0 +1,110 @@
|
||||||
|
//
|
||||||
|
// MIT License
|
||||||
|
//
|
||||||
|
// Copyright (c) 2021 Alexander Söderberg & Contributors
|
||||||
|
//
|
||||||
|
// Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||||
|
// of this software and associated documentation files (the "Software"), to deal
|
||||||
|
// in the Software without restriction, including without limitation the rights
|
||||||
|
// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
||||||
|
// copies of the Software, and to permit persons to whom the Software is
|
||||||
|
// furnished to do so, subject to the following conditions:
|
||||||
|
//
|
||||||
|
// The above copyright notice and this permission notice shall be included in all
|
||||||
|
// copies or substantial portions of the Software.
|
||||||
|
//
|
||||||
|
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||||
|
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||||
|
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||||
|
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||||
|
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||||
|
// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
|
||||||
|
// SOFTWARE.
|
||||||
|
//
|
||||||
|
package cloud.commandframework.fabric.argument;
|
||||||
|
|
||||||
|
import cloud.commandframework.arguments.CommandArgument;
|
||||||
|
import cloud.commandframework.context.CommandContext;
|
||||||
|
import cloud.commandframework.fabric.data.SingleEntitySelector;
|
||||||
|
import org.checkerframework.checker.nullness.qual.NonNull;
|
||||||
|
import org.checkerframework.checker.nullness.qual.Nullable;
|
||||||
|
|
||||||
|
import java.util.List;
|
||||||
|
import java.util.function.BiFunction;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* An argument for selecting a single entity
|
||||||
|
*
|
||||||
|
* @param <C> the sender type
|
||||||
|
* @since 1.5.0
|
||||||
|
*/
|
||||||
|
public final class SingleEntitySelectorArgument<C> extends CommandArgument<C, SingleEntitySelector> {
|
||||||
|
|
||||||
|
SingleEntitySelectorArgument(
|
||||||
|
final boolean required,
|
||||||
|
final @NonNull String name,
|
||||||
|
final @NonNull String defaultValue,
|
||||||
|
final @Nullable BiFunction<CommandContext<C>, String, List<String>> suggestionsProvider
|
||||||
|
) {
|
||||||
|
super(
|
||||||
|
required,
|
||||||
|
name,
|
||||||
|
FabricArgumentParsers.singleEntitySelector(),
|
||||||
|
defaultValue,
|
||||||
|
SingleEntitySelector.class,
|
||||||
|
suggestionsProvider
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Create a new builder.
|
||||||
|
*
|
||||||
|
* @param name Name of the argument
|
||||||
|
* @param <C> Command sender type
|
||||||
|
* @return Created builder
|
||||||
|
*/
|
||||||
|
public static <C> SingleEntitySelectorArgument.@NonNull Builder<C> newBuilder(final @NonNull String name) {
|
||||||
|
return new SingleEntitySelectorArgument.Builder<>(name);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Create a new required command argument.
|
||||||
|
*
|
||||||
|
* @param name Component name
|
||||||
|
* @param <C> Command sender type
|
||||||
|
* @return Created argument
|
||||||
|
*/
|
||||||
|
public static <C> @NonNull SingleEntitySelectorArgument<C> of(final @NonNull String name) {
|
||||||
|
return SingleEntitySelectorArgument.<C>newBuilder(name).asRequired().build();
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Create a new optional command argument
|
||||||
|
*
|
||||||
|
* @param name Component name
|
||||||
|
* @param <C> Command sender type
|
||||||
|
* @return Created argument
|
||||||
|
*/
|
||||||
|
public static <C> @NonNull SingleEntitySelectorArgument<C> optional(final @NonNull String name) {
|
||||||
|
return SingleEntitySelectorArgument.<C>newBuilder(name).asOptional().build();
|
||||||
|
}
|
||||||
|
|
||||||
|
public static final class Builder<C> extends TypedBuilder<C, SingleEntitySelector, Builder<C>> {
|
||||||
|
|
||||||
|
Builder(final @NonNull String name) {
|
||||||
|
super(SingleEntitySelector.class, name);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Build a single entity selector argument
|
||||||
|
*
|
||||||
|
* @return Constructed argument
|
||||||
|
*/
|
||||||
|
@Override
|
||||||
|
public @NonNull SingleEntitySelectorArgument<C> build() {
|
||||||
|
return new SingleEntitySelectorArgument<>(this.isRequired(), this.getName(), this.getDefaultValue(), this.getSuggestionsProvider());
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
|
@ -0,0 +1,110 @@
|
||||||
|
//
|
||||||
|
// MIT License
|
||||||
|
//
|
||||||
|
// Copyright (c) 2021 Alexander Söderberg & Contributors
|
||||||
|
//
|
||||||
|
// Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||||
|
// of this software and associated documentation files (the "Software"), to deal
|
||||||
|
// in the Software without restriction, including without limitation the rights
|
||||||
|
// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
||||||
|
// copies of the Software, and to permit persons to whom the Software is
|
||||||
|
// furnished to do so, subject to the following conditions:
|
||||||
|
//
|
||||||
|
// The above copyright notice and this permission notice shall be included in all
|
||||||
|
// copies or substantial portions of the Software.
|
||||||
|
//
|
||||||
|
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||||
|
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||||
|
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||||
|
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||||
|
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||||
|
// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
|
||||||
|
// SOFTWARE.
|
||||||
|
//
|
||||||
|
package cloud.commandframework.fabric.argument;
|
||||||
|
|
||||||
|
import cloud.commandframework.arguments.CommandArgument;
|
||||||
|
import cloud.commandframework.context.CommandContext;
|
||||||
|
import cloud.commandframework.fabric.data.SinglePlayerSelector;
|
||||||
|
import org.checkerframework.checker.nullness.qual.NonNull;
|
||||||
|
import org.checkerframework.checker.nullness.qual.Nullable;
|
||||||
|
|
||||||
|
import java.util.List;
|
||||||
|
import java.util.function.BiFunction;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* An argument for selecting a single player
|
||||||
|
*
|
||||||
|
* @param <C> the sender type
|
||||||
|
* @since 1.5.0
|
||||||
|
*/
|
||||||
|
public final class SinglePlayerSelectorArgument<C> extends CommandArgument<C, SinglePlayerSelector> {
|
||||||
|
|
||||||
|
SinglePlayerSelectorArgument(
|
||||||
|
final boolean required,
|
||||||
|
final @NonNull String name,
|
||||||
|
final @NonNull String defaultValue,
|
||||||
|
final @Nullable BiFunction<CommandContext<C>, String, List<String>> suggestionsProvider
|
||||||
|
) {
|
||||||
|
super(
|
||||||
|
required,
|
||||||
|
name,
|
||||||
|
FabricArgumentParsers.singlePlayerSelector(),
|
||||||
|
defaultValue,
|
||||||
|
SinglePlayerSelector.class,
|
||||||
|
suggestionsProvider
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Create a new builder.
|
||||||
|
*
|
||||||
|
* @param name Name of the argument
|
||||||
|
* @param <C> Command sender type
|
||||||
|
* @return Created builder
|
||||||
|
*/
|
||||||
|
public static <C> SinglePlayerSelectorArgument.@NonNull Builder<C> newBuilder(final @NonNull String name) {
|
||||||
|
return new SinglePlayerSelectorArgument.Builder<>(name);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Create a new required command argument.
|
||||||
|
*
|
||||||
|
* @param name Component name
|
||||||
|
* @param <C> Command sender type
|
||||||
|
* @return Created argument
|
||||||
|
*/
|
||||||
|
public static <C> @NonNull SinglePlayerSelectorArgument<C> of(final @NonNull String name) {
|
||||||
|
return SinglePlayerSelectorArgument.<C>newBuilder(name).asRequired().build();
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Create a new optional command argument
|
||||||
|
*
|
||||||
|
* @param name Component name
|
||||||
|
* @param <C> Command sender type
|
||||||
|
* @return Created argument
|
||||||
|
*/
|
||||||
|
public static <C> @NonNull SinglePlayerSelectorArgument<C> optional(final @NonNull String name) {
|
||||||
|
return SinglePlayerSelectorArgument.<C>newBuilder(name).asOptional().build();
|
||||||
|
}
|
||||||
|
|
||||||
|
public static final class Builder<C> extends TypedBuilder<C, SinglePlayerSelector, Builder<C>> {
|
||||||
|
|
||||||
|
Builder(final @NonNull String name) {
|
||||||
|
super(SinglePlayerSelector.class, name);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Build a single player selector argument
|
||||||
|
*
|
||||||
|
* @return Constructed argument
|
||||||
|
*/
|
||||||
|
@Override
|
||||||
|
public @NonNull SinglePlayerSelectorArgument<C> build() {
|
||||||
|
return new SinglePlayerSelectorArgument<>(this.isRequired(), this.getName(), this.getDefaultValue(), this.getSuggestionsProvider());
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
|
@ -0,0 +1,63 @@
|
||||||
|
//
|
||||||
|
// MIT License
|
||||||
|
//
|
||||||
|
// Copyright (c) 2021 Alexander Söderberg & Contributors
|
||||||
|
//
|
||||||
|
// Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||||
|
// of this software and associated documentation files (the "Software"), to deal
|
||||||
|
// in the Software without restriction, including without limitation the rights
|
||||||
|
// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
||||||
|
// copies of the Software, and to permit persons to whom the Software is
|
||||||
|
// furnished to do so, subject to the following conditions:
|
||||||
|
//
|
||||||
|
// The above copyright notice and this permission notice shall be included in all
|
||||||
|
// copies or substantial portions of the Software.
|
||||||
|
//
|
||||||
|
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||||
|
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||||
|
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||||
|
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||||
|
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||||
|
// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
|
||||||
|
// SOFTWARE.
|
||||||
|
//
|
||||||
|
package cloud.commandframework.fabric.data;
|
||||||
|
|
||||||
|
import net.minecraft.command.EntitySelector;
|
||||||
|
import net.minecraft.entity.Entity;
|
||||||
|
import org.checkerframework.checker.nullness.qual.NonNull;
|
||||||
|
|
||||||
|
import java.util.Collection;
|
||||||
|
|
||||||
|
public final class MultipleEntitySelector implements Selector<Entity> {
|
||||||
|
|
||||||
|
private final String inputString;
|
||||||
|
private final net.minecraft.command.EntitySelector entitySelector;
|
||||||
|
private final Collection<Entity> selectedEntities;
|
||||||
|
|
||||||
|
public MultipleEntitySelector(
|
||||||
|
final @NonNull String inputString,
|
||||||
|
final @NonNull EntitySelector entitySelector,
|
||||||
|
final @NonNull Collection<Entity> selectedEntities
|
||||||
|
) {
|
||||||
|
this.inputString = inputString;
|
||||||
|
this.entitySelector = entitySelector;
|
||||||
|
this.selectedEntities = selectedEntities;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public @NonNull String getInput() {
|
||||||
|
return this.inputString;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public @NonNull EntitySelector getSelector() {
|
||||||
|
return this.entitySelector;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public @NonNull Collection<Entity> get() {
|
||||||
|
return this.selectedEntities;
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
|
@ -0,0 +1,63 @@
|
||||||
|
//
|
||||||
|
// MIT License
|
||||||
|
//
|
||||||
|
// Copyright (c) 2021 Alexander Söderberg & Contributors
|
||||||
|
//
|
||||||
|
// Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||||
|
// of this software and associated documentation files (the "Software"), to deal
|
||||||
|
// in the Software without restriction, including without limitation the rights
|
||||||
|
// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
||||||
|
// copies of the Software, and to permit persons to whom the Software is
|
||||||
|
// furnished to do so, subject to the following conditions:
|
||||||
|
//
|
||||||
|
// The above copyright notice and this permission notice shall be included in all
|
||||||
|
// copies or substantial portions of the Software.
|
||||||
|
//
|
||||||
|
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||||
|
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||||
|
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||||
|
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||||
|
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||||
|
// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
|
||||||
|
// SOFTWARE.
|
||||||
|
//
|
||||||
|
package cloud.commandframework.fabric.data;
|
||||||
|
|
||||||
|
import net.minecraft.command.EntitySelector;
|
||||||
|
import net.minecraft.server.network.ServerPlayerEntity;
|
||||||
|
import org.checkerframework.checker.nullness.qual.NonNull;
|
||||||
|
|
||||||
|
import java.util.Collection;
|
||||||
|
|
||||||
|
public final class MultiplePlayerSelector implements Selector<ServerPlayerEntity> {
|
||||||
|
|
||||||
|
private final String inputString;
|
||||||
|
private final EntitySelector entitySelector;
|
||||||
|
private final Collection<ServerPlayerEntity> selectedPlayers;
|
||||||
|
|
||||||
|
public MultiplePlayerSelector(
|
||||||
|
final @NonNull String inputString,
|
||||||
|
final @NonNull EntitySelector entitySelector,
|
||||||
|
final @NonNull Collection<ServerPlayerEntity> selectedPlayers
|
||||||
|
) {
|
||||||
|
this.inputString = inputString;
|
||||||
|
this.entitySelector = entitySelector;
|
||||||
|
this.selectedPlayers = selectedPlayers;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public @NonNull String getInput() {
|
||||||
|
return this.inputString;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public @NonNull EntitySelector getSelector() {
|
||||||
|
return this.entitySelector;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public @NonNull Collection<ServerPlayerEntity> get() {
|
||||||
|
return this.selectedPlayers;
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
|
@ -0,0 +1,61 @@
|
||||||
|
//
|
||||||
|
// MIT License
|
||||||
|
//
|
||||||
|
// Copyright (c) 2021 Alexander Söderberg & Contributors
|
||||||
|
//
|
||||||
|
// Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||||
|
// of this software and associated documentation files (the "Software"), to deal
|
||||||
|
// in the Software without restriction, including without limitation the rights
|
||||||
|
// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
||||||
|
// copies of the Software, and to permit persons to whom the Software is
|
||||||
|
// furnished to do so, subject to the following conditions:
|
||||||
|
//
|
||||||
|
// The above copyright notice and this permission notice shall be included in all
|
||||||
|
// copies or substantial portions of the Software.
|
||||||
|
//
|
||||||
|
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||||
|
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||||
|
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||||
|
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||||
|
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||||
|
// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
|
||||||
|
// SOFTWARE.
|
||||||
|
//
|
||||||
|
package cloud.commandframework.fabric.data;
|
||||||
|
|
||||||
|
import net.minecraft.command.EntitySelector;
|
||||||
|
import net.minecraft.entity.Entity;
|
||||||
|
import org.checkerframework.checker.nullness.qual.NonNull;
|
||||||
|
|
||||||
|
public final class SingleEntitySelector implements Selector.Single<Entity> {
|
||||||
|
|
||||||
|
private final String inputString;
|
||||||
|
private final EntitySelector entitySelector;
|
||||||
|
private final Entity selectedEntity;
|
||||||
|
|
||||||
|
public SingleEntitySelector(
|
||||||
|
final @NonNull String inputString,
|
||||||
|
final @NonNull EntitySelector entitySelector,
|
||||||
|
final @NonNull Entity selectedEntity
|
||||||
|
) {
|
||||||
|
this.inputString = inputString;
|
||||||
|
this.entitySelector = entitySelector;
|
||||||
|
this.selectedEntity = selectedEntity;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public @NonNull String getInput() {
|
||||||
|
return this.inputString;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public @NonNull EntitySelector getSelector() {
|
||||||
|
return this.entitySelector;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public @NonNull Entity getSingle() {
|
||||||
|
return this.selectedEntity;
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
|
@ -0,0 +1,61 @@
|
||||||
|
//
|
||||||
|
// MIT License
|
||||||
|
//
|
||||||
|
// Copyright (c) 2021 Alexander Söderberg & Contributors
|
||||||
|
//
|
||||||
|
// Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||||
|
// of this software and associated documentation files (the "Software"), to deal
|
||||||
|
// in the Software without restriction, including without limitation the rights
|
||||||
|
// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
||||||
|
// copies of the Software, and to permit persons to whom the Software is
|
||||||
|
// furnished to do so, subject to the following conditions:
|
||||||
|
//
|
||||||
|
// The above copyright notice and this permission notice shall be included in all
|
||||||
|
// copies or substantial portions of the Software.
|
||||||
|
//
|
||||||
|
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||||
|
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||||
|
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||||
|
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||||
|
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||||
|
// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
|
||||||
|
// SOFTWARE.
|
||||||
|
//
|
||||||
|
package cloud.commandframework.fabric.data;
|
||||||
|
|
||||||
|
import net.minecraft.command.EntitySelector;
|
||||||
|
import net.minecraft.server.network.ServerPlayerEntity;
|
||||||
|
import org.checkerframework.checker.nullness.qual.NonNull;
|
||||||
|
|
||||||
|
public final class SinglePlayerSelector implements Selector.Single<ServerPlayerEntity> {
|
||||||
|
|
||||||
|
private final String inputString;
|
||||||
|
private final EntitySelector entitySelector;
|
||||||
|
private final ServerPlayerEntity selectedPlayer;
|
||||||
|
|
||||||
|
public SinglePlayerSelector(
|
||||||
|
final @NonNull String inputString,
|
||||||
|
final @NonNull EntitySelector entitySelector,
|
||||||
|
final @NonNull ServerPlayerEntity selectedPlayer
|
||||||
|
) {
|
||||||
|
this.inputString = inputString;
|
||||||
|
this.entitySelector = entitySelector;
|
||||||
|
this.selectedPlayer = selectedPlayer;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public @NonNull String getInput() {
|
||||||
|
return this.inputString;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public @NonNull EntitySelector getSelector() {
|
||||||
|
return this.entitySelector;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public @NonNull ServerPlayerEntity getSingle() {
|
||||||
|
return this.selectedPlayer;
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
|
@ -0,0 +1,34 @@
|
||||||
|
//
|
||||||
|
// MIT License
|
||||||
|
//
|
||||||
|
// Copyright (c) 2021 Alexander Söderberg & Contributors
|
||||||
|
//
|
||||||
|
// Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||||
|
// of this software and associated documentation files (the "Software"), to deal
|
||||||
|
// in the Software without restriction, including without limitation the rights
|
||||||
|
// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
||||||
|
// copies of the Software, and to permit persons to whom the Software is
|
||||||
|
// furnished to do so, subject to the following conditions:
|
||||||
|
//
|
||||||
|
// The above copyright notice and this permission notice shall be included in all
|
||||||
|
// copies or substantial portions of the Software.
|
||||||
|
//
|
||||||
|
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||||
|
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||||
|
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||||
|
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||||
|
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||||
|
// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
|
||||||
|
// SOFTWARE.
|
||||||
|
//
|
||||||
|
package cloud.commandframework.fabric.internal;
|
||||||
|
|
||||||
|
import org.checkerframework.checker.nullness.qual.NonNull;
|
||||||
|
|
||||||
|
public interface EntitySelectorAccess {
|
||||||
|
|
||||||
|
@NonNull String inputString();
|
||||||
|
|
||||||
|
void inputString(@NonNull String inputString);
|
||||||
|
|
||||||
|
}
|
||||||
|
|
@ -45,7 +45,7 @@ public class CloudStringReaderMixin implements StringReaderAsQueue {
|
||||||
private @Nullable String cloud$nextWord;
|
private @Nullable String cloud$nextWord;
|
||||||
|
|
||||||
/* Next whitespace index starting at startIdx, or -1 if none is found */
|
/* Next whitespace index starting at startIdx, or -1 if none is found */
|
||||||
static int cloud$nextWhitespace(final String input, final int startIdx) {
|
private static int cloud$nextWhitespace(final String input, final int startIdx) {
|
||||||
for (int i = startIdx, length = input.length(); i < length; ++i) {
|
for (int i = startIdx, length = input.length(); i < length; ++i) {
|
||||||
if (Character.isWhitespace(input.charAt(i))) {
|
if (Character.isWhitespace(input.charAt(i))) {
|
||||||
return i;
|
return i;
|
||||||
|
|
|
||||||
|
|
@ -0,0 +1,49 @@
|
||||||
|
//
|
||||||
|
// MIT License
|
||||||
|
//
|
||||||
|
// Copyright (c) 2021 Alexander Söderberg & Contributors
|
||||||
|
//
|
||||||
|
// Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||||
|
// of this software and associated documentation files (the "Software"), to deal
|
||||||
|
// in the Software without restriction, including without limitation the rights
|
||||||
|
// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
||||||
|
// copies of the Software, and to permit persons to whom the Software is
|
||||||
|
// furnished to do so, subject to the following conditions:
|
||||||
|
//
|
||||||
|
// The above copyright notice and this permission notice shall be included in all
|
||||||
|
// copies or substantial portions of the Software.
|
||||||
|
//
|
||||||
|
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||||
|
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||||
|
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||||
|
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||||
|
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||||
|
// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
|
||||||
|
// SOFTWARE.
|
||||||
|
//
|
||||||
|
package cloud.commandframework.fabric.mixin;
|
||||||
|
|
||||||
|
import cloud.commandframework.fabric.internal.EntitySelectorAccess;
|
||||||
|
import net.minecraft.command.EntitySelector;
|
||||||
|
import org.checkerframework.checker.nullness.qual.NonNull;
|
||||||
|
import org.spongepowered.asm.mixin.Implements;
|
||||||
|
import org.spongepowered.asm.mixin.Interface;
|
||||||
|
import org.spongepowered.asm.mixin.Mixin;
|
||||||
|
import org.spongepowered.asm.mixin.Unique;
|
||||||
|
|
||||||
|
@Mixin(EntitySelector.class)
|
||||||
|
@Implements({@Interface(iface = EntitySelectorAccess.class, prefix = "cloud$", unique = true)})
|
||||||
|
abstract class EntitySelectorMixin {
|
||||||
|
|
||||||
|
@Unique
|
||||||
|
private String inputString;
|
||||||
|
|
||||||
|
public @NonNull String cloud$inputString() {
|
||||||
|
return this.inputString;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void cloud$inputString(final @NonNull String inputString) {
|
||||||
|
this.inputString = inputString;
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
|
@ -0,0 +1,57 @@
|
||||||
|
//
|
||||||
|
// MIT License
|
||||||
|
//
|
||||||
|
// Copyright (c) 2021 Alexander Söderberg & Contributors
|
||||||
|
//
|
||||||
|
// Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||||
|
// of this software and associated documentation files (the "Software"), to deal
|
||||||
|
// in the Software without restriction, including without limitation the rights
|
||||||
|
// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
||||||
|
// copies of the Software, and to permit persons to whom the Software is
|
||||||
|
// furnished to do so, subject to the following conditions:
|
||||||
|
//
|
||||||
|
// The above copyright notice and this permission notice shall be included in all
|
||||||
|
// copies or substantial portions of the Software.
|
||||||
|
//
|
||||||
|
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||||
|
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||||
|
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||||
|
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||||
|
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||||
|
// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
|
||||||
|
// SOFTWARE.
|
||||||
|
//
|
||||||
|
package cloud.commandframework.fabric.mixin;
|
||||||
|
|
||||||
|
import cloud.commandframework.fabric.internal.EntitySelectorAccess;
|
||||||
|
import com.mojang.brigadier.StringReader;
|
||||||
|
import net.minecraft.command.EntitySelector;
|
||||||
|
import net.minecraft.command.EntitySelectorReader;
|
||||||
|
import org.checkerframework.checker.nullness.qual.NonNull;
|
||||||
|
import org.spongepowered.asm.mixin.Final;
|
||||||
|
import org.spongepowered.asm.mixin.Mixin;
|
||||||
|
import org.spongepowered.asm.mixin.Shadow;
|
||||||
|
import org.spongepowered.asm.mixin.Unique;
|
||||||
|
import org.spongepowered.asm.mixin.injection.At;
|
||||||
|
import org.spongepowered.asm.mixin.injection.Inject;
|
||||||
|
import org.spongepowered.asm.mixin.injection.callback.CallbackInfoReturnable;
|
||||||
|
|
||||||
|
@Mixin(EntitySelectorReader.class)
|
||||||
|
abstract class EntitySelectorReaderMixin {
|
||||||
|
|
||||||
|
@Shadow
|
||||||
|
private int startCursor;
|
||||||
|
|
||||||
|
@Shadow
|
||||||
|
@Final
|
||||||
|
private StringReader reader;
|
||||||
|
|
||||||
|
@Unique
|
||||||
|
@Inject(method = "read", at = @At("RETURN"))
|
||||||
|
public void setInputString(final @NonNull CallbackInfoReturnable<EntitySelector> cir) {
|
||||||
|
final EntitySelector selector = cir.getReturnValue();
|
||||||
|
final String inputString = this.reader.getString().substring(this.startCursor, this.reader.getCursor());
|
||||||
|
((EntitySelectorAccess) selector).inputString(inputString);
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
|
@ -5,6 +5,8 @@
|
||||||
"mixins": [
|
"mixins": [
|
||||||
"CloudStringReaderMixin",
|
"CloudStringReaderMixin",
|
||||||
"CommandManagerMixin",
|
"CommandManagerMixin",
|
||||||
|
"EntitySelectorMixin",
|
||||||
|
"EntitySelectorReaderMixin",
|
||||||
"MessageArgumentTypeMessageFormatAccess",
|
"MessageArgumentTypeMessageFormatAccess",
|
||||||
"MessageArgumentTypeMessageSelectorAccess"
|
"MessageArgumentTypeMessageSelectorAccess"
|
||||||
],
|
],
|
||||||
|
|
|
||||||
|
|
@ -13,6 +13,10 @@
|
||||||
"license": "MIT",
|
"license": "MIT",
|
||||||
"icon": "assets/cloud/logo.png",
|
"icon": "assets/cloud/logo.png",
|
||||||
|
|
||||||
|
"mixins": [
|
||||||
|
"cloud.mixins.json"
|
||||||
|
],
|
||||||
|
|
||||||
"depends": {
|
"depends": {
|
||||||
"fabricloader": ">=0.7.4",
|
"fabricloader": ">=0.7.4",
|
||||||
"fabric-command-api-v1": "*",
|
"fabric-command-api-v1": "*",
|
||||||
|
|
|
||||||
|
|
@ -28,7 +28,7 @@ import cloud.commandframework.execution.CommandExecutionCoordinator;
|
||||||
import cloud.commandframework.fabric.FabricClientCommandManager;
|
import cloud.commandframework.fabric.FabricClientCommandManager;
|
||||||
import net.fabricmc.api.ClientModInitializer;
|
import net.fabricmc.api.ClientModInitializer;
|
||||||
import net.fabricmc.fabric.api.client.command.v1.FabricClientCommandSource;
|
import net.fabricmc.fabric.api.client.command.v1.FabricClientCommandSource;
|
||||||
import net.minecraft.text.Text;
|
import net.minecraft.text.LiteralText;
|
||||||
|
|
||||||
public class FabricClientExample implements ClientModInitializer {
|
public class FabricClientExample implements ClientModInitializer {
|
||||||
@Override
|
@Override
|
||||||
|
|
@ -41,7 +41,7 @@ public class FabricClientExample implements ClientModInitializer {
|
||||||
.literal("say")
|
.literal("say")
|
||||||
.argument(StringArgument.greedy("message"))
|
.argument(StringArgument.greedy("message"))
|
||||||
.handler(ctx -> ctx.getSender().sendFeedback(
|
.handler(ctx -> ctx.getSender().sendFeedback(
|
||||||
Text.of("Cloud client commands says: " + ctx.get("message"))
|
new LiteralText("Cloud client commands says: " + ctx.get("message"))
|
||||||
))
|
))
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -30,6 +30,8 @@ import cloud.commandframework.arguments.standard.IntegerArgument;
|
||||||
import cloud.commandframework.arguments.standard.StringArgument;
|
import cloud.commandframework.arguments.standard.StringArgument;
|
||||||
import cloud.commandframework.execution.CommandExecutionCoordinator;
|
import cloud.commandframework.execution.CommandExecutionCoordinator;
|
||||||
import cloud.commandframework.fabric.FabricServerCommandManager;
|
import cloud.commandframework.fabric.FabricServerCommandManager;
|
||||||
|
import cloud.commandframework.fabric.argument.MultiplePlayerSelectorArgument;
|
||||||
|
import cloud.commandframework.fabric.data.MultiplePlayerSelector;
|
||||||
import cloud.commandframework.meta.CommandMeta;
|
import cloud.commandframework.meta.CommandMeta;
|
||||||
import com.google.gson.JsonObject;
|
import com.google.gson.JsonObject;
|
||||||
import com.google.gson.internal.Streams;
|
import com.google.gson.internal.Streams;
|
||||||
|
|
@ -40,23 +42,29 @@ import net.fabricmc.loader.api.FabricLoader;
|
||||||
import net.minecraft.client.MinecraftClient;
|
import net.minecraft.client.MinecraftClient;
|
||||||
import net.minecraft.command.CommandSource;
|
import net.minecraft.command.CommandSource;
|
||||||
import net.minecraft.command.argument.ArgumentTypes;
|
import net.minecraft.command.argument.ArgumentTypes;
|
||||||
|
import net.minecraft.network.MessageType;
|
||||||
import net.minecraft.server.command.CommandManager;
|
import net.minecraft.server.command.CommandManager;
|
||||||
import net.minecraft.server.command.ServerCommandSource;
|
import net.minecraft.server.command.ServerCommandSource;
|
||||||
|
import net.minecraft.server.network.ServerPlayerEntity;
|
||||||
import net.minecraft.text.ClickEvent;
|
import net.minecraft.text.ClickEvent;
|
||||||
import net.minecraft.text.LiteralText;
|
import net.minecraft.text.LiteralText;
|
||||||
import net.minecraft.text.TextColor;
|
import net.minecraft.text.TextColor;
|
||||||
|
import net.minecraft.util.Util;
|
||||||
|
|
||||||
import java.io.BufferedWriter;
|
import java.io.BufferedWriter;
|
||||||
import java.io.IOException;
|
import java.io.IOException;
|
||||||
import java.nio.file.Files;
|
import java.nio.file.Files;
|
||||||
import java.nio.file.Path;
|
import java.nio.file.Path;
|
||||||
import java.time.Instant;
|
import java.time.Instant;
|
||||||
|
import java.util.Collection;
|
||||||
|
|
||||||
public final class FabricExample implements ModInitializer {
|
public final class FabricExample implements ModInitializer {
|
||||||
private static final CommandArgument<ServerCommandSource, String> NAME = StringArgument.of("name");
|
private static final CommandArgument<ServerCommandSource, String> NAME = StringArgument.of("name");
|
||||||
private static final CommandArgument<ServerCommandSource, Integer> HUGS = IntegerArgument.<ServerCommandSource>newBuilder("hugs")
|
private static final CommandArgument<ServerCommandSource, Integer> HUGS = IntegerArgument.<ServerCommandSource>newBuilder("hugs")
|
||||||
.asOptionalWithDefault("1")
|
.asOptionalWithDefault("1")
|
||||||
.build();
|
.build();
|
||||||
|
private static final CommandArgument<ServerCommandSource, MultiplePlayerSelector> PLAYER_SELECTOR =
|
||||||
|
MultiplePlayerSelectorArgument.of("players");
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void onInitialize() {
|
public void onInitialize() {
|
||||||
|
|
@ -112,7 +120,17 @@ public final class FabricExample implements ModInitializer {
|
||||||
}
|
}
|
||||||
}));
|
}));
|
||||||
|
|
||||||
|
manager.command(base.literal("wave")
|
||||||
|
.argument(PLAYER_SELECTOR)
|
||||||
|
.handler(ctx -> {
|
||||||
|
final MultiplePlayerSelector selector = ctx.get(PLAYER_SELECTOR);
|
||||||
|
final Collection<ServerPlayerEntity> selected = selector.get();
|
||||||
|
selected.forEach(selectedPlayer ->
|
||||||
|
selectedPlayer.sendMessage(new LiteralText("Wave"), MessageType.SYSTEM, Util.NIL_UUID));
|
||||||
|
ctx.getSender().sendFeedback(new LiteralText(String.format("Waved at %d players (%s)", selected.size(),
|
||||||
|
selector.getInput())),
|
||||||
|
false);
|
||||||
|
}));
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
||||||
Loading…
Add table
Add a link
Reference in a new issue