Print the names of nearby gates when executing /gate nb.

Fixed a serious bug when trying to print a very long title.
Made the info command work without a supplied gate id. It then will print information about the closest gate. (Issue #13)
This commit is contained in:
Tobias Ottenweller 2013-09-17 17:57:31 +02:00
parent e9a454182a
commit 12a0bba6cc
6 changed files with 209 additions and 67 deletions

View File

@ -68,6 +68,35 @@ public class GatesManager
}
/**
* Returns the closest gate.
* @param location The location at which to look for a gate.
* @return Might return null if there are no nearby gates.
*/
public Gate getNearestGate(final Location location)
{
Set<Gate> nearbyGates = getNearbyGates(location.getChunk());
if (nearbyGates == null) {
return null;
}
double minDist = Double.MAX_VALUE;
Gate nearestGate = null;
for (Gate g : nearbyGates) {
double dist = location.distance(g.getLocation());
if (dist < minDist) {
minDist = dist;
nearestGate = g;
}
}
return nearestGate;
}
public Gate getGateAtLocation(final Location location)
{
SimpleLocation simpleLocation = new SimpleLocation(location);

View File

@ -17,10 +17,12 @@
package de.craftinc.gates.commands;
import de.craftinc.gates.util.GateBlockChangeSender;
import org.bukkit.ChatColor;
import de.craftinc.gates.Plugin;
import de.craftinc.gates.util.TextUtil;
import org.bukkit.entity.Player;
public class CommandInfo extends BaseCommand
@ -30,48 +32,82 @@ public class CommandInfo extends BaseCommand
aliases.add("info");
aliases.add("i");
requiredParameters.add("id");
optionalParameters.add("id");
helpDescription = "Print detailed information about a certain gate.";
helpDescription = "Print detailed information about a certain or the closest gate.";
requiredPermission = Plugin.permissionInfo;
needsPermissionAtCurrentLocation = false;
shouldPersistToDisk = false;
senderMustBePlayer = false;
hasGateParam = false;
}
public void perform()
{
sendMessage(TextUtil.titleize("Information about: '" + ChatColor.WHITE + gate.getId() + ChatColor.YELLOW + "'"));
if (this.parameters.size() > 0) {
String openHiddenMessage = ChatColor.DARK_AQUA + "This gate is";
if (!this.setGateUsingParameter(this.parameters.get(0))) {
sendMessage(ChatColor.RED + "You either provided a invalid gate or do not have permission to " + this.helpDescription.toLowerCase());
return;
}
if (gate.isOpen())
openHiddenMessage += ChatColor.AQUA + " open";
else
openHiddenMessage += ChatColor.AQUA + " closed";
sendMessage(TextUtil.titleize("Information about: '" + ChatColor.WHITE + gate.getId() + ChatColor.YELLOW + "'"));
}
else {
boolean senderIsPlayer = this.sender instanceof Player;
if (gate.isHidden())
openHiddenMessage += ChatColor.DARK_AQUA +" and" + ChatColor.AQUA + " hidden";
if (!senderIsPlayer) {
sendMessage(ChatColor.RED + "Only ingame players can perform this command without a supplied gate id!");
return;
}
openHiddenMessage += ".\n";
Player p = (Player)this.sender;
this.gate = Plugin.getPlugin().getGatesManager().getNearestGate(p.getLocation());
sendMessage(openHiddenMessage);
if (!this.hasPermission() || this.gate == null) {
sendMessage(ChatColor.RED + "There is either no gate nearby or you do not have permission to " + this.helpDescription.toLowerCase());
return;
}
if (gate.getLocation() != null)
sendMessage(ChatColor.DARK_AQUA + "location: " + ChatColor.AQUA + "( " + (int)gate.getLocation().getX() +
" | " + (int)gate.getLocation().getY() + " | " + (int)gate.getLocation().getZ() + " ) in " +
gate.getLocation().getWorld().getName());
else
sendMessage(ChatColor.DARK_AQUA + "NOTE: this gate has no location");
Plugin.log(this.gate.toString());
if (gate.getExit() != null)
sendMessage(ChatColor.DARK_AQUA + "exit: " + ChatColor.AQUA + "( " + (int)gate.getExit().getX() + " | "
+ (int)gate.getExit().getY() + " | " + (int)gate.getExit().getZ() + " ) in " +
gate.getExit().getWorld().getName());
else
sendMessage(ChatColor.DARK_AQUA + "NOTE: this gate has no exit");
sendMessage(TextUtil.titleize("Information about closest gate: '" + ChatColor.WHITE + gate.getId() + ChatColor.YELLOW + "'"));
}
String openHiddenMessage = ChatColor.DARK_AQUA + "This gate is";
if (gate.isOpen())
openHiddenMessage += ChatColor.AQUA + " open";
else
openHiddenMessage += ChatColor.AQUA + " closed";
if (gate.isHidden())
openHiddenMessage += ChatColor.DARK_AQUA +" and" + ChatColor.AQUA + " hidden";
openHiddenMessage += ".\n";
sendMessage(openHiddenMessage);
if (gate.getLocation() != null)
sendMessage(ChatColor.DARK_AQUA + "location: " + ChatColor.AQUA + "( " + (int)gate.getLocation().getX() +
" | " + (int)gate.getLocation().getY() + " | " + (int)gate.getLocation().getZ() + " ) in " +
gate.getLocation().getWorld().getName());
else
sendMessage(ChatColor.DARK_AQUA + "NOTE: this gate has no location");
if (gate.getExit() != null)
sendMessage(ChatColor.DARK_AQUA + "exit: " + ChatColor.AQUA + "( " + (int)gate.getExit().getX() + " | "
+ (int)gate.getExit().getY() + " | " + (int)gate.getExit().getZ() + " ) in " +
gate.getExit().getWorld().getName());
else
sendMessage(ChatColor.DARK_AQUA + "NOTE: this gate has no exit");
if (this.sender instanceof Player) {
GateBlockChangeSender.temporaryHighlightGateFrame((Player)this.sender, this.gate);
}
}
}

