Skip to content

Instantly share code, notes, and snippets.

@aadnk
Created November 26, 2012 06:28
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save aadnk/4146843 to your computer and use it in GitHub Desktop.
Save aadnk/4146843 to your computer and use it in GitHub Desktop.
Path-find to a nearby block lit by sunlight
package com.comphenix.example;
import net.minecraft.server.EntityPlayer;
import net.minecraft.server.PathEntity;
import net.minecraft.server.PathPoint;
import net.minecraft.server.WorldServer;
import org.bukkit.ChatColor;
import org.bukkit.DyeColor;
import org.bukkit.Location;
import org.bukkit.Material;
import org.bukkit.World;
import org.bukkit.block.Block;
import org.bukkit.command.Command;
import org.bukkit.command.CommandSender;
import org.bukkit.craftbukkit.CraftWorld;
import org.bukkit.craftbukkit.entity.CraftPlayer;
import org.bukkit.entity.Entity;
import org.bukkit.entity.Player;
import org.bukkit.event.Listener;
import org.bukkit.plugin.java.JavaPlugin;
public class PathFinderExample extends JavaPlugin implements Listener {
@Override
public boolean onCommand(CommandSender sender, Command command, String label, String[] args) {
if (args.length > 0) {
sender.sendMessage("This command doesn't take any arguments.");
return true;
}
if (label.equalsIgnoreCase("performaction")) {
if (sender instanceof Player)
performAction((Player) sender, args);
else
performAction(sender);
return true;
}
return false;
}
private void performAction(CommandSender sender) {
sender.sendMessage("Cannot perform action on console.");
}
private void performAction(Player sender, String[] args) {
PathEntity path = getSurfacePath(sender, 10);
// Print the result
if (path != null) {
displayPathLocally(sender, path, Material.WOOL, DyeColor.GREEN.getData());
} else {
sender.sendMessage(ChatColor.RED + "Unable to find path.");
}
}
private PathEntity getSurfacePath(Player player, int maximumDistance) {
World world = player.getWorld();
Location center = player.getLocation();
int centerX = center.getBlockX();
int centerZ = center.getBlockZ();
int maximumSquared = maximumDistance * maximumDistance;
// Find suitable locations in a 20x20 rectangle
for (int dX = -maximumDistance; dX < maximumDistance; dX++) {
for (int dZ = -maximumDistance; dZ < maximumDistance; dZ++) {
Block highest = world.getHighestBlockAt(centerX + dX, centerZ + dZ);
// The shortest (direct) distance must be valid first and foremost
if (highest.getLocation().distanceSquared(center) < maximumSquared) {
PathEntity path = getPath(player, highest.getLocation(), maximumDistance);
if (path != null) {
return path;
}
}
}
}
return null;
}
private PathEntity getPath(Entity source, Location destination, int maximumDistance) {
WorldServer nmsWorld = ((CraftWorld) source.getWorld()).getHandle();
EntityPlayer entity = ((CraftPlayer) source).getHandle();
return nmsWorld.a(entity, destination.getBlockX(), destination.getBlockY(), destination.getBlockZ(),
maximumDistance, true, false, false, true);
}
private void displayPathLocally(Player sender, PathEntity path, Material material, int data) {
for (int i = 0; i < path.d(); i++) {
PathPoint point = path.a(i);
Location loc = new Location(sender.getWorld(), point.a, point.b, point.c);
// "Display" the path
sender.sendBlockChange(loc, material, (byte) (data & 0xFF));
}
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment