repositories {
maven ( "https://repo.bluecolored.de/releases" )
}
dependencies {
implementation("de.bluecolored:bluecommands-core:1.2.0")
implementation("de.bluecolored:bluecommands-brigadier:1.2.0") // Optional
}classMyCommands {
privateCommand<CommandSender, Object> commands;
publicMyCommands() {
BlueCommands<CommandSender> commandFactory = newBlueCommands<>();
this.commands = commandFactory.createCommand(this);
}
publicvoidrunCommand(CommandSendersender, Stringinput) {
// parse the commandParseResult<CommandSender, Object> parseResult = this.commands.parse(sender, newInputReader(input));
// get the match with the highest priorityParseMatch<CommandSender, Object> match = parseResult.getMatches().stream()
.max(Comparator.comparing(ParseMatch::getPriority))
.orElse(null);
if (match == null) {
// handle no command foundreturn;
}
// execute the command (the result is whatever the command-method returns)ObjectexecutionResult = match.execute();
}
@Command("foo <arg1> [optionalArg2]")
publicvoidfooCommand(
CommandSendersender,
@Argument("arg1") StringstringArgument,
@Argument("optionalArg2") DoubleoptionalDoubleArgument
) {
// do something
}
}Example here for creating an argument parser which accepts online Bukkit-Players:
publicclassPlayerArgument<S> extendsSimpleArgumentParser<S, Player> {
publicPlayerArgument() {
super(false, false);
}
@OverridepublicPlayerparse(Scontext, Stringname) throwsCommandParseException {
Playerplayer = Bukkit.getPlayerExact(name);
if (player == null) {
thrownewCommandParseException("'" + name + "' is not an online player!");
}
returnplayer;
}
@OverridepublicList<Suggestion> suggest(Scontext, InputReaderinput) {
returnBukkit.getOnlinePlayers().stream()
.map(player -> (Suggestion) newSimpleSuggestion(player.getName()))
.toList();
}
}Then register the new Parser before creating your commands:
BlueCommands<CommandSender> commandFactory = newBlueCommands<>();
// register the custom argument-parsercommandFactory.setArgumentParserForArgumentType(Player.class, newPlayerArgument<>());
this.commands = commandFactory.createCommand(this);With context-resolvers you can add other parameters to your command-method that should be resolved from the context.
BlueCommands<CommandSender> commandFactory = newBlueCommands<>();
commandFactory.setContextResolverForType(Server.class, CommandSender::getServer);Then in a command you can add a Server parameter which will be filled based on the current command-context:
@Command("foo <arg1> [optionalArg2]")
publicvoidfooCommand(
Serverserver,
@Argument("arg1") StringstringArgument,
@Argument("optionalArg2") DoubleoptionalDoubleArgument
) {
// ...
}Here an example to create a Permission annotation and use it to validate commands for a context.
Create the new Annotation:
@Target(ElementType.METHOD)
@Retention(RetentionPolicy.RUNTIME)
public @interface Permission {
Stringvalue();
}Label your commands with this new annotation:
@Command("foo <arg1> [optionalArg2]")
@Permission("foo.bar.bazz")
publicvoidfooCommand(
CommandSendersender,
@Argument("arg1") StringstringArgument,
@Argument("optionalArg2") DoubleoptionalDoubleArgument
) {
// ...
}Register a context-predicate for this Annotation:
BlueCommands<CommandSender> commandFactory = newBlueCommands<>();
commandFactory.setAnnotationContextPredicate(Permission.class, (permission, commandSender) -> {
returncommandSender.hasPermission(permission.value());
});When the annotation is present, the command will now only be available if the registered predicate returns true.
You can merge multiple commands into one. E.g. if you have multiple objects that hold command-methods:
BlueCommands<CommandSender> commandFactory = newBlueCommands<>();
Command<CommandSender, Object> root = newCommand<>();
root.tryMerge(commandFactory.createCommand(object1));
root.tryMerge(commandFactory.createCommand(object2));
root.tryMerge(commandFactory.createCommand(object3));