View File

@ -1,8 +1,14 @@
package de.craftinc.gates.commands;
import de.craftinc.gates.Gate;
import de.craftinc.gates.GatesManager;
import de.craftinc.gates.Plugin;
import de.craftinc.gates.util.GateBlockChangeSender;
import de.craftinc.gates.util.TextUtil;
import java.util.ArrayList;
import java.util.Set;
public class CommandNearby extends BaseLocationCommand
{
@ -24,6 +30,24 @@ public class CommandNearby extends BaseLocationCommand
public void perform()
{
GateBlockChangeSender.temporaryHighlightGatesFrames(player);
GatesManager manager = Plugin.getPlugin().getGatesManager();
Set<Gate> nearbyGates = manager.getNearbyGates(player.getLocation().getChunk());
if (nearbyGates == null) {
player.sendMessage("There are no gates near you!");
}
else {
GateBlockChangeSender.temporaryHighlightGatesFrames(player, nearbyGates);
ArrayList<String> gateNames = new ArrayList<String>();
for (Gate g : nearbyGates) {
gateNames.add(g.getId());
}
player.sendMessage("Nearby gates: " + TextUtil.implode(gateNames, ", "));
}
}
}

View File

@ -1,3 +1,19 @@
/* Craft Inc. Gates
Copyright (C) 2011-2013 Craft Inc. Gates Team (see AUTHORS.txt)
This program is free software: you can redistribute it and/or modify
it under the terms of the GNU Lesser General Public License as published
by the Free Software Foundation, either version 3 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU Lesser General Public License for more details.
You should have received a copy of the GNU Lesser General Public License
along with this program (LGPLv3). If not, see <http://www.gnu.org/licenses/>.
*/
package de.craftinc.gates.util;

View File

