Less object creation with short-use Locations + other preparation.

* Make use of Entity.getLocation(Location) in most places, for starters.
* Prepare a check for moving location consistency.
This commit is contained in:
asofold 2014-02-23 01:28:42 +01:00
parent 16db04f397
commit abdeb12377
23 changed files with 243 additions and 95 deletions

View File

@ -11,6 +11,9 @@ public class BlockCacheBukkit extends BlockCache{
protected World world; protected World world;
/** Temporary use. Use LocUtil.clone before passing on. Call setWorld(null) after use. */
protected final Location useLoc = new Location(null, 0, 0, 0);
public BlockCacheBukkit(World world) { public BlockCacheBukkit(World world) {
setAccess(world); setAccess(world);
} }
@ -49,8 +52,9 @@ public class BlockCacheBukkit extends BlockCache{
if (type != EntityType.BOAT){ // && !(other instanceof Minecart)) if (type != EntityType.BOAT){ // && !(other instanceof Minecart))
continue; continue;
} }
final Location loc = entity.getLocation(); final double locY = entity.getLocation(useLoc).getY();
if (Math.abs(loc.getY() - minY) < 0.7){ useLoc.setWorld(null);
if (Math.abs(locY - minY) < 0.7){
// TODO: A "better" estimate is possible, though some more tolerance would be good. // TODO: A "better" estimate is possible, though some more tolerance would be good.
return true; return true;
} }

View File

@ -13,6 +13,9 @@ import fr.neatmonster.nocheatplus.utilities.TrigUtil;
* The Direction check will find out if a player tried to interact with something that's not in their field of view. * The Direction check will find out if a player tried to interact with something that's not in their field of view.
*/ */
public class Direction extends Check { public class Direction extends Check {
/** For temporary use: LocUtil.clone before passing deeply, call setWorld(null) after use. */
private final Location useLoc = new Location(null, 0, 0, 0);
/** /**
* Instantiates a new direction check. * Instantiates a new direction check.
@ -36,7 +39,7 @@ public class Direction extends Check {
// How far "off" is the player with their aim. We calculate from the players eye location and view direction to // How far "off" is the player with their aim. We calculate from the players eye location and view direction to
// the center of the target block. If the line of sight is more too far off, "off" will be bigger than 0. // the center of the target block. If the line of sight is more too far off, "off" will be bigger than 0.
final Location loc = player.getLocation(); final Location loc = player.getLocation(useLoc);
final Vector direction = loc.getDirection(); final Vector direction = loc.getDirection();
final double off = TrigUtil.directionCheck(loc, player.getEyeHeight(), direction, block, TrigUtil.DIRECTION_PRECISION); final double off = TrigUtil.directionCheck(loc, player.getEyeHeight(), direction, block, TrigUtil.DIRECTION_PRECISION);
@ -52,10 +55,11 @@ public class Direction extends Check {
// cancel the event. // cancel the event.
cancel = executeActions(player, data.directionVL, distance, cancel = executeActions(player, data.directionVL, distance,
BlockBreakConfig.getConfig(player).directionActions); BlockBreakConfig.getConfig(player).directionActions);
} else } else {
// Player did likely nothing wrong, reduce violation counter to reward them. // Player did likely nothing wrong, reduce violation counter to reward them.
data.directionVL *= 0.9D; data.directionVL *= 0.9D;
}
useLoc.setWorld(null);
return cancel; return cancel;
} }
} }

View File

@ -3,6 +3,7 @@ package fr.neatmonster.nocheatplus.checks.blockbreak;
import java.util.Map; import java.util.Map;
import org.bukkit.GameMode; import org.bukkit.GameMode;
import org.bukkit.Location;
import org.bukkit.block.Block; import org.bukkit.block.Block;
import org.bukkit.entity.Player; import org.bukkit.entity.Player;
@ -16,6 +17,9 @@ import fr.neatmonster.nocheatplus.utilities.TrigUtil;
* The Reach check will find out if a player interacts with something that's too far away. * The Reach check will find out if a player interacts with something that's too far away.
*/ */
public class Reach extends Check { public class Reach extends Check {
/** For temporary use: LocUtil.clone before passing deeply, call setWorld(null) after use. */
private final Location useLoc = new Location(null, 0, 0, 0);
/** The maximum distance allowed to interact with a block in creative mode. */ /** The maximum distance allowed to interact with a block in creative mode. */
public static final double CREATIVE_DISTANCE = 5.6D; public static final double CREATIVE_DISTANCE = 5.6D;
@ -47,7 +51,10 @@ public class Reach extends Check {
// Distance is calculated from eye location to center of targeted block. If the player is further away from their // Distance is calculated from eye location to center of targeted block. If the player is further away from their
// target than allowed, the difference will be assigned to "distance". // target than allowed, the difference will be assigned to "distance".
final double distance = TrigUtil.distance(player.getEyeLocation(), block) - distanceLimit; final Location loc = player.getLocation(useLoc);
loc.setY(loc.getY() + player.getEyeHeight());
final double distance = TrigUtil.distance(loc, block) - distanceLimit;
useLoc.setWorld(null);
if (distance > 0) { if (distance > 0) {
// They failed, increment violation level. // They failed, increment violation level.

View File

@ -36,6 +36,9 @@ public class BlockInteractListener extends CheckListener {
/** Speed of interaction. */ /** Speed of interaction. */
private final Speed speed = addCheck(new Speed()); private final Speed speed = addCheck(new Speed());
/** For temporary use: LocUtil.clone before passing deeply, call setWorld(null) after use. */
private final Location useLoc = new Location(null, 0, 0, 0);
public BlockInteractListener(){ public BlockInteractListener(){
super(CheckType.BLOCKINTERACT); super(CheckType.BLOCKINTERACT);
} }
@ -86,7 +89,7 @@ public class BlockInteractListener extends CheckListener {
boolean cancelled = false; boolean cancelled = false;
final BlockFace face = event.getBlockFace(); final BlockFace face = event.getBlockFace();
final Location loc = player.getLocation(); final Location loc = player.getLocation(useLoc);
// Interaction speed. // Interaction speed.
if (!cancelled && speed.isEnabled(player) && speed.check(player, data, cc)){ if (!cancelled && speed.isEnabled(player) && speed.check(player, data, cc)){
@ -114,5 +117,6 @@ public class BlockInteractListener extends CheckListener {
event.setUseItemInHand(Result.DENY); event.setUseItemInHand(Result.DENY);
event.setCancelled(true); event.setCancelled(true);
} }
useLoc.setWorld(null);
} }
} }

View File

@ -75,6 +75,9 @@ public class BlockPlaceListener extends CheckListener {
/** The speed check. */ /** The speed check. */
private final Speed speed = addCheck(new Speed()); private final Speed speed = addCheck(new Speed());
/** For temporary use: LocUtil.clone before passing deeply, call setWorld(null) after use. */
private final Location useLoc = new Location(null, 0, 0, 0);
public BlockPlaceListener(){ public BlockPlaceListener(){
super(CheckType.BLOCKPLACE); super(CheckType.BLOCKPLACE);
} }
@ -131,6 +134,7 @@ public class BlockPlaceListener extends CheckListener {
if (!cancelled && reach.isEnabled(player) && reach.check(player, block, data, cc)) { if (!cancelled && reach.isEnabled(player) && reach.check(player, block, data, cc)) {
cancelled = true; cancelled = true;
} }
useLoc.setWorld(null);
// Direction check. // Direction check.
if (!cancelled && direction.isEnabled(player) && direction.check(player, block, blockAgainst, data, cc)) { if (!cancelled && direction.isEnabled(player) && direction.check(player, block, blockAgainst, data, cc)) {
@ -264,7 +268,7 @@ public class BlockPlaceListener extends CheckListener {
boolean cancel = false; boolean cancel = false;
if (speed.isEnabled(player)){ if (speed.isEnabled(player)){
final long now = System.currentTimeMillis(); final long now = System.currentTimeMillis();
final Location loc = player.getLocation(); final Location loc = player.getLocation(useLoc);
if (Combined.checkYawRate(player, loc.getYaw(), now, loc.getWorld().getName())){ if (Combined.checkYawRate(player, loc.getYaw(), now, loc.getWorld().getName())){
// Yawrate (checked extra). // Yawrate (checked extra).
cancel = true; cancel = true;
@ -285,19 +289,20 @@ public class BlockPlaceListener extends CheckListener {
// Do nothing ! // Do nothing !
// TODO: Might have further flags? // TODO: Might have further flags?
} }
else if (!BlockProperties.isPassable(projectile.getLocation())){ else if (!BlockProperties.isPassable(projectile.getLocation(useLoc))){
// Launch into a block. // Launch into a block.
// TODO: This might be a general check later. // TODO: This might be a general check later.
cancel = true; cancel = true;
} }
else{ else{
if (!BlockProperties.isPassable(player.getEyeLocation(), projectile.getLocation())){ if (!BlockProperties.isPassable(player.getEyeLocation(), projectile.getLocation(useLoc))){
// (Spare a useLoc2, for this is seldom rather.)
// Something between player // Something between player
// TODO: This might be a general check later. // TODO: This might be a general check later.
cancel = true; cancel = true;
} }
else{ else{
final Material mat = player.getLocation().getBlock().getType(); final Material mat = player.getLocation(useLoc).getBlock().getType();
final long flags = BlockProperties.F_CLIMBABLE | BlockProperties.F_LIQUID | BlockProperties.F_IGN_PASSABLE; final long flags = BlockProperties.F_CLIMBABLE | BlockProperties.F_LIQUID | BlockProperties.F_IGN_PASSABLE;
if (mat != Material.AIR && (BlockProperties.getBlockFlags(mat.getId()) & flags) == 0 && !mcAccess.hasGravity(mat)){ if (mat != Material.AIR && (BlockProperties.getBlockFlags(mat.getId()) & flags) == 0 && !mcAccess.hasGravity(mat)){
// Still fails on piston traps etc. // Still fails on piston traps etc.
@ -313,5 +318,7 @@ public class BlockPlaceListener extends CheckListener {
if (cancel){ if (cancel){
event.setCancelled(true); event.setCancelled(true);
} }
// Cleanup.
useLoc.setWorld(null);
} }
} }

View File

@ -13,6 +13,9 @@ import fr.neatmonster.nocheatplus.utilities.TrigUtil;
* The Direction check will find out if a player tried to interact with something that's not in their field of view. * The Direction check will find out if a player tried to interact with something that's not in their field of view.
*/ */
public class Direction extends Check { public class Direction extends Check {
/** For temporary use: LocUtil.clone before passing deeply, call setWorld(null) after use. */
private final Location useLoc = new Location(null, 0, 0, 0);
/** /**
* Instantiates a new direction check. * Instantiates a new direction check.
@ -38,7 +41,7 @@ public class Direction extends Check {
// How far "off" is the player with their aim. We calculate from the players eye location and view direction to // How far "off" is the player with their aim. We calculate from the players eye location and view direction to
// the center of the target block. If the line of sight is more too far off, "off" will be bigger than 0. // the center of the target block. If the line of sight is more too far off, "off" will be bigger than 0.
final Location loc = player.getLocation(); final Location loc = player.getLocation(useLoc);
final Vector direction = loc.getDirection(); final Vector direction = loc.getDirection();
double off = TrigUtil.directionCheck(loc, player.getEyeHeight(), direction, against, TrigUtil.DIRECTION_PRECISION); double off = TrigUtil.directionCheck(loc, player.getEyeHeight(), direction, against, TrigUtil.DIRECTION_PRECISION);
@ -75,10 +78,11 @@ public class Direction extends Check {
// Execute whatever actions are associated with this check and the violation level and find out if we should // Execute whatever actions are associated with this check and the violation level and find out if we should
// cancel the event. // cancel the event.
cancel = executeActions(player, data.directionVL, distance, cc.directionActions); cancel = executeActions(player, data.directionVL, distance, cc.directionActions);
} else } else {
// Player did likely nothing wrong, reduce violation counter to reward them. // Player did likely nothing wrong, reduce violation counter to reward them.
data.directionVL *= 0.9D; data.directionVL *= 0.9D;
}
useLoc.setWorld(null);
return cancel; return cancel;
} }
} }

View File

@ -3,6 +3,7 @@ package fr.neatmonster.nocheatplus.checks.blockplace;
import java.util.Map; import java.util.Map;
import org.bukkit.GameMode; import org.bukkit.GameMode;
import org.bukkit.Location;
import org.bukkit.block.Block; import org.bukkit.block.Block;
import org.bukkit.entity.Player; import org.bukkit.entity.Player;
@ -22,6 +23,9 @@ public class Reach extends Check {
/** The maximum distance allowed to interact with a block in survival mode. */ /** The maximum distance allowed to interact with a block in survival mode. */
public static final double SURVIVAL_DISTANCE = 5.2D; public static final double SURVIVAL_DISTANCE = 5.2D;
/** For temporary use: LocUtil.clone before passing deeply, call setWorld(null) after use. */
private final Location useLoc = new Location(null, 0, 0, 0);
/** /**
* Instantiates a new reach check. * Instantiates a new reach check.
@ -35,6 +39,7 @@ public class Reach extends Check {
* *
* @param player * @param player
* the player * the player
* @param loc
* @param cc * @param cc
* @param data2 * @param data2
* @param location * @param location
@ -49,7 +54,9 @@ public class Reach extends Check {
// Distance is calculated from eye location to center of targeted block. If the player is further away from their // Distance is calculated from eye location to center of targeted block. If the player is further away from their
// target than allowed, the difference will be assigned to "distance". // target than allowed, the difference will be assigned to "distance".
final double distance = TrigUtil.distance(player.getEyeLocation(), block) - distanceLimit; final Location eyeLoc = player.getLocation(useLoc);
eyeLoc.setY(eyeLoc.getY() + player.getEyeHeight());
final double distance = TrigUtil.distance(eyeLoc, block) - distanceLimit;
if (distance > 0) { if (distance > 0) {
// They failed, increment violation level. // They failed, increment violation level.
@ -66,7 +73,9 @@ public class Reach extends Check {
data.reachVL *= 0.9D; data.reachVL *= 0.9D;
} }
// Cleanup.
useLoc.setWorld(null);
return cancel; return cancel;
} }

View File

@ -49,7 +49,7 @@ public class Angle extends Check {
data.angleHits.remove(time); data.angleHits.remove(time);
// Add the new location to the map. // Add the new location to the map.
data.angleHits.put(System.currentTimeMillis(), player.getLocation()); data.angleHits.put(System.currentTimeMillis(), player.getLocation()); // This needs to be a copy at present.
// Not enough data to calculate deltas. // Not enough data to calculate deltas.
if (data.angleHits.size() < 2) if (data.angleHits.size() < 2)

View File

@ -38,14 +38,11 @@ public class Critical extends Check {
* the player * the player
* @return true, if successful * @return true, if successful
*/ */
public boolean check(final Player player) { public boolean check(final Player player, final Location loc) {
final FightConfig cc = FightConfig.getConfig(player); final FightConfig cc = FightConfig.getConfig(player);
final FightData data = FightData.getData(player); final FightData data = FightData.getData(player);
boolean cancel = false; boolean cancel = false;
// We'll need the PlayerLocation to know some important stuff.
final Location loc = player.getLocation();
final float mcFallDistance = player.getFallDistance(); final float mcFallDistance = player.getFallDistance();
final MovingConfig mCc = MovingConfig.getConfig(player); final MovingConfig mCc = MovingConfig.getConfig(player);

View File

@ -30,7 +30,7 @@ public class Direction extends Check {
* the damaged * the damaged
* @return true, if successful * @return true, if successful
*/ */
public boolean check(final Player player, final Entity damaged) { public boolean check(final Player player, final Location loc, final Entity damaged, final Location dLoc) {
final FightConfig cc = FightConfig.getConfig(player); final FightConfig cc = FightConfig.getConfig(player);
final FightData data = FightData.getData(player); final FightData data = FightData.getData(player);
@ -47,14 +47,11 @@ public class Direction extends Check {
// entity.height is broken and will always be 0, therefore. Calculate height instead based on boundingBox. // entity.height is broken and will always be 0, therefore. Calculate height instead based on boundingBox.
final double height = mcAccess.getHeight(damaged); final double height = mcAccess.getHeight(damaged);
final Location dLoc = damaged.getLocation();
// TODO: allow any hit on the y axis (might just adapt interface to use foot position + height)! // TODO: allow any hit on the y axis (might just adapt interface to use foot position + height)!
// How far "off" is the player with their aim. We calculate from the players eye location and view direction to // How far "off" is the player with their aim. We calculate from the players eye location and view direction to
// the center of the target entity. If the line of sight is more too far off, "off" will be bigger than 0. // the center of the target entity. If the line of sight is more too far off, "off" will be bigger than 0.
final Location loc = player.getLocation(); final Vector direction = loc.getDirection();
final Vector direction = player.getEyeLocation().getDirection();
final double off; final double off;
if (cc.directionStrict){ if (cc.directionStrict){

View File

@ -74,6 +74,12 @@ public class FightListener extends CheckListener implements JoinLeaveListener{
/** The speed check. */ /** The speed check. */
private final Speed speed = addCheck(new Speed()); private final Speed speed = addCheck(new Speed());
/** For temporary use: LocUtil.clone before passing deeply, call setWorld(null) after use. */
private final Location useLoc1 = new Location(null, 0, 0, 0);
/** For temporary use: LocUtil.clone before passing deeply, call setWorld(null) after use. */
private final Location useLoc2 = new Location(null, 0, 0, 0);
public FightListener(){ public FightListener(){
super(CheckType.FIGHT); super(CheckType.FIGHT);
} }
@ -100,8 +106,8 @@ public class FightListener extends CheckListener implements JoinLeaveListener{
final long now = System.currentTimeMillis(); final long now = System.currentTimeMillis();
final boolean worldChanged = !worldName.equals(data.lastWorld); final boolean worldChanged = !worldName.equals(data.lastWorld);
final Location loc = player.getLocation(); final Location loc = player.getLocation(useLoc1);
final Location targetLoc = damaged.getLocation(); final Location damagedLoc = damaged.getLocation(useLoc2);
// final double targetDist = CheckUtils.distance(loc, targetLoc); // TODO: Calculate distance as is done in fight.reach ! // final double targetDist = CheckUtils.distance(loc, targetLoc); // TODO: Calculate distance as is done in fight.reach !
final double targetMove; final double targetMove;
final int tickAge; final int tickAge;
@ -118,7 +124,7 @@ public class FightListener extends CheckListener implements JoinLeaveListener{
else{ else{
tickAge = tick - data.lastAttackTick; tickAge = tick - data.lastAttackTick;
// TODO: Maybe use 3d distance if dy(normalized) is too big. // TODO: Maybe use 3d distance if dy(normalized) is too big.
targetMove = TrigUtil.distance(data.lastAttackedX, data.lastAttackedZ, targetLoc.getX(), targetLoc.getZ()); targetMove = TrigUtil.distance(data.lastAttackedX, data.lastAttackedZ, damagedLoc.getX(), damagedLoc.getZ());
msAge = (long) (50f * TickTask.getLag(50L * tickAge) * (float) tickAge); msAge = (long) (50f * TickTask.getLag(50L * tickAge) * (float) tickAge);
normalizedMove = msAge == 0 ? targetMove : targetMove * Math.min(20.0, 1000.0 / (double) msAge); normalizedMove = msAge == 0 ? targetMove : targetMove * Math.min(20.0, 1000.0 / (double) msAge);
} }
@ -188,39 +194,45 @@ public class FightListener extends CheckListener implements JoinLeaveListener{
if (angle.check(player, worldChanged)) cancelled = true; if (angle.check(player, worldChanged)) cancelled = true;
} }
if (!cancelled && critical.isEnabled(player) && critical.check(player)) if (!cancelled && critical.isEnabled(player) && critical.check(player, loc)) {
cancelled = true; cancelled = true;
}
if (!cancelled && knockback.isEnabled(player) && knockback.check(player)) if (!cancelled && knockback.isEnabled(player) && knockback.check(player)) {
cancelled = true; cancelled = true;
}
if (!cancelled && noSwing.isEnabled(player) && noSwing.check(player)) if (!cancelled && noSwing.isEnabled(player) && noSwing.check(player)) {
cancelled = true; cancelled = true;
}
if (!cancelled && player.isBlocking() && !player.hasPermission(Permissions.MOVING_SURVIVALFLY_BLOCKING)) if (!cancelled && player.isBlocking() && !player.hasPermission(Permissions.MOVING_SURVIVALFLY_BLOCKING)) {
cancelled = true; cancelled = true;
}
// TODO: Order of the last two [might put first] ? // TODO: Order of the last two [might put first] ?
if (!cancelled && reach.isEnabled(player) && reach.check(player, damaged)) if (!cancelled && reach.isEnabled(player) && reach.check(player, loc, damaged, damagedLoc)) {
cancelled = true; cancelled = true;
}
if (!cancelled && direction.isEnabled(player) && direction.check(player, damaged)) if (!cancelled && direction.isEnabled(player) && direction.check(player, loc, damaged, damagedLoc)) {
cancelled = true; cancelled = true;
}
// Set values. // Set values.
data.lastWorld = worldName; data.lastWorld = worldName;
data.lastAttackTick = tick; data.lastAttackTick = tick;
data.lastAttackedX = targetLoc.getX(); data.lastAttackedX = damagedLoc.getX();
data.lastAttackedY = targetLoc.getY(); data.lastAttackedY = damagedLoc.getY();
data.lastAttackedZ = targetLoc.getZ(); data.lastAttackedZ = damagedLoc.getZ();
// data.lastAttackedDist = targetDist; // data.lastAttackedDist = targetDist;
// Care for the "lost sprint problem": sprint resets, client moves as if still... // Care for the "lost sprint problem": sprint resets, client moves as if still...
// TODO: Use stored distance calculation same as reach check? // TODO: Use stored distance calculation same as reach check?
// TODO: For pvp: make use of "player was there" heuristic later on. // TODO: For pvp: make use of "player was there" heuristic later on.
// TODO: Confine further with simple pre-conditions. // TODO: Confine further with simple pre-conditions.
if (!cancelled && TrigUtil.distance(loc.getX(), loc.getZ(), targetLoc.getX(), targetLoc.getZ()) < 4.5){ if (!cancelled && TrigUtil.distance(loc.getX(), loc.getZ(), damagedLoc.getX(), damagedLoc.getZ()) < 4.5){
final MovingData mData = MovingData.getData(player); final MovingData mData = MovingData.getData(player);
// Check if fly checks is an issue at all, re-check "real sprinting". // Check if fly checks is an issue at all, re-check "real sprinting".
if (mData.fromX != Double.MAX_VALUE && mData.mediumLiftOff != MediumLiftOff.LIMIT_JUMP){ if (mData.fromX != Double.MAX_VALUE && mData.mediumLiftOff != MediumLiftOff.LIMIT_JUMP){
@ -233,7 +245,7 @@ public class FightListener extends CheckListener implements JoinLeaveListener{
// TODO: What would mData.lostSprintCount > 0 mean here? // TODO: What would mData.lostSprintCount > 0 mean here?
mData.lostSprintCount = 7; mData.lostSprintCount = 7;
if ((cc.debug || mc.debug) && BuildParameters.debugLevel > 0){ if ((cc.debug || mc.debug) && BuildParameters.debugLevel > 0){
System.out.println(player.getName() + " (lostsprint) hDist to last from: " + hDist + " | targetdist=" + TrigUtil.distance(loc.getX(), loc.getZ(), targetLoc.getX(), targetLoc.getZ()) + " | sprinting=" + player.isSprinting() + " | food=" + player.getFoodLevel() +" | hbuf=" + mData.sfHorizontalBuffer); System.out.println(player.getName() + " (lostsprint) hDist to last from: " + hDist + " | targetdist=" + TrigUtil.distance(loc.getX(), loc.getZ(), damagedLoc.getX(), damagedLoc.getZ()) + " | sprinting=" + player.isSprinting() + " | food=" + player.getFoodLevel() +" | hbuf=" + mData.sfHorizontalBuffer);
} }
} }
} }
@ -248,7 +260,11 @@ public class FightListener extends CheckListener implements JoinLeaveListener{
System.out.println(player.getName() + " ~ attack penalty."); System.out.println(player.getName() + " ~ attack penalty.");
} }
} }
// Cleanup.
useLoc1.setWorld(null);
useLoc2.setWorld(null);
return cancelled; return cancelled;
} }

View File

@ -51,7 +51,7 @@ public class Reach extends Check {
* the damaged * the damaged
* @return true, if successful * @return true, if successful
*/ */
public boolean check(final Player player, final Entity damaged) { public boolean check(final Player player, final Location pLoc, final Entity damaged, final Location dRef) {
final FightConfig cc = FightConfig.getConfig(player); final FightConfig cc = FightConfig.getConfig(player);
final FightData data = FightData.getData(player); final FightData data = FightData.getData(player);
@ -67,20 +67,17 @@ public class Reach extends Check {
final double distanceLimit = player.getGameMode() == GameMode.CREATIVE ? CREATIVE_DISTANCE : SURVIVAL_DISTANCE + getDistMod(damaged); final double distanceLimit = player.getGameMode() == GameMode.CREATIVE ? CREATIVE_DISTANCE : SURVIVAL_DISTANCE + getDistMod(damaged);
final double distanceMin = (distanceLimit - DYNAMIC_RANGE) / distanceLimit; final double distanceMin = (distanceLimit - DYNAMIC_RANGE) / distanceLimit;
// Reference locations to check distance for.
final Location dRef = damaged.getLocation();
final double height = mcAccess.getHeight(damaged); final double height = mcAccess.getHeight(damaged);
final Location pRef = player.getEyeLocation();
// Refine y position. // Refine y position.
// TODO: Make a little more accurate by counting in the actual bounding box. // TODO: Make a little more accurate by counting in the actual bounding box.
final double pY = pRef.getY(); final double pY = pLoc.getY() + player.getEyeHeight();
final double dY = dRef.getY(); final double dY = dRef.getY();
if (pY <= dY); // Keep the foot level y. if (pY <= dY); // Keep the foot level y.
else if (pY >= dY + height) dRef.setY(dY + height); // Highest ref y. else if (pY >= dY + height) dRef.setY(dY + height); // Highest ref y.
else dRef.setY(pY); // Level with damaged. else dRef.setY(pY); // Level with damaged.
final Vector pRel = dRef.toVector().subtract(pRef.toVector()); final Vector pRel = dRef.toVector().subtract(pLoc.toVector().setY(pY)); // TODO: Run calculations on numbers only :p.
// Distance is calculated from eye location to center of targeted. If the player is further away from their target // Distance is calculated from eye location to center of targeted. If the player is further away from their target
// than allowed, the difference will be assigned to "distance". // than allowed, the difference will be assigned to "distance".

View File

@ -55,6 +55,9 @@ public class InventoryListener extends CheckListener implements JoinLeaveListen
private final Open open = addCheck(new Open()); private final Open open = addCheck(new Open());
/** For temporary use: LocUtil.clone before passing deeply, call setWorld(null) after use. */
private final Location useLoc = new Location(null, 0, 0, 0);
public InventoryListener(){ public InventoryListener(){
super(CheckType.INVENTORY); super(CheckType.INVENTORY);
} }
@ -73,7 +76,7 @@ public class InventoryListener extends CheckListener implements JoinLeaveListen
final Player player = (Player) event.getEntity(); final Player player = (Player) event.getEntity();
if (instantBow.isEnabled(player)){ if (instantBow.isEnabled(player)){
final long now = System.currentTimeMillis(); final long now = System.currentTimeMillis();
final Location loc = player.getLocation(); final Location loc = player.getLocation(useLoc);
if (Combined.checkYawRate(player, loc.getYaw(), now, loc.getWorld().getName())){ if (Combined.checkYawRate(player, loc.getYaw(), now, loc.getWorld().getName())){
// No else if with this, could be cancelled due to other checks feeding, does not have actions. // No else if with this, could be cancelled due to other checks feeding, does not have actions.
event.setCancelled(true); event.setCancelled(true);
@ -87,6 +90,7 @@ public class InventoryListener extends CheckListener implements JoinLeaveListen
// Combined fighting speed (Else if: Matter of taste, preventing extreme cascading and actions spam). // Combined fighting speed (Else if: Matter of taste, preventing extreme cascading and actions spam).
event.setCancelled(true); event.setCancelled(true);
} }
useLoc.setWorld(null);
} }
} }
} }

View File

@ -16,6 +16,8 @@ public class MoveInfo {
public final BlockCache cache; public final BlockCache cache;
public final PlayerLocation from; public final PlayerLocation from;
public final PlayerLocation to; public final PlayerLocation to;
/** For temporary use. Might need cloning for passing to external API. */
public final Location useLoc = new Location(null, 0, 0, 0);
public MoveInfo(final MCAccess mcAccess){ public MoveInfo(final MCAccess mcAccess){
cache = mcAccess.getBlockCache(null); cache = mcAccess.getBlockCache(null);
@ -38,10 +40,12 @@ public class MoveInfo {
this.to.set(to, player, yOnGround); this.to.set(to, player, yOnGround);
this.to.setBlockCache(cache); this.to.setBlockCache(cache);
} }
useLoc.setWorld(null); // Just in case of repeated setting.
} }
public final void cleanup(){ public final void cleanup(){
from.cleanup(); from.cleanup();
to.cleanup(); to.cleanup();
cache.cleanup(); cache.cleanup();
useLoc.setWorld(null);
} }
} }

View File

@ -139,6 +139,8 @@ public class MovingConfig extends ACheckConfig {
public final int speedGrace; public final int speedGrace;
public final boolean vehicleEnforceLocation; public final boolean vehicleEnforceLocation;
public final boolean vehiclePreventDestroyOwn; public final boolean vehiclePreventDestroyOwn;
public final boolean enforceLocation = true; // TODO: Configurable + name.
/** /**
* Instantiates a new moving configuration. * Instantiates a new moving configuration.

View File

@ -269,8 +269,12 @@ public class MovingData extends ACheckData {
* @param loc * @param loc
*/ */
public void resetPositions(final Location loc) { public void resetPositions(final Location loc) {
if (loc == null) resetPositions(Double.MAX_VALUE, 0, 0); if (loc == null) {
else resetPositions(loc.getX(), loc.getY(), loc.getZ()); resetPositions(Double.MAX_VALUE, 0, 0);
}
else {
resetPositions(loc.getX(), loc.getY(), loc.getZ());
}
} }
/** /**
@ -278,8 +282,12 @@ public class MovingData extends ACheckData {
* @param loc * @param loc
*/ */
public void resetPositions(PlayerLocation loc) { public void resetPositions(PlayerLocation loc) {
if (loc == null) resetPositions(Double.MAX_VALUE, 0, 0); if (loc == null) {
else resetPositions(loc.getX(), loc.getY(), loc.getZ()); resetPositions(Double.MAX_VALUE, 0, 0);
}
else {
resetPositions(loc.getX(), loc.getY(), loc.getZ());
}
} }
/** /**
@ -375,8 +383,12 @@ public class MovingData extends ACheckData {
} }
public boolean hasSetBackWorldChanged(final Location loc) { public boolean hasSetBackWorldChanged(final Location loc) {
if (setBack == null) return true; if (setBack == null) {
else return setBack.getWorld().equals(loc.getWorld()); return true;
}
else {
return setBack.getWorld().equals(loc.getWorld());
}
} }
@ -418,13 +430,21 @@ public class MovingData extends ACheckData {
} }
public final void setMorePacketsSetBack(final PlayerLocation loc) { public final void setMorePacketsSetBack(final PlayerLocation loc) {
if (morePacketsSetback == null) morePacketsSetback = loc.getLocation(); if (morePacketsSetback == null) {
else LocUtil.set(morePacketsSetback, loc); morePacketsSetback = loc.getLocation();
}
else {
LocUtil.set(morePacketsSetback, loc);
}
} }
public final void setMorePacketsSetBack(final Location loc) { public final void setMorePacketsSetBack(final Location loc) {
if (morePacketsSetback == null) morePacketsSetback = LocUtil.clone(loc); if (morePacketsSetback == null) {
else LocUtil.set(morePacketsSetback, loc); morePacketsSetback = LocUtil.clone(loc);
}
else {
LocUtil.set(morePacketsSetback, loc);
}
} }
public Location getMorePacketsSetBack() { public Location getMorePacketsSetBack() {
@ -436,13 +456,21 @@ public class MovingData extends ACheckData {
} }
public final void setMorePacketsVehicleSetBack(final PlayerLocation loc) { public final void setMorePacketsVehicleSetBack(final PlayerLocation loc) {
if (morePacketsVehicleSetback == null) morePacketsVehicleSetback = loc.getLocation(); if (morePacketsVehicleSetback == null) {
else LocUtil.set(morePacketsVehicleSetback, loc); morePacketsVehicleSetback = loc.getLocation();
}
else {
LocUtil.set(morePacketsVehicleSetback, loc);
}
} }
public final void setMorePacketsVehicleSetBack(final Location loc) { public final void setMorePacketsVehicleSetBack(final Location loc) {
if (morePacketsVehicleSetback == null) morePacketsVehicleSetback = LocUtil.clone(loc); if (morePacketsVehicleSetback == null) {
else LocUtil.set(morePacketsVehicleSetback, loc); morePacketsVehicleSetback = LocUtil.clone(loc);
}
else {
LocUtil.set(morePacketsVehicleSetback, loc);
}
} }
public final Location getMorePacketsVehicleSetBack() { public final Location getMorePacketsVehicleSetBack() {

View File

@ -170,12 +170,19 @@ public class MovingListener extends CheckListener implements TickListener, IRemo
*/ */
private final Map<String, PlayerMoveEvent> processingEvents = new HashMap<String, PlayerMoveEvent>(); private final Map<String, PlayerMoveEvent> processingEvents = new HashMap<String, PlayerMoveEvent>();
private final Set<String> hoverTicks = new LinkedHashSet<String>(30); /** Player names to check hover for, case insensitive. */
private final Set<String> hoverTicks = new LinkedHashSet<String>(30); // TODO: Rename
/** Player names to check enforcing the location for in onTick, case insensitive. */
private final Set<String> playersEnforce = new LinkedHashSet<String>(30);
private int hoverTicksStep = 5; private int hoverTicksStep = 5;
private final Set<EntityType> normalVehicles = new HashSet<EntityType>(); private final Set<EntityType> normalVehicles = new HashSet<EntityType>();
/** Location for temporary use with getLocation(useLoc). Always call setWorld(null) after use. Use LocUtil.clone before passing to other API. */
private final Location useLoc = new Location(null, 0, 0, 0); // TODO: Put to use...
public MovingListener() { public MovingListener() {
super(CheckType.MOVING); super(CheckType.MOVING);
} }
@ -212,7 +219,7 @@ public class MovingListener extends CheckListener implements TickListener, IRemo
if (!data.hasSetBack() || blockY + 1D < data.getSetBackY()) return; if (!data.hasSetBack() || blockY + 1D < data.getSetBackY()) return;
final Location loc = player.getLocation(); final Location loc = player.getLocation(useLoc);
if (Math.abs(loc.getX() - 0.5 - block.getX()) <= 1D if (Math.abs(loc.getX() - 0.5 - block.getX()) <= 1D
&& Math.abs(loc.getZ() - 0.5 - block.getZ()) <= 1D && Math.abs(loc.getZ() - 0.5 - block.getZ()) <= 1D
&& loc.getY() - blockY > 0D && loc.getY() - blockY < 2D && loc.getY() - blockY > 0D && loc.getY() - blockY < 2D
@ -223,6 +230,7 @@ public class MovingListener extends CheckListener implements TickListener, IRemo
data.setSetBackY(blockY + 1D); data.setSetBackY(blockY + 1D);
data.sfJumpPhase = 0; data.sfJumpPhase = 0;
} }
useLoc.setWorld(null);
} }
/** /**
@ -261,16 +269,19 @@ public class MovingListener extends CheckListener implements TickListener, IRemo
if (bedLeave.isEnabled(player) && bedLeave.checkBed(player)) { if (bedLeave.isEnabled(player) && bedLeave.checkBed(player)) {
// Check if the player has to be reset. // Check if the player has to be reset.
// To "cancel" the event, we teleport the player. // To "cancel" the event, we teleport the player.
final Location loc = player.getLocation(); final Location loc = player.getLocation(useLoc);
final MovingData data = MovingData.getData(player); final MovingData data = MovingData.getData(player);
final MovingConfig cc = MovingConfig.getConfig(player); final MovingConfig cc = MovingConfig.getConfig(player);
Location target = null; Location target = null;
final boolean sfCheck = shouldCheckSurvivalFly(player, data, cc); final boolean sfCheck = shouldCheckSurvivalFly(player, data, cc);
if (sfCheck) target = data.getSetBack(loc); if (sfCheck) {
target = data.getSetBack(loc);
}
if (target == null) { if (target == null) {
// TODO: Add something to guess the best set back location (possibly data.guessSetBack(Location)). // TODO: Add something to guess the best set back location (possibly data.guessSetBack(Location)).
target = loc; target = LocUtil.clone(loc);
} }
useLoc.setWorld(null);
if (target != null) { if (target != null) {
// Actually this should not possibly be null, this is a block for "future" purpose, feel free to criticize it. // Actually this should not possibly be null, this is a block for "future" purpose, feel free to criticize it.
if (sfCheck && cc.sfFallDamage && noFall.isEnabled(player)) { if (sfCheck && cc.sfFallDamage && noFall.isEnabled(player)) {
@ -306,7 +317,8 @@ public class MovingListener extends CheckListener implements TickListener, IRemo
data.clearFlyData(); data.clearFlyData();
data.clearMorePacketsData(); data.clearMorePacketsData();
// TODO: Might omit this if neither check is activated. // TODO: Might omit this if neither check is activated.
data.setSetBack(player.getLocation()); data.setSetBack(player.getLocation(useLoc));
useLoc.setWorld(null);
} }
/** /**
@ -382,6 +394,7 @@ public class MovingListener extends CheckListener implements TickListener, IRemo
} }
return; return;
} }
// newTo should be null here.
// TODO: Order this to above "early return"? // TODO: Order this to above "early return"?
// Set up data / caching. // Set up data / caching.
@ -404,6 +417,10 @@ public class MovingListener extends CheckListener implements TickListener, IRemo
parkedInfo.add(moveInfo); parkedInfo.add(moveInfo);
return; return;
} }
// Check for location consistency.
if (cc.enforceLocation) {
// TODO: Check if lastTo matches from.
}
final long time = System.currentTimeMillis(); final long time = System.currentTimeMillis();
if (player.isSprinting() || cc.assumeSprint) { if (player.isSprinting() || cc.assumeSprint) {
@ -447,7 +464,7 @@ public class MovingListener extends CheckListener implements TickListener, IRemo
// The players location. // The players location.
// TODO: Change to getLocation(moveInfo.loc) once 1.4.5 support is dropped. // TODO: Change to getLocation(moveInfo.loc) once 1.4.5 support is dropped.
final Location loc = (cc.noFallCheck || cc.passableCheck) ? player.getLocation() : null; final Location loc = (cc.noFallCheck || cc.passableCheck) ? player.getLocation(moveInfo.useLoc) : null;
// Check passable first to prevent set-back override. // Check passable first to prevent set-back override.
// TODO: Redesign to set set-backs later (queue + invalidate). // TODO: Redesign to set set-backs later (queue + invalidate).
@ -612,7 +629,7 @@ public class MovingListener extends CheckListener implements TickListener, IRemo
data.sfLowJump = false; data.sfLowJump = false;
// TODO: What with processingEvents.remove(player.getName()); // TODO: What with processingEvents.remove(player.getName());
if (vehicle != null) { if (vehicle != null) {
final Location vLoc = vehicle.getLocation(); final Location vLoc = vehicle.getLocation(); // TODO: Use a location as argument.
// (Auto detection of missing events, might fire one time too many per plugin run.) // (Auto detection of missing events, might fire one time too many per plugin run.)
if (!normalVehicles.contains(vehicle.getType())) { if (!normalVehicles.contains(vehicle.getType())) {
onVehicleMove(vehicle, vLoc, vLoc, true); onVehicleMove(vehicle, vLoc, vLoc, true);
@ -688,7 +705,8 @@ public class MovingListener extends CheckListener implements TickListener, IRemo
// TODO: maybe even not count vehicles at all ? // TODO: maybe even not count vehicles at all ?
if (player.isInsideVehicle()) { if (player.isInsideVehicle()) {
// TODO: refine (!). // TODO: refine (!).
MovingData.getData(player).resetPositions(player.getVehicle().getLocation()); MovingData.getData(player).resetPositions(player.getVehicle().getLocation(useLoc));
useLoc.setWorld(null);
} }
else if (!fromWorldName.equals(toWorldName)) { else if (!fromWorldName.equals(toWorldName)) {
MovingData.getData(player).resetPositions(to); MovingData.getData(player).resetPositions(to);
@ -755,7 +773,8 @@ public class MovingListener extends CheckListener implements TickListener, IRemo
final MovingData data = MovingData.getData(player); final MovingData data = MovingData.getData(player);
data.clearFlyData(); data.clearFlyData();
data.clearMorePacketsData(); data.clearMorePacketsData();
data.setSetBack(player.getLocation()); // TODO: Monitor this change (!). data.setSetBack(player.getLocation(useLoc)); // TODO: Monitor this change (!).
useLoc.setWorld(null);
} }
/** /**
@ -843,7 +862,7 @@ public class MovingListener extends CheckListener implements TickListener, IRemo
event.setTo(ref); event.setTo(ref);
} }
else{ else{
ref = from; ref = from; // Player.getLocation ?
event.setCancelled(true); event.setCancelled(true);
} }
} }
@ -1016,11 +1035,11 @@ public class MovingListener extends CheckListener implements TickListener, IRemo
if (!from.getWorld().equals(to.getWorld())) return; if (!from.getWorld().equals(to.getWorld())) return;
final MovingData data = MovingData.getData(player); final MovingData data = MovingData.getData(player);
data.vehicleConsistency = MoveConsistency.getConsistency(from, to, player.getLocation()); data.vehicleConsistency = MoveConsistency.getConsistency(from, to, player.getLocation(useLoc));
switch (data.vehicleConsistency) { switch (data.vehicleConsistency) {
case FROM: case FROM:
case TO: case TO:
data.resetPositions(player.getLocation()); // TODO: Drop MC 1.4! data.resetPositions(player.getLocation(useLoc)); // TODO: Drop MC 1.4!
break; break;
case INCONSISTENT: case INCONSISTENT:
// TODO: Any exploits exist? -> TeleportUtil.forceMount(player, vehicle) // TODO: Any exploits exist? -> TeleportUtil.forceMount(player, vehicle)
@ -1062,6 +1081,7 @@ public class MovingListener extends CheckListener implements TickListener, IRemo
// TODO: Reset on world changes or not? // TODO: Reset on world changes or not?
data.morePacketsVehicleTaskId = Bukkit.getScheduler().scheduleSyncDelayedTask(plugin, new VehicleSetBack(vehicle, player, newTo, cc.debug)); data.morePacketsVehicleTaskId = Bukkit.getScheduler().scheduleSyncDelayedTask(plugin, new VehicleSetBack(vehicle, player, newTo, cc.debug));
} }
useLoc.setWorld(null);
} }
@EventHandler(priority = EventPriority.LOWEST, ignoreCancelled = false) @EventHandler(priority = EventPriority.LOWEST, ignoreCancelled = false)
@ -1076,7 +1096,7 @@ public class MovingListener extends CheckListener implements TickListener, IRemo
data.clearNoFallData(); data.clearNoFallData();
return; return;
} }
final Location loc = player.getLocation(); final Location loc = player.getLocation(useLoc);
boolean allowReset = true; boolean allowReset = true;
if (!data.noFallSkipAirCheck) { if (!data.noFallSkipAirCheck) {
final MoveInfo moveInfo; final MoveInfo moveInfo;
@ -1107,6 +1127,7 @@ public class MovingListener extends CheckListener implements TickListener, IRemo
moveInfo.cleanup(); moveInfo.cleanup();
parkedInfo.add(moveInfo); parkedInfo.add(moveInfo);
} }
useLoc.setWorld(null);
final float fallDistance = player.getFallDistance(); final float fallDistance = player.getFallDistance();
final double damage = BridgeHealth.getDamage(event); final double damage = BridgeHealth.getDamage(event);
final float yDiff = (float) (data.noFallMaxY - loc.getY()); final float yDiff = (float) (data.noFallMaxY - loc.getY());
@ -1148,7 +1169,7 @@ public class MovingListener extends CheckListener implements TickListener, IRemo
// TODO: on existing set back: detect world changes and loss of world on join (+ set up some paradigm). // TODO: on existing set back: detect world changes and loss of world on join (+ set up some paradigm).
data.clearMorePacketsData(); data.clearMorePacketsData();
data.removeAllVelocity(); data.removeAllVelocity();
final Location loc = player.getLocation(); final Location loc = player.getLocation(useLoc);
// Correct set-back on join. // Correct set-back on join.
if (data.hasSetBackWorldChanged(loc)) { if (data.hasSetBackWorldChanged(loc)) {
@ -1169,6 +1190,11 @@ public class MovingListener extends CheckListener implements TickListener, IRemo
data.toWasReset = BlockProperties.isOnGroundOrResetCond(player, loc, cc.yOnGround); data.toWasReset = BlockProperties.isOnGroundOrResetCond(player, loc, cc.yOnGround);
data.fromWasReset = data.toWasReset; data.fromWasReset = data.toWasReset;
// Enforcing the location.
if (cc.enforceLocation) {
playersEnforce.add(player.getName());
}
// Hover. // Hover.
// Reset hover ticks until a better method is used. // Reset hover ticks until a better method is used.
if (cc.sfHoverCheck) { if (cc.sfHoverCheck) {
@ -1192,6 +1218,9 @@ public class MovingListener extends CheckListener implements TickListener, IRemo
} }
} }
// Cleanup.
useLoc.setWorld(null);
} }
@Override @Override
@ -1248,7 +1277,8 @@ public class MovingListener extends CheckListener implements TickListener, IRemo
final MovingData data = MovingData.getData(player); final MovingData data = MovingData.getData(player);
data.removeAllVelocity(); data.removeAllVelocity();
// Event should have a vehicle, in case check this last. // Event should have a vehicle, in case check this last.
data.vehicleConsistency = MoveConsistency.getConsistency(event.getVehicle().getLocation(), null, player.getLocation()); data.vehicleConsistency = MoveConsistency.getConsistency(event.getVehicle().getLocation(), null, player.getLocation(useLoc));
useLoc.setWorld(null); // TODO: A pool ?
// TODO: more resetting, visible check ? // TODO: more resetting, visible check ?
} }
@ -1268,7 +1298,7 @@ public class MovingListener extends CheckListener implements TickListener, IRemo
final MovingConfig cc = MovingConfig.getConfig(player); final MovingConfig cc = MovingConfig.getConfig(player);
// TODO: Loc can be inconsistent, determine which to use ! // TODO: Loc can be inconsistent, determine which to use !
final Location pLoc = player.getLocation(); final Location pLoc = player.getLocation(useLoc);
Location loc = pLoc; // The location to use as set-back. Location loc = pLoc; // The location to use as set-back.
// TODO: Which vehicle to use ? // TODO: Which vehicle to use ?
// final Entity vehicle = player.getVehicle(); // final Entity vehicle = player.getVehicle();
@ -1314,6 +1344,7 @@ public class MovingListener extends CheckListener implements TickListener, IRemo
data.verticalFreedom = 1.2; data.verticalFreedom = 1.2;
data.verticalVelocity = 0.15; data.verticalVelocity = 0.15;
data.verticalVelocityUsed = 0; data.verticalVelocityUsed = 0;
useLoc.setWorld(null);
} }
@EventHandler(priority = EventPriority.MONITOR, ignoreCancelled = true) @EventHandler(priority = EventPriority.MONITOR, ignoreCancelled = true)
@ -1330,7 +1361,16 @@ public class MovingListener extends CheckListener implements TickListener, IRemo
@Override @Override
public void onTick(final int tick, final long timeLast) { public void onTick(final int tick, final long timeLast) {
// Hover checks ! final List<String> rem = new ArrayList<String>(hoverTicks.size()); // Pessimistic.
// Enforcing location check.
for (final String playerName : playersEnforce) {
// TODO: Check location consistency (depending on cc).
}
if (!rem.isEmpty()) {
playersEnforce.removeAll(rem);
}
// Hover check (survivalfly).
rem.clear();
if (tick % hoverTicksStep != 0) { if (tick % hoverTicksStep != 0) {
// Only check every so and so ticks. // Only check every so and so ticks.
return; return;
@ -1338,7 +1378,6 @@ public class MovingListener extends CheckListener implements TickListener, IRemo
final MoveInfo info; final MoveInfo info;
if (parkedInfo.isEmpty()) info = new MoveInfo(mcAccess); if (parkedInfo.isEmpty()) info = new MoveInfo(mcAccess);
else info = parkedInfo.remove(parkedInfo.size() - 1); else info = parkedInfo.remove(parkedInfo.size() - 1);
final List<String> rem = new ArrayList<String>(hoverTicks.size()); // Pessimistic.
for (final String playerName : hoverTicks) { for (final String playerName : hoverTicks) {
// TODO: put players into the set (+- one tick would not matter ?) // TODO: put players into the set (+- one tick would not matter ?)
// TODO: might add an online flag to data ! // TODO: might add an online flag to data !
@ -1379,10 +1418,11 @@ public class MovingListener extends CheckListener implements TickListener, IRemo
rem.add(playerName); rem.add(playerName);
} }
} }
info.cleanup(); // Just in case.
parkedInfo.add(info);
hoverTicks.removeAll(rem); hoverTicks.removeAll(rem);
rem.clear(); rem.clear();
info.cleanup();
parkedInfo.add(info);
useLoc.setWorld(null);
} }
/** /**
@ -1395,7 +1435,7 @@ public class MovingListener extends CheckListener implements TickListener, IRemo
*/ */
private boolean checkHover(final Player player, final MovingData data, final MovingConfig cc, final MoveInfo info) { private boolean checkHover(final Player player, final MovingData data, final MovingConfig cc, final MoveInfo info) {
// Check if player is on ground. // Check if player is on ground.
final Location loc = player.getLocation(); final Location loc = player.getLocation(useLoc); // useLoc.setWorld(null) is done in onTick.
info.set(player, loc, null, cc.yOnGround); info.set(player, loc, null, cc.yOnGround);
final boolean res; final boolean res;
// TODO: Collect flags, more margin ? // TODO: Collect flags, more margin ?

View File

@ -16,6 +16,9 @@ import fr.neatmonster.nocheatplus.utilities.StringUtil;
* A check to see if people cheat by tricking the server to not deal them fall damage. * A check to see if people cheat by tricking the server to not deal them fall damage.
*/ */
public class NoFall extends Check { public class NoFall extends Check {
/** For temporary use: LocUtil.clone before passing deeply, call setWorld(null) after use. */
private final Location useLoc = new Location(null, 0, 0, 0);
/** /**
* Instantiates a new no fall check. * Instantiates a new no fall check.
@ -209,7 +212,8 @@ public class NoFall extends Check {
if (data.noFallFallDistance - fallDistance > 0){ if (data.noFallFallDistance - fallDistance > 0){
// Might use tolerance, might log, might use method (compare: MovingListener.onEntityDamage). // Might use tolerance, might log, might use method (compare: MovingListener.onEntityDamage).
// Might consider triggering violations here as well. // Might consider triggering violations here as well.
final float yDiff = (float) (data.noFallMaxY - player.getLocation().getY()); final float yDiff = (float) (data.noFallMaxY - player.getLocation(useLoc).getY());
useLoc.setWorld(null);
final float maxDist = Math.max(yDiff, Math.max(data.noFallFallDistance, fallDistance)); final float maxDist = Math.max(yDiff, Math.max(data.noFallFallDistance, fallDistance));
player.setFallDistance(maxDist); player.setFallDistance(maxDist);
} }

View File

@ -65,6 +65,9 @@ public class SurvivalFly extends Check {
private final Set<String> reallySneaking = new HashSet<String>(30); private final Set<String> reallySneaking = new HashSet<String>(30);
/** For temporary use: LocUtil.clone before passing deeply, call setWorld(null) after use. */
private final Location useLoc = new Location(null, 0, 0, 0);
/** /**
* Instantiates a new survival fly check. * Instantiates a new survival fly check.
*/ */
@ -1344,7 +1347,10 @@ public class SurvivalFly extends Check {
} }
if (data.sfCobwebVL < 550) { // Totally random ! if (data.sfCobwebVL < 550) { // Totally random !
// Silently set back. // Silently set back.
if (!data.hasSetBack()) data.setSetBack(player.getLocation()); // ? check moment of call. if (!data.hasSetBack()) {
data.setSetBack(player.getLocation(useLoc)); // ? check moment of call.
useLoc.setWorld(null);
}
data.sfJumpPhase = 0; data.sfJumpPhase = 0;
data.sfLastYDist = data.sfLastHDist = Double.MAX_VALUE; data.sfLastYDist = data.sfLastHDist = Double.MAX_VALUE;
return true; return true;

View File

@ -19,6 +19,8 @@ import fr.neatmonster.nocheatplus.utilities.build.BuildParameters;
*/ */
public class DebugUtil { public class DebugUtil {
// TODO: Add useLoc1 and useLoc2.
public static boolean isSamePos(final double x1, final double y1, final double z1, final double x2, final double y2, final double z2){ public static boolean isSamePos(final double x1, final double y1, final double z1, final double x2, final double y2, final double z2){
return x1 == x2 && y1 == y2 && z1 == z2; return x1 == x2 && y1 == y2 && z1 == z2;
} }

View File

@ -355,6 +355,8 @@ public class BlockProperties {
*/ */
private static final Map<String, Long> nameFlagMap = new LinkedHashMap<String, Long>(); private static final Map<String, Long> nameFlagMap = new LinkedHashMap<String, Long>();
private static final Location useLoc = new Location(null, 0, 0, 0);
static{ static{
// Use reflection to get a flag -> name mapping and vice versa. // Use reflection to get a flag -> name mapping and vice versa.
for (Field field : BlockProperties.class.getDeclaredFields()){ for (Field field : BlockProperties.class.getDeclaredFields()){
@ -880,7 +882,9 @@ public class BlockProperties {
* @return * @return
*/ */
public static long getBreakingDuration(final int blockId, final Player player){ public static long getBreakingDuration(final int blockId, final Player player){
return getBreakingDuration(blockId, player.getItemInHand(), player.getInventory().getHelmet(), player, player.getLocation()); final long res = getBreakingDuration(blockId, player.getItemInHand(), player.getInventory().getHelmet(), player, player.getLocation(useLoc));
useLoc.setWorld(null);
return res;
} }
/** /**

View File

@ -6,6 +6,9 @@ import org.bukkit.entity.Player;
import org.bukkit.event.player.PlayerTeleportEvent.TeleportCause; import org.bukkit.event.player.PlayerTeleportEvent.TeleportCause;
public class TeleportUtil { public class TeleportUtil {
/** Temp use. LocUtil.clone on passing. setWorld(null) after use. */
private static final Location useLoc = new Location(null, 0, 0, 0);
/** /**
* Teleport the player with vehicle, temporarily eject the passenger and set teleported in MovingData. * Teleport the player with vehicle, temporarily eject the passenger and set teleported in MovingData.
@ -29,13 +32,14 @@ public class TeleportUtil {
} }
else vehicleTeleported = false; else vehicleTeleported = false;
final boolean playerTeleported = player.teleport(location); final boolean playerTeleported = player.teleport(location);
if (playerIsPassenger && playerTeleported && vehicleTeleported && player.getLocation().distance(vehicle.getLocation()) < 1.0){ if (playerIsPassenger && playerTeleported && vehicleTeleported && player.getLocation().distance(vehicle.getLocation(useLoc)) < 1.0){
// Somewhat check against tp showing something wrong (< 1.0). // Somewhat check against tp showing something wrong (< 1.0).
vehicle.setPassenger(player); vehicle.setPassenger(player);
} }
if (debug){ if (debug){
System.out.println(player.getName() + " vehicle set back: " + location); System.out.println(player.getName() + " vehicle set back: " + location);
} }
useLoc.setWorld(null);
} }
/** /**

View File

@ -20,6 +20,8 @@ public class TrigUtil {
public static final double fRadToGrad = 360.0 / (2.0 * Math.PI); public static final double fRadToGrad = 360.0 / (2.0 * Math.PI);
/** Some default precision value for the directionCheck method. */ /** Some default precision value for the directionCheck method. */
public static final double DIRECTION_PRECISION = 2.6; public static final double DIRECTION_PRECISION = 2.6;
private static final Location useLoc = new Location(null, 0, 0, 0);
/** /**
* Check if a player looks at a target of a specific size, with a specific * Check if a player looks at a target of a specific size, with a specific
@ -43,9 +45,11 @@ public class TrigUtil {
*/ */
public static double directionCheck(final Player player, final double targetX, final double targetY, final double targetZ, final double targetWidth, final double targetHeight, final double precision) public static double directionCheck(final Player player, final double targetX, final double targetY, final double targetZ, final double targetWidth, final double targetHeight, final double precision)
{ {
final Location loc = player.getLocation(); final Location loc = player.getLocation(useLoc);
final Vector dir = loc.getDirection(); final Vector dir = loc.getDirection();
return directionCheck(loc.getX(), loc.getY() + player.getEyeHeight(), loc.getZ(), dir.getX(), dir.getY(), dir.getZ(), targetX, targetY, targetZ, targetWidth, targetHeight, precision); final double res = directionCheck(loc.getX(), loc.getY() + player.getEyeHeight(), loc.getZ(), dir.getX(), dir.getY(), dir.getZ(), targetX, targetY, targetZ, targetWidth, targetHeight, precision);
useLoc.setWorld(null);
return res;
} }
/** /**