diff --git a/vMinecraft.java b/vMinecraft.java new file mode 100644 index 000000000..654be29fd --- /dev/null +++ b/vMinecraft.java @@ -0,0 +1,32 @@ +import java.util.logging.Logger; + +//===================================================================== +//Class: vMinecraftPlugin +//Use: Starts the plugin +//Author: nossr50, TrapAlice, cerevisiae +//===================================================================== +public class vMinecraft extends Plugin { + static final vMinecraftListener listener = new vMinecraftListener(); + protected static final Logger log = Logger.getLogger("Minecraft"); + + public void enable() { + vMinecraftSettings.getInstance().loadSettings(); + vMinecraftCommands.loadCommands(); + } + + public void disable() { + //And remove the commands here. + } + + public void initialize() { + //Here we add the hook we're going to use. In this case it's the arm swing event. + etc.getLoader().addListener(PluginLoader.Hook.CHAT, listener, this, PluginListener.Priority.MEDIUM); + etc.getLoader().addListener(PluginLoader.Hook.COMMAND, listener, this, PluginListener.Priority.HIGH); + etc.getLoader().addListener(PluginLoader.Hook.IGNITE, listener, this, PluginListener.Priority.HIGH); + etc.getLoader().addListener(PluginLoader.Hook.DAMAGE, listener, this, PluginListener.Priority.MEDIUM); + etc.getLoader().addListener(PluginLoader.Hook.EXPLODE, listener, this, PluginListener.Priority.HIGH); + if(etc.getInstance().isHealthEnabled()){ + etc.getLoader().addListener(PluginLoader.Hook.HEALTH_CHANGE, listener, this, PluginListener.Priority.MEDIUM); + } + } +} diff --git a/vMinecraftAnnouncements.java b/vMinecraftAnnouncements.java new file mode 100644 index 000000000..c93db1b96 --- /dev/null +++ b/vMinecraftAnnouncements.java @@ -0,0 +1,53 @@ +//===================================================================== +//Class: vMinecraftAnnouncements +//Use: Encapsulates all announcements broadcast when commands are +// run +//Author: nossr50, TrapAlice, cerevisiae +//===================================================================== +public class vMinecraftAnnouncements { + + //===================================================================== + //Function: onCommand + //Input: Player player: The player calling the command + // String[] split: The arguments + //Output: boolean: If the user has access to the command + // and it is enabled + //Use: Checks if /kick, /ban, /ipban, and /time are run and + // displays a global message + //===================================================================== + public boolean onCommand(Player player, String[] split) { + if(!player.canUseCommand(split[0])) { + return false; + } + //Only run if the global message feature is enabled + if(vMinecraftSettings.getInstance().globalmessages()) + { + //Global messages that should only parse when a command can be successful + if(split[0].equalsIgnoreCase("/kick")) { + Player playerTarget = etc.getServer().matchPlayer(split[1]); + if (playerTarget != null && !playerTarget.hasControlOver(player)) { + vMinecraftChat.gmsg(player.getColor()+player.getName()+Colors.Blue+" has kicked "+Colors.Red+playerTarget.getColor()+playerTarget.getName()); + } + } + if(split[0].equalsIgnoreCase("/ban")) { + Player playerTarget = etc.getServer().matchPlayer(split[1]); + if (playerTarget != null && !playerTarget.hasControlOver(player)) { + vMinecraftChat.gmsg(player.getColor()+player.getName()+Colors.Blue+" has banned "+Colors.Red+playerTarget.getColor()+playerTarget.getName()); + } + } + if(split[0].equalsIgnoreCase("/ipban")) { + Player playerTarget = etc.getServer().matchPlayer(split[1]); + if (playerTarget != null && !playerTarget.hasControlOver(player)) { + vMinecraftChat.gmsg(player.getColor()+player.getName()+Colors.Blue+" has IP banned "+Colors.Red+playerTarget.getColor()+playerTarget.getName()); + } + } + if(split[0].equalsIgnoreCase("/time")) { + if (split.length <= 2) { + vMinecraftChat.gmsg(Colors.Blue+"Time changes thanks to "+player.getColor()+player.getName()); + } + } + } + + return true; + } +} diff --git a/vMinecraftChat.java b/vMinecraftChat.java new file mode 100644 index 000000000..3f6463855 --- /dev/null +++ b/vMinecraftChat.java @@ -0,0 +1,495 @@ +import java.util.ArrayList; +import java.util.logging.Level; +import java.util.logging.Logger; + +//===================================================================== +//Class: vMinecraftChat +//Use: Encapsulates all chat commands added by this mod +//Author: nossr50, TrapAlice, cerevisiae +//===================================================================== +public class vMinecraftChat { + protected static final Logger log = Logger.getLogger("Minecraft"); + + //===================================================================== + //Function: gmsg + //Input: String msg: The message to be broadcast to all players + //Output: None + //Use: Outputs a message to everybody + //===================================================================== + public static void gmsg(String msg){ + for (Player p : etc.getServer().getPlayerList()) { + if (p != null) { + p.sendMessage(msg); + } + } + } + + //===================================================================== + //Function: wordWrap + //Input: String msg: The message to be wrapped + //Output: String[]: The array of substrings + //Use: Cuts the message apart into whole words short enough to fit + // on one line + //===================================================================== + public static String[] wordWrap(String msg){ + //Split each word apart + String[] split = msg.split(" "); + + //Create an arraylist for the output + ArrayList out = new ArrayList(); + + //While i is less than the length of the array of words + int i = 0; + while(i < split.length){ + int len = 0; + int j = i; + + //Loop through the words finding their length and increasing + //j, the end point for the sub string + while(len <= 316 && i < split.length) + { + len += msgLength(split[i]) + 4; + if( len <= 316) + i++; + + } + //Copy the words in the selection into a new array + String[] temp = new String[i - j]; + System.arraycopy(split, j, temp, 0, i - j); + + //Merge them and add them to the output array + out.add( etc.combineSplit(0, temp, " ") ); + } + + //Convert to an array and return + String[] tempout = new String[out.size()]; + out.toArray(tempout); + return tempout; + } + + //===================================================================== + //Function: msgLength + //Input: String str: The string to find the length of + //Output: int: The length on the screen of a string + //Use: Finds the length on the screen of a string. Ignores colors. + //===================================================================== + private static int msgLength(String str){ + int length = 0; + //Loop through all the characters, skipping any color characters + //and their following color codes + for(int x = 0; x\"*()".indexOf(str.charAt(x)) != -1) + length+=5; + else if("hequcbrownxjmpsvazydgTHEQUCKBROWNFXJMPSVLAZYDG1234567890#\\/?$%-=_+&".indexOf(str.charAt(x)) != -1) + length+=6; + else if("@~".indexOf(str.charAt(x)) != -1) + length+=7; + else if(str.charAt(x)==' ') + length+=4; + } + return length; + } + + //===================================================================== + //Function: rainbow + //Input: String msg: The string to colorify + //Output: String: The rainbowed result + //Use: Rainbowifies a string; + //===================================================================== + public static String rainbow(String msg){ + String temp = ""; + //The array of colors to use + String[] rainbow = new String[] {Colors.Red, Colors.Rose, Colors.Gold, + Colors.Yellow, Colors.LightGreen, Colors.Green, Colors.Blue, + Colors.Navy, Colors.DarkPurple, Colors.Purple, Colors.LightPurple}; + int counter=0; + //Loop through the message applying the colors + for(int x=0; x " + message); + return true; + } + return false; + } + public static boolean adminChatToggle(Player player, String message){ + if(vMinecraftSettings.getInstance().isAdminToggled(player.getName())) { + String adminchat = Colors.DarkPurple + "{" + getName(player) + + Colors.DarkPurple +"}" + Colors.White + " "; + String[] msg = wordWrap(adminchat + message.substring(1, message.length())); + for (Player p: etc.getServer().getPlayerList()) { + if (p != null) { + if (p.isAdmin() || p.canUseCommand("/adminchat")) { + for(String str: msg) + p.sendMessage(str); + } + } + } + log.log(Level.INFO, "@" + "<" + getName(player) + + Colors.White +"> " + message); + return true; + } + return false; + } + + //===================================================================== + //Function: quote + //Input: Player player: The player talking + // String message: The message to apply the effect to + //Output: boolean: If this feature is enabled + //Use: Displays a message as a quote + //===================================================================== + public static boolean quote(Player player, String message) + { + //Format the name + String playerName = Colors.White + "<" + getName(player) + + Colors.White + "> "; + if(vMinecraftSettings.getInstance().greentext()) { + //Log the chat + log.log(Level.INFO, "<"+player.getName()+"> " +message); + + //Get the multi line array + String[] msg = wordWrap(playerName + Colors.LightGreen + message); + + //Output the lines + for(String str: msg) + gmsg(Colors.LightGreen + str); + return true; + } + return false; + } + + //===================================================================== + //Function: rage + //Input: Player player: The player talking + // String message: The message to apply the effect to + //Output: boolean: If this feature is enabled + //Use: Displays a message in red + //===================================================================== + public static boolean rage(Player player, String message) + { + //Format the name + String playerName = Colors.White + "<" + + getName(player) + Colors.White +"> "; + if (vMinecraftSettings.getInstance().FFF()) { + log.log(Level.INFO, "<"+player.getName()+"> "+message); + + //Get the multi line array + String[] msg = wordWrap(playerName + Colors.Red + message); + + //Output the message + for(String str: msg) + gmsg(Colors.Red + str); + return true; + } + return false; + } + + //===================================================================== + //Function: quakeColors + //Input: Player player: The player talking + // String message: The message to apply the effect to + //Output: boolean: If this feature is enabled + //Use: Displays a message in red + //===================================================================== + public static boolean quakeColors(Player player, String message) + { + //Format the name + String playerName = Colors.White + "<" + + getName(player) + Colors.White +"> "; + if(vMinecraftSettings.getInstance().quakeColors()) { + + //Log the chat + log.log(Level.INFO, "<"+player.getName()+"> "+message); + + //Get the multi line array + String[] msg = wordWrap(playerName + message); + //Apply colors to the lines + applyColors(msg); + + //Output the message + for(String str: msg) + gmsg(str); + + //Loop through the string finding the color codes and inserting them + return true; + } + return false; + } + + + //===================================================================== + //Function: applyColors + //Input: String[] message: The lines to be colored + //Output: String[]: The lines, but colorful + //Use: Colors each line + //===================================================================== + public static String[] applyColors(String[] message) + { + if(message != null && message[0] != null && !message[0].equals("")){ + //The color to start the line with + String recentColor = Colors.White; + + //Go through each line + int counter = 0; + for(String msg: message) + { + //Start the line with the most recent color + String temp = recentColor; + + //Loop through looking for a color code + for(int x = 0; x< msg.length(); x++) + { + //If the char is a ^ or � + if(msg.charAt(x) == '^' || msg.charAt(x) == '§') + { + if(x != msg.length() - 1) + { + //If the following character is a color code + if(vMinecraftChat.colorChange(msg.charAt(x+1)) != null) + { + //Set the most recent color to the new color + recentColor = vMinecraftChat.colorChange(msg.charAt(x+1)); + //Add the color + temp += recentColor; + //Skip these chars + x++; + //Otherwise ignore it. + } else { + temp += msg.charAt(x); + } + //Insert the character + } + } else { + temp += msg.charAt(x); + } + } + //Replace the message with the colorful message + message[counter] = temp; + counter++; + } + } + return message; + } + + //===================================================================== + //Function: applyColors + //Input: String message: The line to be colored + //Output: String: The line, but colorful + //Use: Colors a line + //===================================================================== + public static String applyColors(String message) + { + return applyColors(message, Colors.White); + } + + //===================================================================== + //Function: applyColors + //Input: String message: The line to be colored + // String color: The color to start the line with + //Output: String: The line, but colorful + //Use: Colors a line + //===================================================================== + public static String applyColors(String message, String color) + { + if(message != null && !message.equals("")) + { + //The color to start the line with + if(color == null) + color = Colors.White; + + //Start the line with the most recent color + String temp = color; + + //Loop through looking for a color code + for(int x = 0; x< message.length(); x++) + { + //If the char is a ^ or � + if(message.charAt(x) == '^' || message.charAt(x) == '§') + { + if(x != message.length() - 1) + { + //If the following character is a color code + if(vMinecraftChat.colorChange(message.charAt(x+1)) != null) + { + //Set the most recent color to the new color + color = vMinecraftChat.colorChange(message.charAt(x+1)); + //Add the color + temp += color; + //Skip these chars + x++; + //Otherwise ignore it. + } else { + temp += message.charAt(x); + } + //Insert the character + } else { + temp += message.charAt(x); + } + } + + } + } + return message; + } +} diff --git a/vMinecraftListener.java b/vMinecraftListener.java new file mode 100644 index 000000000..a89cfda06 --- /dev/null +++ b/vMinecraftListener.java @@ -0,0 +1,100 @@ +import java.util.logging.Level; +import java.util.logging.Logger; +//===================================================================== +//Class: vMinecraftListener +//Use: The listener to catch incoming chat and commands +//Author: nossr50, TrapAlice, cerevisiae +//===================================================================== +public class vMinecraftListener extends PluginListener { + protected static final Logger log = Logger.getLogger("Minecraft"); + + //===================================================================== + //Function: disable + //Input: None + //Output: None + //Use: Disables vMinecraft, but why would you want to do that? ;) + //===================================================================== + public void disable() { + log.log(Level.INFO, "vMinecraft disabled"); + } + + //===================================================================== + //Function: onChat + //Input: Player player: The player calling the command + // String message: The message to color + //Output: boolean: If the user has access to the command + // and it is enabled + //Use: Checks for quote, rage, and colors + //===================================================================== + public boolean onChat(Player player, String message){ + + //Quote (Greentext) + if (message.startsWith("@")) + return vMinecraftChat.adminChat(player, message); + if (vMinecraftSettings.getInstance().isAdminToggled(player.getName())) + return vMinecraftChat.adminChatToggle(player, message); + + else if (message.startsWith(">")) + return vMinecraftChat.quote(player, message); + + //Rage (FFF) + else if (message.startsWith("FFF")) + return vMinecraftChat.rage(player, message); + + //Send through quakeColors otherwise + else + return vMinecraftChat.quakeColors(player, message); + } + + //===================================================================== + //Function: onCommand + //Input: Player player: The player calling the command + // String[] split: The arguments + //Output: boolean: If the user has access to the command + // and it is enabled + //Use: Checks for exploits and runs the commands + //===================================================================== + public boolean onCommand(Player player, String[] split) { + + //Copy the arguments into their own array. + String[] args = new String[split.length - 1]; + System.arraycopy(split, 1, args, 0, args.length); + + //Return the results of the command + int exitCode = vMinecraftCommands.cl.call(split[0], player, args); + if(exitCode == 0) + return false; + else if(exitCode == 1) + return true; + else + return false; + + } + + //===================================================================== + //Function: onHealthChange + //Input: Player player: The player calling the command + // int oldValue: The old health value; + // int newValue: The new health value + //Output: boolean: If the user has access to the command + // and it is enabled + //Use: Checks for exploits and runs the commands + //===================================================================== + public boolean onHealthChange(Player player,int oldValue,int newValue){ + if (player.getHealth() != vMinecraftSettings.getInstance().ezModoHealth() && vMinecraftSettings.getInstance().isEzModo(player.getName())) { + player.setHealth(vMinecraftSettings.getInstance().ezModoHealth()); + + } + else if (vMinecraftSettings.getInstance().globalmessages() && player.getHealth() < 1) { + vMinecraftChat.gmsg(Colors.Gray + player.getName() + " " + vMinecraftSettings.randomDeathMsg()); + } + return false; + } + /** Not working yet, I posted the issue to hMod on github though + public boolean onDamage(DamageType type, BaseEntity attacker, BaseEntity defender, int amount) { + + return false; + } + **/ + +} \ No newline at end of file diff --git a/vMinecraftSettings.java b/vMinecraftSettings.java new file mode 100644 index 000000000..71f4c26ea --- /dev/null +++ b/vMinecraftSettings.java @@ -0,0 +1,229 @@ +import java.io.*; +import java.util.ArrayList; +import java.util.logging.Level; +import java.util.logging.Logger; +//===================================================================== +//Class: vminecraftSettings +//Use: Controls the settings for vminecraft +//Author: nossr50, TrapAlice, cerevisiae +//===================================================================== +public class vMinecraftSettings { + //private final static Object syncLock = new Object(); + protected static final Logger log = Logger.getLogger("Minecraft"); + private static volatile vMinecraftSettings instance; + + + //The feature settings + static boolean toggle = true, + adminChat = false, + greentext = false, + FFF = false, + quakeColors = false, + cmdFabulous = false, + cmdPromote = false, + cmdDemote = false, + cmdWhoIs = false, + cmdRules = false, + cmdMasstp = false, + cmdTp = false, + cmdTphere = false, + globalmessages = false, + cmdSay = false, + cmdWho = false, + stopFire = false, + stopTnt = false, + cmdHeal = false, + cmdSuicide = false, + cmdAdminToggle = false, + cmdEzModo = false; + //An array of players currently in ezmodo + static ArrayList ezModo = new ArrayList(); + //An array of players currently toggled for admin chat + static ArrayList adminChatList = new ArrayList(); + //The max health for ezModo + static int ezHealth = 30; + + private PropertiesFile properties; + String file = "vminecraft.properties"; + public String rules[] = new String[0]; + public static String deathMessages[] = new String[0]; + + //===================================================================== + //Function: loadSettings + //Input: None + //Output: None + //Use: Loads the settings from the properties + //===================================================================== + public void loadSettings() + { + File theDir = new File("vminecraft.properties"); + if(!theDir.exists()){ + String location = "vminecraft.properties"; + properties = new PropertiesFile("vminecraft.properties"); + FileWriter writer = null; + try { + writer = new FileWriter(location); + writer.write("#This plugin is modular\r\n"); + writer.write("#Turn any features you don't want to false and they won't be running\r\n"); + writer.write("#If you edit this file and save it, then use /reload it will reload the settings\r\n"); + writer.write("greentext=true\r\n"); + writer.write("quakeColors=true\r\n"); + writer.write("cmdTphere=true\r\n"); + writer.write("cmdFabulous=true\r\n"); + writer.write("cmdWhoIs=true\r\n"); + writer.write("cmdWho=true\r\n"); + writer.write("cmdPromote=true\r\n"); + writer.write("cmdDemote=true\r\n"); + writer.write("cmdMasstp=true\r\n"); + writer.write("cmdSay=true\r\n"); + writer.write("cmdTp=true\r\n"); + writer.write("cmdRules=true\r\n"); + writer.write("cmdSuicide=true\r\n"); + writer.write("cmdAdminToggle=true\r\n"); + writer.write("globalmessages=true\r\n"); + writer.write("FFF=true\r\n"); + writer.write("adminchat=true\r\n"); + writer.write("cmdEzModo=true\r\n"); + writer.write("#Adding player names to this list will have them start off in ezmodo\r\n"); + writer.write("ezModo=\r\n"); + writer.write("#The health ezmodo people will have while in ezmodo. Don't set to 0\r\n"); + writer.write("ezHealth=30\r\n"); + writer.write("stopFire=false\r\n"); + writer.write("stopTnt=false\r\n"); + writer.write("rules=Rules@#1: No griefing@#2: No griefing\r\n"); + writer.write("#Death messages, seperate them by comma. All death messages start with the player name and a space.\r\n"); + writer.write("deathMessages=is no more,died horribly,went peacefully\r\n"); + } catch (Exception e) { + log.log(Level.SEVERE, "Exception while creating " + location, e); + } finally { + try { + if (writer != null) { + writer.close(); + } + } catch (IOException e) { + log.log(Level.SEVERE, "Exception while closing writer for " + location, e); + } + } + + } else { + properties = new PropertiesFile("vminecraft.properties"); + try { + properties.load(); + } catch (IOException e) { + log.log(Level.SEVERE, "Exception while loading vminecraft.properties", e); + } + } + + try { + adminChat = properties.getBoolean("adminchat",true); + greentext = properties.getBoolean("greentext",true); + FFF = properties.getBoolean("FFF",true); + quakeColors = properties.getBoolean("quakeColors",true); + cmdFabulous = properties.getBoolean("cmdFabulous",true); + cmdPromote = properties.getBoolean("cmdPromote",true); + cmdDemote = properties.getBoolean("cmdDemote",true); + cmdWhoIs = properties.getBoolean("cmdWhoIs",true); + cmdWho = properties.getBoolean("cmdWho",true); + cmdRules = properties.getBoolean("cmdRules",true); + cmdTp = properties.getBoolean("cmdTp",true); + cmdMasstp = properties.getBoolean("cmdMasstp",true); + cmdTphere = properties.getBoolean("cmdTphere",true); + cmdSuicide = properties.getBoolean("cmdSuicide", true); + cmdHeal = properties.getBoolean("cmdHeal",true); + cmdAdminToggle = properties.getBoolean("cmdAdminToggle", true); + globalmessages = properties.getBoolean("globalmessages",true); + cmdSay = properties.getBoolean("cmdSay",true); + cmdEzModo = properties.getBoolean("cmdEzModo",true); + stopFire = properties.getBoolean("stopFire",true); + stopTnt = properties.getBoolean("stopTNT",true); + rules = properties.getString("rules", "").split("@"); + deathMessages = properties.getString("deathmessages", "").split(","); + + String[] tempEz = properties.getString("ezModo").split(","); + ezModo = new ArrayList(); + for(String ezName : tempEz) + ezModo.add(ezName); + + ezHealth = properties.getInt("ezHealth"); + + log.log(Level.INFO, "vminecraft plugin successfully loaded"); + + } + catch (Exception e) + { + log.log(Level.SEVERE, "vminecraft Error: ERROR LOADING PROPERTIES FILE"); + } + } + + //===================================================================== + //Function: adminchat, greentext, FFF, quakeColors, cmdFabulous, + // cmdPromote, cmdDemote, cmdWhoIs, cmdTp, cmdTphere, cmdSay + // cmdRules, globalmessages, cmdMasstp, cmdEzModo + //Input: None + //Output: Boolan: If the feature is enabled + //Use: Returns if the feature is enabled + //===================================================================== + public boolean adminchat() {return adminChat;} + public boolean adminChatToggle() {return cmdAdminToggle;} + public boolean greentext() {return greentext;} + public boolean FFF() {return FFF;} + public boolean quakeColors() {return quakeColors;} + public boolean cmdFabulous() {return cmdFabulous;} + public boolean cmdPromote() {return cmdPromote;} + public boolean cmdDemote() {return cmdDemote;} + public boolean cmdWhoIs() {return cmdWhoIs;} + public boolean cmdTp() {return cmdTp;} + public boolean cmdTphere() {return cmdTphere;} + public boolean cmdSay() {return cmdSay;} + public boolean cmdRules() {return cmdRules;} + public boolean globalmessages() {return globalmessages;} + public boolean cmdMasstp() {return cmdMasstp;} + public boolean cmdWho() {return cmdWho;} + public boolean stopFire() {return stopFire;} + public boolean stopTnt() {return stopTnt;} + public boolean cmdSuicide() {return cmdSuicide;} + public boolean cmdHeal() {return cmdHeal;} + + //EzModo methods + public boolean cmdEzModo() {return cmdEzModo;} + public boolean isEzModo(String playerName) {return ezModo.contains(playerName);} + public boolean isAdminToggled(String playerName) {return adminChatList.contains(playerName);} + public void removeEzModo(String playerName) {ezModo.remove(ezModo.indexOf(playerName));} + public void removeAdminToggled(String playerName) {adminChatList.remove(adminChatList.indexOf(playerName));} + public void addEzModo(String playerName) {ezModo.add(playerName);} + public void addAdminToggled(String playerName) {adminChatList.add(playerName);} + public int ezModoHealth() {return ezHealth;} + public String ezModoList() {return ezModo.toString();} + + //Random death message method + public static String randomDeathMsg() { + if (deathMessages == null) { + return "died"; + } + return deathMessages[ (int) (Math.random() * deathMessages.length)]; + } + + //===================================================================== + //Function: getInstance + //Input: None + //Output: vminecraftSettings: The instance of the settings + //Use: Returns the instance of the settings + //===================================================================== + public static vMinecraftSettings getInstance() { + if (instance == null) { + instance = new vMinecraftSettings(); + } + return instance; + } + + //===================================================================== + //Function: getRules + //Input: None + //Output: String[]: The list of rules + //Use: Gets the array containing the rules + //===================================================================== + public String[] getRules() { + return rules; + } + +} \ No newline at end of file