diff --git a/build.gradle b/build.gradle index a62b9b5..cc97bdd 100644 --- a/build.gradle +++ b/build.gradle @@ -15,21 +15,30 @@ buildscript { } } +repositories { + flatDir { + dirs 'lib' + } +} + apply plugin: 'forge' [compileJava, compileTestJava]*.options*.encoding = 'UTF-8' -version = "1.4" +version = "1.5" group= "com.gamerforea" archivesBaseName = "EventHelper" minecraft { - version = "1.7.10-10.13.4.1492-1.7.10" + version = "1.7.10-10.13.4.1614-1.7.10" runDir = "eclipse" + replace "@VERSION@", project.version } dependencies { - compile fileTree(dir: 'lib', include: '*.jar') + compile name: 'bukkit-1.7.10' + compile name: 'worldedit-6.1' + compile name: 'worldguard-6.1' } task devJar(type: Jar) { @@ -37,6 +46,12 @@ task devJar(type: Jar) { from sourceSets.main.output } +task sourcesJar(type: Jar) { + classifier = 'sources' + from sourceSets.main.allSource +} + artifacts { archives devJar + archives sourcesJar } \ No newline at end of file diff --git a/lib/bukkit-1.7.10-sources.jar b/lib/bukkit-1.7.10-sources.jar new file mode 100644 index 0000000..af98aba Binary files /dev/null and b/lib/bukkit-1.7.10-sources.jar differ diff --git a/lib/bukkit-1.7.10.jar b/lib/bukkit-1.7.10.jar new file mode 100644 index 0000000..9fd0b0a Binary files /dev/null and b/lib/bukkit-1.7.10.jar differ diff --git a/lib/cauldron-api-1.7.10-SNAPSHOT.jar b/lib/cauldron-api-1.7.10-SNAPSHOT.jar deleted file mode 100644 index 0ae4a1b..0000000 Binary files a/lib/cauldron-api-1.7.10-SNAPSHOT.jar and /dev/null differ diff --git a/lib/worldedit-6.1-sources.jar b/lib/worldedit-6.1-sources.jar new file mode 100644 index 0000000..7a140f1 Binary files /dev/null and b/lib/worldedit-6.1-sources.jar differ diff --git a/lib/worldguard-6.1-sources.jar b/lib/worldguard-6.1-sources.jar new file mode 100644 index 0000000..4a55cb9 Binary files /dev/null and b/lib/worldguard-6.1-sources.jar differ diff --git a/src/main/java/com/gamerforea/eventhelper/EventHelper.java b/src/main/java/com/gamerforea/eventhelper/EventHelper.java index 6e3a6af..4f16abe 100644 --- a/src/main/java/com/gamerforea/eventhelper/EventHelper.java +++ b/src/main/java/com/gamerforea/eventhelper/EventHelper.java @@ -24,13 +24,13 @@ import net.minecraftforge.common.config.Configuration; @SideOnly(Side.SERVER) -@Mod(modid = "EventHelper", name = "EventHelper", version = "1.4", acceptableRemoteVersions = "*") +@Mod(modid = "EventHelper", name = "EventHelper", version = "@VERSION@", acceptableRemoteVersions = "*") public final class EventHelper { public static final File cfgDir = new File(Loader.instance().getConfigDir(), "Events"); public static final List listeners = Lists.newArrayList(); + public static String craftPackage = "org/bukkit/craftbukkit/v1_7_R4"; public static boolean debug = false; - public static boolean fastEvents = false; @EventHandler public final void serverStarted(FMLServerStartedEvent event) @@ -38,8 +38,8 @@ public final void serverStarted(FMLServerStartedEvent event) Configuration cfg = FastUtils.getConfig("EventHelper"); String[] plugins = cfg.getStringList("plugins", CATEGORY_GENERAL, new String[] { "WorldGuard" }, "Plugins for sending events"); boolean wgHooking = cfg.getBoolean("wgHooking", CATEGORY_GENERAL, true, "Hooking WorldGuard plugin (allow checking regions)"); + craftPackage = cfg.getString("craftPackage", CATEGORY_GENERAL, craftPackage, "CraftBukkit package (for reflection)"); debug = cfg.getBoolean("debug", CATEGORY_GENERAL, debug, "Debugging enabled"); - fastEvents = cfg.getBoolean("fastEvents", CATEGORY_GENERAL, fastEvents, "Fast events enabled (not recommended, work only on WorldGuard)"); cfg.save(); PluginManager plManager = Bukkit.getPluginManager(); diff --git a/src/main/java/com/gamerforea/eventhelper/util/ConvertUtils.java b/src/main/java/com/gamerforea/eventhelper/util/ConvertUtils.java index 34f7c56..ed41cb5 100644 --- a/src/main/java/com/gamerforea/eventhelper/util/ConvertUtils.java +++ b/src/main/java/com/gamerforea/eventhelper/util/ConvertUtils.java @@ -3,23 +3,28 @@ import java.lang.reflect.Method; import org.bukkit.Bukkit; +import org.bukkit.block.BlockFace; +import org.bukkit.entity.Player; import net.minecraft.entity.Entity; import net.minecraft.entity.player.EntityPlayer; +import net.minecraft.item.ItemStack; import net.minecraft.world.World; +import net.minecraftforge.common.util.ForgeDirection; public final class ConvertUtils { private static final Method getBukkitEntity; + private static final Method asCraftMirror; public static final org.bukkit.entity.Entity toBukkitEntity(Entity entity) throws Exception { return (org.bukkit.entity.Entity) getBukkitEntity.invoke(entity); } - public static final org.bukkit.entity.Player toBukkitEntity(EntityPlayer player) throws Exception + public static final Player toBukkitEntity(EntityPlayer player) throws Exception { - return (org.bukkit.entity.Player) getBukkitEntity.invoke(player); + return (Player) getBukkitEntity.invoke(player); } public static final org.bukkit.World toBukkitWorld(World world) @@ -27,16 +32,47 @@ public static final org.bukkit.World toBukkitWorld(World world) return Bukkit.getWorld(world.getWorldInfo().getWorldName()); } + public static final org.bukkit.inventory.ItemStack toBukkitItemStackMirror(ItemStack stack) throws Exception + { + return (org.bukkit.inventory.ItemStack) asCraftMirror.invoke(null, stack); + } + + public static final BlockFace toBukkitFace(ForgeDirection direction) + { + switch (direction) + { + case DOWN: + return BlockFace.DOWN; + case UP: + return BlockFace.UP; + case NORTH: + return BlockFace.NORTH; + case SOUTH: + return BlockFace.SOUTH; + case WEST: + return BlockFace.WEST; + case EAST: + return BlockFace.EAST; + case UNKNOWN: + return BlockFace.SELF; + default: + return BlockFace.SELF; + } + } + static { try { getBukkitEntity = Entity.class.getDeclaredMethod("getBukkitEntity"); getBukkitEntity.setAccessible(true); + + asCraftMirror = CraftUtils.getCraftClass("inventory/CraftItemStack").getDeclaredMethod("asCraftMirror", ItemStack.class); + asCraftMirror.setAccessible(true); } catch (Throwable throwable) { - throw new RuntimeException("Failed hooking Entity.getBukkitEntity() method!", throwable); + throw new RuntimeException("Failed hooking CraftBukkit methods!", throwable); } } } \ No newline at end of file diff --git a/src/main/java/com/gamerforea/eventhelper/util/CraftUtils.java b/src/main/java/com/gamerforea/eventhelper/util/CraftUtils.java new file mode 100644 index 0000000..8519fd1 --- /dev/null +++ b/src/main/java/com/gamerforea/eventhelper/util/CraftUtils.java @@ -0,0 +1,11 @@ +package com.gamerforea.eventhelper.util; + +import com.gamerforea.eventhelper.EventHelper; + +public final class CraftUtils +{ + public static final Class getCraftClass(String name) throws ClassNotFoundException + { + return Class.forName((EventHelper.craftPackage + '/' + name).replace("//", ".").replace('/', '.')); + } +} \ No newline at end of file diff --git a/src/main/java/com/gamerforea/eventhelper/util/EventUtils.java b/src/main/java/com/gamerforea/eventhelper/util/EventUtils.java index 4d35a95..51bd5b8 100644 --- a/src/main/java/com/gamerforea/eventhelper/util/EventUtils.java +++ b/src/main/java/com/gamerforea/eventhelper/util/EventUtils.java @@ -1,100 +1,127 @@ package com.gamerforea.eventhelper.util; import static com.gamerforea.eventhelper.util.ConvertUtils.toBukkitEntity; +import static com.gamerforea.eventhelper.util.ConvertUtils.toBukkitFace; +import static com.gamerforea.eventhelper.util.ConvertUtils.toBukkitItemStackMirror; import static com.gamerforea.eventhelper.util.ConvertUtils.toBukkitWorld; +import org.bukkit.entity.Player; +import org.bukkit.event.block.Action; import org.bukkit.event.block.BlockBreakEvent; +import org.bukkit.event.block.BlockFromToEvent; import org.bukkit.event.entity.EntityDamageByEntityEvent; import org.bukkit.event.entity.EntityDamageEvent.DamageCause; +import org.bukkit.event.player.PlayerInteractEvent; import com.gamerforea.eventhelper.EventHelper; -import com.gamerforea.eventhelper.wg.WGFastEvents; import com.gamerforea.eventhelper.wg.WGRegionChecker; import net.minecraft.entity.Entity; import net.minecraft.entity.player.EntityPlayer; +import net.minecraft.item.ItemStack; import net.minecraft.util.MathHelper; import net.minecraft.world.World; +import net.minecraftforge.common.util.ForgeDirection; public final class EventUtils { public static final boolean cantBreak(EntityPlayer player, int x, int y, int z) { - if (!EventHelper.fastEvents) - try - { - BlockBreakEvent event = new BlockBreakEvent(toBukkitWorld(player.worldObj).getBlockAt(x, y, z), toBukkitEntity(player)); - EventHelper.callEvent(event); - return event.isCancelled(); - } - catch (Throwable throwable) - { - System.err.println(String.format("Failed call BlockBreakEvent: [Player: %s, X:%d, Y:%d, Z:%d]", player.toString(), x, y, z)); - if (EventHelper.debug) - throwable.printStackTrace(); - return true; - } - else - try - { - return !WGFastEvents.hasAccess(toBukkitEntity(player), x, y, z, false); - } - catch (Throwable throwable) - { - System.err.println(String.format("Failed use fast hasAccess(): [Player: %s, X:%d, Y:%d, Z:%d]", player.toString(), x, y, z)); - if (EventHelper.debug) - throwable.printStackTrace(); - return true; - } + try + { + Player bPlayer = toBukkitEntity(player); + BlockBreakEvent event = new BlockBreakEvent(bPlayer.getWorld().getBlockAt(x, y, z), bPlayer); + EventHelper.callEvent(event); + return event.isCancelled(); + } + catch (Throwable throwable) + { + err("Failed call BlockBreakEvent: [Player: %s, X:%d, Y:%d, Z:%d]", String.valueOf(player), x, y, z); + if (EventHelper.debug) + throwable.printStackTrace(); + return true; + } } public static final boolean cantDamage(Entity damager, Entity damagee) { - if (!EventHelper.fastEvents) - try - { - EntityDamageByEntityEvent event = new EntityDamageByEntityEvent(toBukkitEntity(damager), toBukkitEntity(damagee), DamageCause.ENTITY_ATTACK, 0D); - EventHelper.callEvent(event); - return event.isCancelled(); - } - catch (Throwable throwable) - { - System.err.println(String.format("Failed call EntityDamageByEntityEvent: [Damager: %s, Damagee: %s]", damager.toString(), damagee.toString())); - if (EventHelper.debug) - throwable.printStackTrace(); - return true; - } - else - try - { - if (damager instanceof EntityPlayer) - { - int x = MathHelper.floor_double(damagee.posX); - int y = MathHelper.floor_double(damagee.posY); - int z = MathHelper.floor_double(damagee.posZ); - return !WGFastEvents.hasAccess(toBukkitEntity((EntityPlayer) damager), x, y, z, true); - } - else - return isInPrivate(damagee); - } - catch (Throwable throwable) - { - System.err.println(String.format("Failed use fast hasAccess(): [Damager: %s, Damagee: %s]", damager.toString(), damagee.toString())); - if (EventHelper.debug) - throwable.printStackTrace(); - return true; - } + try + { + EntityDamageByEntityEvent event = new EntityDamageByEntityEvent(toBukkitEntity(damager), toBukkitEntity(damagee), DamageCause.ENTITY_ATTACK, 0D); + EventHelper.callEvent(event); + return event.isCancelled(); + } + catch (Throwable throwable) + { + err("Failed call EntityDamageByEntityEvent: [Damager: %s, Damagee: %s]", String.valueOf(damager), String.valueOf(damagee)); + if (EventHelper.debug) + throwable.printStackTrace(); + return true; + } + } + + public static final boolean cantInteract(EntityPlayer player, ItemStack stack, int x, int y, int z, ForgeDirection side) + { + try + { + org.bukkit.entity.Player bPlayer = toBukkitEntity(player); + PlayerInteractEvent event = new PlayerInteractEvent(bPlayer, Action.RIGHT_CLICK_BLOCK, toBukkitItemStackMirror(stack), bPlayer.getWorld().getBlockAt(x, y, z), toBukkitFace(side)); + return event.isCancelled(); + } + catch (Throwable throwable) + { + err("Failed call PlayerInteractEvent: [Player: %s, Item: %s, X:%d, Y:%d, Z:%d, Side: %s]", String.valueOf(player), String.valueOf(stack), x, y, z, String.valueOf(side)); + if (EventHelper.debug) + throwable.printStackTrace(); + return true; + } + } + + public static final boolean cantFromTo(World world, int fromX, int fromY, int fromZ, int toX, int toY, int toZ) + { + try + { + org.bukkit.World bWorld = toBukkitWorld(world); + BlockFromToEvent event = new BlockFromToEvent(bWorld.getBlockAt(fromX, fromY, fromZ), bWorld.getBlockAt(toX, toY, toZ)); + EventHelper.callEvent(event); + return event.isCancelled(); + } + catch (Throwable throwable) + { + err("Failed call BlockFromToEvent: [FromX: %d, FromY: %d, FromZ: %d, ToX: %d, ToY: %d, ToZ: %d]", fromX, fromY, fromZ, toX, toY, toZ); + if (EventHelper.debug) + throwable.printStackTrace(); + return true; + } + } + + public static final boolean cantFromTo(World world, int fromX, int fromY, int fromZ, ForgeDirection direction) + { + try + { + org.bukkit.World bWorld = toBukkitWorld(world); + BlockFromToEvent event = new BlockFromToEvent(bWorld.getBlockAt(fromX, fromY, fromZ), toBukkitFace(direction)); + EventHelper.callEvent(event); + return event.isCancelled(); + } + catch (Throwable throwable) + { + err("Failed call BlockFromToEvent: [FromX: %d, FromY: %d, FromZ: %d, Direction: %s]", fromX, fromY, fromZ, String.valueOf(direction)); + if (EventHelper.debug) + throwable.printStackTrace(); + return true; + } } public static final boolean isInPrivate(World world, int x, int y, int z) { try { - return WGRegionChecker.isInPrivate(ConvertUtils.toBukkitWorld(world), x, y, z); + return WGRegionChecker.isInPrivate(toBukkitWorld(world), x, y, z); } catch (Throwable throwable) { - System.err.println(String.format("Failed check private: [World: %s, X: %d, Y: %d, Z: %d]", world.getWorldInfo().getWorldName(), x, y, z)); + err("Failed check private: [World: %s, X: %d, Y: %d, Z: %d]", world.getWorldInfo().getWorldName(), x, y, z); if (EventHelper.debug) throwable.printStackTrace(); return true; @@ -108,4 +135,9 @@ public static final boolean isInPrivate(Entity entity) int z = MathHelper.floor_double(entity.posZ); return isInPrivate(entity.worldObj, x, y, z); } + + private static final void err(String format, Object... args) + { + System.err.println(String.format(format, args)); + } } \ No newline at end of file diff --git a/src/main/java/com/gamerforea/eventhelper/util/FastUtils.java b/src/main/java/com/gamerforea/eventhelper/util/FastUtils.java index 798c148..7f17074 100644 --- a/src/main/java/com/gamerforea/eventhelper/util/FastUtils.java +++ b/src/main/java/com/gamerforea/eventhelper/util/FastUtils.java @@ -1,7 +1,6 @@ package com.gamerforea.eventhelper.util; import java.io.File; -import java.util.List; import com.gamerforea.eventhelper.EventHelper; import com.mojang.authlib.GameProfile; @@ -31,8 +30,7 @@ public static final boolean isOnline(EntityPlayer player) if (player instanceof FakePlayer) return true; - List playersOnline = FMLCommonHandler.instance().getMinecraftServerInstance().getConfigurationManager().playerEntityList; - for (EntityPlayer playerOnline : playersOnline) + for (EntityPlayer playerOnline : (Iterable) getServer().getConfigurationManager().playerEntityList) if (playerOnline.equals(player)) return true; @@ -41,37 +39,54 @@ public static final boolean isOnline(EntityPlayer player) public static final FakePlayer getFake(World world, FakePlayer fake) { - fake.worldObj = world; + fake.worldObj = world == null ? getEntityWorld() : world; return fake; } public static final FakePlayer getFake(World world, GameProfile profile) { - MinecraftServer server = FMLCommonHandler.instance().getMinecraftServerInstance(); - return getFake(world, FakePlayerFactory.get((WorldServer) (world == null ? server.getEntityWorld() : world), profile)); + return getFake(world, FakePlayerFactory.get((WorldServer) (world == null ? getEntityWorld() : world), profile)); + } + + public static final EntityPlayer getLivingPlayer(EntityLivingBase entity, FakePlayer modFake) + { + return entity instanceof EntityPlayer ? (EntityPlayer) entity : getFake(entity == null ? null : entity.worldObj, modFake); + } + + public static final EntityPlayer getLivingPlayer(EntityLivingBase entity, GameProfile modFakeProfile) + { + return entity instanceof EntityPlayer ? (EntityPlayer) entity : getFake(entity == null ? null : entity.worldObj, modFakeProfile); } public static final EntityPlayer getThrowerPlayer(EntityThrowable entity, FakePlayer modFake) { - EntityLivingBase thrower = entity.getThrower(); - return thrower instanceof EntityPlayer ? (EntityPlayer) thrower : getFake(entity.worldObj, modFake); + return getLivingPlayer(entity.getThrower(), modFake); } public static final EntityPlayer getThrowerPlayer(EntityThrowable entity, GameProfile modFakeProfile) { - EntityLivingBase thrower = entity.getThrower(); - return thrower instanceof EntityPlayer ? (EntityPlayer) thrower : getFake(entity.worldObj, modFakeProfile); + return getLivingPlayer(entity.getThrower(), modFakeProfile); } public static final EntityLivingBase getThrower(EntityThrowable entity, FakePlayer modFake) { EntityLivingBase thrower = entity.getThrower(); - return thrower != null ? thrower : getFake(entity.worldObj, modFake); + return thrower != null ? thrower : getFake(entity == null ? null : entity.worldObj, modFake); } public static final EntityLivingBase getThrower(EntityThrowable entity, GameProfile modFakeProfile) { EntityLivingBase thrower = entity.getThrower(); - return thrower != null ? thrower : getFake(entity.worldObj, modFakeProfile); + return thrower != null ? thrower : getFake(entity == null ? null : entity.worldObj, modFakeProfile); + } + + private static final MinecraftServer getServer() + { + return FMLCommonHandler.instance().getMinecraftServerInstance(); + } + + private static final World getEntityWorld() + { + return getServer().getEntityWorld(); } } \ No newline at end of file diff --git a/src/main/java/com/gamerforea/eventhelper/wg/WGFastEvents.java b/src/main/java/com/gamerforea/eventhelper/wg/WGFastEvents.java deleted file mode 100644 index b583a2d..0000000 --- a/src/main/java/com/gamerforea/eventhelper/wg/WGFastEvents.java +++ /dev/null @@ -1,51 +0,0 @@ -package com.gamerforea.eventhelper.wg; - -import java.lang.reflect.Method; - -import org.bukkit.entity.Player; - -import com.sk89q.worldedit.Vector; -import com.sk89q.worldguard.bukkit.BukkitPlayer; -import com.sk89q.worldguard.bukkit.WorldGuardPlugin; -import com.sk89q.worldguard.protection.flags.DefaultFlag; -import com.sk89q.worldguard.protection.flags.StateFlag.State; -import com.sk89q.worldguard.protection.regions.ProtectedRegion; - -public final class WGFastEvents -{ - private static final Method hasAccess; - - public static final boolean hasAccess(Player player, int x, int y, int z, boolean checkPvP) throws Throwable - { - return (Boolean) hasAccess.invoke(null, player, x, y, z); - } - - static - { - try - { - Class clazz = WGReflection.injectIntoWG(WGFastEvents.class); - hasAccess = clazz.getDeclaredMethod("hasAccessInj", Player.class, int.class, int.class, int.class, boolean.class); - hasAccess.setAccessible(true); - } - catch (Throwable throwable) - { - throw new RuntimeException("Failed injecting WGFastEvents$Inj.hasAccessInj() method!", throwable); - } - } - - public static final class Inj - { - public static final boolean hasAccessInj(Player player, int x, int y, int z, boolean checkPvP) - { - BukkitPlayer bPlayer = new BukkitPlayer(WorldGuardPlugin.inst(), player); - for (ProtectedRegion region : WorldGuardPlugin.inst().getRegionManager(player.getWorld()).getApplicableRegions(new Vector(x, y, z))) - if (!region.getId().equals(ProtectedRegion.GLOBAL_REGION)) - if (!region.isMember(bPlayer) && !region.isOwner(bPlayer)) - return false; - else if (checkPvP && region.getFlag(DefaultFlag.PVP) == State.DENY) - return false; - return true; - } - } -} \ No newline at end of file