@ -29,6 +29,8 @@ import org.bukkit.entity.Player;
import java.util.ArrayList;
import java.util.Set;
import static de.craftinc.gates.util.ConfigurationUtil.*;
public class GateBlockChangeSender
{
@ -39,36 +41,16 @@ public class GateBlockChangeSender
* @param player The player for whom the frame should be highlighted.
* Must not be null!
*/
public static void temporaryHighlightGatesFrames(final Player player)
public static void temporaryHighlightGatesFrames(final Player player, final Set<Gate> gates)
{
if (player == null) {
throw new IllegalArgumentException("'player' must not be 'null'!");
}
Location location = player.getLocation();
final Set<Gate> gatesNearby = Plugin.getPlugin().getGatesManager().getNearbyGates(location.getChunk());
if (gatesNearby == null) {
return; // no gates nearby
if (gates == null) {
throw new IllegalArgumentException("'gate' must not be 'null!");
}
highlightGatesFrames(player, gatesNearby);
Plugin plugin = Plugin.getPlugin();
long highlightDuration = 20 * plugin.getConfig().getLong(ConfigurationUtil.confHighlightDurationKey);
Bukkit.getScheduler().scheduleSyncDelayedTask(plugin, new Runnable() {
@Override
public void run() {
dehighlightGateFrame(player, gatesNearby);
}
}, highlightDuration);
}
protected static void highlightGatesFrames(final Player player, final Set<Gate> gates)
{
for (Gate g : gates) {
Set<Block> frameBlocks = g.getGateFrameBlocks();
@ -76,10 +58,48 @@ public class GateBlockChangeSender
player.sendBlockChange(b.getLocation(), Material.GLOWSTONE, (byte)0);
}
}
Plugin plugin = Plugin.getPlugin();
long highlightDuration = 20 * plugin.getConfig().getLong(confHighlightDurationKey);
Bukkit.getScheduler().scheduleSyncDelayedTask(plugin, new Runnable() {
@Override
public void run() {
dehighlightGatesFrames(player, gates);
}
}, highlightDuration);
}
protected static void dehighlightGateFrame(final Player player, final Set<Gate> gates)
public static void temporaryHighlightGateFrame(final Player player, final Gate gate)
{
if (gate == null) {
throw new IllegalArgumentException("'gate' must not be 'null!");
}
if (player == null) {
throw new IllegalArgumentException("'player' must not be 'null'!");
}
Set<Block> frameBlocks = gate.getGateFrameBlocks();
for (Block b : frameBlocks) {
player.sendBlockChange(b.getLocation(), Material.GLOWSTONE, (byte)0);
}
Plugin plugin = Plugin.getPlugin();
long highlightDuration = 20 * plugin.getConfig().getLong(confHighlightDurationKey);
Bukkit.getScheduler().scheduleSyncDelayedTask(plugin, new Runnable() {
@Override
public void run() {
dehighlightGateFrame(player, gate);
}
}, highlightDuration);
}
protected static void dehighlightGatesFrames(final Player player, final Set<Gate> gates)
{
for (Gate g : gates) {
Set<Block> frameBlocks = g.getGateFrameBlocks();
@ -91,6 +111,16 @@ public class GateBlockChangeSender
}
protected static void dehighlightGateFrame(final Player player, final Gate gate)
{
Set<Block> frameBlocks = gate.getGateFrameBlocks();
for (Block b : frameBlocks) {
player.sendBlockChange(b.getLocation(), b.getType(), (byte)0);
}
}
/**
* Sends gate blocks to player at a given location. Will send the updates either immediately or
* immediately and after a short delay.
@ -110,7 +140,7 @@ public class GateBlockChangeSender
}
Set<Gate> gatesNearby = Plugin.getPlugin().getGatesManager().getNearbyGates(location.getChunk());
GateMaterial gateMaterial = ConfigurationUtil.getPortalMaterial();
GateMaterial gateMaterial = getPortalMaterial();
if (gatesNearby == null) {
return; // no gates nearby
@ -188,7 +218,7 @@ public class GateBlockChangeSender
ArrayList<Player> playersNearby = new ArrayList<Player>();
int searchRadius = Plugin.getPlugin().getConfig().getInt(ConfigurationUtil.confPlayerGateBlockUpdateRadiusKey);
int searchRadius = Plugin.getPlugin().getConfig().getInt(confPlayerGateBlockUpdateRadiusKey);
for (Player p : Plugin.getPlugin().getServer().getOnlinePlayers()) {
@ -197,7 +227,7 @@ public class GateBlockChangeSender
}
}
GateMaterial gateMaterial = ConfigurationUtil.getPortalMaterial();
GateMaterial gateMaterial = getPortalMaterial();
Material material;
byte data = 0;

View File

@ -24,13 +24,20 @@ public class TextUtil
{
public static String titleize(String str)
{
String line = ChatColor.GOLD + repeat("_", 60);
String center = ".[ " + ChatColor.YELLOW + str + ChatColor.GOLD + " ].";
int pivot = line.length() / 2;
int eatLeft = center.length() / 2;
int eatRight = center.length() - eatLeft;
return line.substring(0, pivot - eatLeft) + center + line.substring(pivot + eatRight);
if (center.length() >= 60) {
return ChatColor.GOLD + center;
}
else {
String line = ChatColor.GOLD + repeat("_", 60);
int pivot = line.length() / 2;
int eatLeft = center.length() / 2;
int eatRight = center.length() - eatLeft;
return line.substring(0, pivot - eatLeft) + center + line.substring(pivot + eatRight);
}
}