diff --git a/src/main/java/org/bukkit/craftbukkit/help/HelpTopicComparator.java b/src/main/java/org/bukkit/craftbukkit/help/HelpTopicComparator.java index 7819bef97b..9c0028ec3e 100644 --- a/src/main/java/org/bukkit/craftbukkit/help/HelpTopicComparator.java +++ b/src/main/java/org/bukkit/craftbukkit/help/HelpTopicComparator.java @@ -1,19 +1,29 @@ package org.bukkit.craftbukkit.help; +import org.bukkit.help.HelpTopic; + import java.util.Comparator; /** * Used to impose a custom total ordering on help topics. All topics are listed in alphabetic order, but topics * that start with a slash come after topics that don't. */ -public class HelpTopicComparator implements Comparator { - public int compare(String lhs, String rhs) { - if (lhs.startsWith("/") && !rhs.startsWith("/")) { - return 1; - } else if (!lhs.startsWith("/") && rhs.startsWith("/")) { - return -1; - } else { - return lhs.compareToIgnoreCase(rhs); +public class HelpTopicComparator implements Comparator { + private TopicNameComparator tnc = new TopicNameComparator(); + + public int compare(HelpTopic lhs, HelpTopic rhs) { + return tnc.compare(lhs.getName(), rhs.getName()); + } + + public static class TopicNameComparator implements Comparator { + public int compare(String lhs, String rhs) { + if (lhs.startsWith("/") && !rhs.startsWith("/")) { + return 1; + } else if (!lhs.startsWith("/") && rhs.startsWith("/")) { + return -1; + } else { + return lhs.compareToIgnoreCase(rhs); + } } } } diff --git a/src/main/java/org/bukkit/craftbukkit/help/SimpleHelpMap.java b/src/main/java/org/bukkit/craftbukkit/help/SimpleHelpMap.java index d7313ff1d5..d5696c84ea 100644 --- a/src/main/java/org/bukkit/craftbukkit/help/SimpleHelpMap.java +++ b/src/main/java/org/bukkit/craftbukkit/help/SimpleHelpMap.java @@ -2,11 +2,9 @@ package org.bukkit.craftbukkit.help; import com.google.common.base.Predicates; import com.google.common.collect.Collections2; +import org.bukkit.ChatColor; import org.bukkit.Server; -import org.bukkit.command.Command; -import org.bukkit.command.CommandExecutor; -import org.bukkit.command.MultipleCommandAlias; -import org.bukkit.command.PluginCommand; +import org.bukkit.command.*; import org.bukkit.command.defaults.BukkitCommand; import org.bukkit.command.defaults.VanillaCommand; import org.bukkit.craftbukkit.CraftServer; @@ -21,11 +19,13 @@ public class SimpleHelpMap implements HelpMap { private HelpTopic defaultTopic; private Map helpTopics; + private Set pluginIndexes; private Map> topicFactoryMap; private CraftServer server; public SimpleHelpMap(CraftServer server) { - helpTopics = new TreeMap(new HelpTopicComparator()); // Using a TreeMap for its explicit sorting on key + helpTopics = new TreeMap(new HelpTopicComparator.TopicNameComparator()); // Using a TreeMap for its explicit sorting on key + pluginIndexes = new TreeSet(new HelpTopicComparator()); defaultTopic = new IndexHelpTopic("Index", null, null, Collections2.filter(helpTopics.values(), Predicates.not(Predicates.instanceOf(CommandAliasHelpTopic.class)))); topicFactoryMap = new HashMap>(); this.server = server; @@ -45,6 +45,10 @@ public class SimpleHelpMap implements HelpMap { return null; } + public Collection getHelpTopics() { + return helpTopics.values(); + } + public synchronized void addTopic(HelpTopic topic) { // Existing topics take priority if (!helpTopics.containsKey(topic.getName())) { @@ -89,11 +93,13 @@ public class SimpleHelpMap implements HelpMap { // Register a topic for (Class c : topicFactoryMap.keySet()) { if (c.isAssignableFrom(command.getClass())) { - addTopic(topicFactoryMap.get(c).createTopic(command)); + HelpTopic t = topicFactoryMap.get(c).createTopic(command); + if (t != null) addTopic(t); continue outer; } if (command instanceof PluginCommand && c.isAssignableFrom(((PluginCommand)command).getExecutor().getClass())) { - addTopic(topicFactoryMap.get(c).createTopic(command)); + HelpTopic t = topicFactoryMap.get(c).createTopic(command); + if (t != null) addTopic(t); continue outer; } } @@ -119,6 +125,15 @@ public class SimpleHelpMap implements HelpMap { // Add alias sub-index addTopic(new IndexHelpTopic("Aliases", "Lists command aliases", null, Collections2.filter(helpTopics.values(), Predicates.instanceOf(CommandAliasHelpTopic.class)))); + + // Initialize plugin-level sub-topics + Map> pluginIndexes = new HashMap>(); + fillPluginIndexes(pluginIndexes, server.getCommandMap().getCommands()); + fillPluginIndexes(pluginIndexes, server.getCommandMap().getFallbackCommands()); + + for (Map.Entry> entry : pluginIndexes.entrySet()) { + addTopic(new IndexHelpTopic(entry.getKey(), "All commands for " + entry.getKey(), null, entry.getValue(), ChatColor.GRAY + "Below is a list of all " + entry.getKey() + " commands:")); + } // Amend help topics from the help.yml file for (HelpTopicAmendment amendment : helpYamlReader.getTopicAmendments()) { @@ -131,14 +146,36 @@ public class SimpleHelpMap implements HelpMap { } } + private void fillPluginIndexes(Map> pluginIndexes, Collection commands) { + for (Command command : commands) { + String pluginName = getCommandPluginName(command); + if (pluginName != null) { + HelpTopic topic = getHelpTopic("/" + command.getLabel()); + if (topic != null) { + if (!pluginIndexes.containsKey(pluginName)) { + pluginIndexes.put(pluginName, new TreeSet(new HelpTopicComparator())); //keep things in topic order + } + pluginIndexes.get(pluginName).add(topic); + } + } + } + } + + private String getCommandPluginName(Command command) { + if (command instanceof BukkitCommand || command instanceof VanillaCommand) { + return "Bukkit"; + } + if (command instanceof PluginIdentifiableCommand) { + return ((PluginIdentifiableCommand)command).getPlugin().getName(); + } + return null; + } + private boolean commandInIgnoredPlugin(Command command, List ignoredPlugins) { - if (command instanceof BukkitCommand && ignoredPlugins.contains("Bukkit")) { + if ((command instanceof BukkitCommand || command instanceof VanillaCommand) && ignoredPlugins.contains("Bukkit")) { return true; } - if (command instanceof VanillaCommand && ignoredPlugins.contains("Bukkit")) { - return true; - } - if (command instanceof PluginCommand && ignoredPlugins.contains(((PluginCommand)command).getPlugin().getName())) { + if (command instanceof PluginIdentifiableCommand && ignoredPlugins.contains(((PluginIdentifiableCommand)command).getPlugin().getName())) { return true; } return false;