Add a workaround case for skipping a vehicle move event. Adjust ids.

* Add a late in-air phase skip once workaround.
* Adjust oddSlope workaround ids to be lower-case and not contain wrpt.
* Add workaround counter for back to surface.
This commit is contained in:
asofold 2016-05-01 13:02:30 +02:00
parent f9d0a1a6ca
commit ab5ca5c9dc
4 changed files with 159 additions and 38 deletions

View File

@ -1,5 +1,10 @@
package fr.neatmonster.nocheatplus.checks.moving.magic;
import fr.neatmonster.nocheatplus.checks.moving.MovingData;
import fr.neatmonster.nocheatplus.checks.moving.model.VehicleMoveData;
import fr.neatmonster.nocheatplus.checks.workaround.WRPT;
import fr.neatmonster.nocheatplus.utilities.RichEntityLocation;
/**
* Magic for vehicles.
*
@ -40,6 +45,78 @@ public class MagicVehicle {
public static final double boatGravityMax = Magic.GRAVITY_MAX + Magic.GRAVITY_SPAN;
/** The speed up to which gravity mechanics roughly work. */
public static final double boatVerticalFallTarget = 3.7;
public static final double boatMaxBackToSurfaceAscend = 1.5;
public static final double boatMaxBackToSurfaceAscend = 3.25;
/**
*
* @param thisMove
* @param minDescend Case-sensitive.
* @param maxDescend Case-sensitive.
* @param data
* @return
*/
public static boolean oddInAir(final VehicleMoveData thisMove, final double minDescend, final double maxDescend, final MovingData data) {
// TODO: Guard by past move tracking, instead of minDescend and maxDescend.
// (Try individual if this time, let JIT do the rest.)
if (thisMove.vDistance < 0 && oddInAirDescend(thisMove, minDescend, maxDescend, data)) {
return true;
}
return false;
}
/**
*
* @param thisMove
* @param minDescend Case-sensitive.
* @param maxDescend Case-sensitive.
* @param data
* @return
*/
private static boolean oddInAirDescend(final VehicleMoveData thisMove, final double minDescend, final double maxDescend, final MovingData data) {
// TODO: Guard by past move tracking, instead of minDescend and maxDescend.
// (Try individual if this time, let JIT do the rest.)
if (thisMove.vDistance < 2.0 * minDescend && thisMove.vDistance > 2.0 * maxDescend
// TODO: Past move tracking.
// TODO: Fall distances?
&& data.ws.use(WRPT.W_M_V_ENV_INAIR_SKIP)
) {
return true;
}
return false;
}
/**
* In-water (water-water) cases.
* @param thisMove
* @return
*/
public static boolean oddInWater(final RichEntityLocation from, final RichEntityLocation to,
final VehicleMoveData thisMove, final MovingData data) {
if (thisMove.vDistance > 0.0) {
if (oddInWaterAscend(from, to, thisMove, data)) {
return true;
}
}
return false;
}
/**
* Ascending in-water (water-water).
* @param thisMove
* @return
*/
private static boolean oddInWaterAscend(final RichEntityLocation from, final RichEntityLocation to,
final VehicleMoveData thisMove, final MovingData data) {
// (Try individual if this time, let JIT do the rest.)
if (thisMove.vDistance > MagicVehicle.maxAscend && thisMove.vDistance < MagicVehicle.boatMaxBackToSurfaceAscend
&& data.ws.use(WRPT.W_M_V_ENV_INWATER_BTS)) {
// (Assume players can't control sinking boats for now.)
// TODO: Limit by more side conditions (e.g. to is on the surface and in-medium count is about 1, past moves).
// TODO: Checking for surface can be complicated. Might check blocks at location and above and accept if any is not liquid.
// (Always smaller than previous descending move, roughly to below 0.5 above water.)
return true;
}
return false;
}
}

View File

@ -25,6 +25,7 @@ import fr.neatmonster.nocheatplus.checks.moving.MovingData;
import fr.neatmonster.nocheatplus.checks.moving.location.setback.SetBackEntry;
import fr.neatmonster.nocheatplus.checks.moving.magic.MagicVehicle;
import fr.neatmonster.nocheatplus.checks.moving.model.VehicleMoveData;
import fr.neatmonster.nocheatplus.checks.workaround.WRPT;
import fr.neatmonster.nocheatplus.logging.Streams;
import fr.neatmonster.nocheatplus.utilities.BlockCache;
import fr.neatmonster.nocheatplus.utilities.CheckUtils;
@ -63,6 +64,7 @@ public class VehicleEnvelope extends Check {
tags.add("entity." + vehicle.getType());
if (data.debug) {
debugDetails.clear();
data.ws.setJustUsedIds(debugDetails); // Add just used workaround ids to this list directly, for now.
}
final boolean violation;
if (vehicle instanceof LivingEntity) {
@ -74,6 +76,7 @@ public class VehicleEnvelope extends Check {
}
if (data.debug && !debugDetails.isEmpty()) {
debugDetails(player);
debugDetails.clear();
}
if (violation) {
// Add up one for now.
@ -198,18 +201,16 @@ public class VehicleEnvelope extends Check {
if (maxDistHorizontal(thisMove, MagicVehicle.boatMaxDistanceHorizontal)) {
return true;
}
// Maximum descend speed.
if (thisMove.vDistance < -MagicVehicle.maxDescend) {
// TODO: At times it looks like one move is skipped, resulting in double distance ~ -5 and at the same time 'vehicle moved too quickly'.
// TODO: Test with log this to console to see the order of things.
tags.add("descend_much");
return true;
}
// TODO: Could limit descend by 2*maxDescend, ascend by much less.
// Medium dependent checking.
boolean violation = false;
boolean checkAscendMuch = true;
boolean checkDescendMuch = true;
// (Assume boats can't climb.)
final boolean fromIsSafeMedium = from.isInWater() || from.isOnGround() || from.isInWeb();
final boolean toIsSafeMedium = to.isInWater() || to.isOnGround() || to.isInWeb();
final boolean inAir = !fromIsSafeMedium && !toIsSafeMedium;
// TODO: Split code to methods.
if (from.isInWeb()) {
// TODO: Check anything?
if (data.debug) {
@ -228,12 +229,13 @@ public class VehicleEnvelope extends Check {
// TODO: Should still cover extreme moves here.
// Special case moving up after falling.
// TODO: Move to MagicVehicle.oddInWater
// TODO: Check past moves for falling (not yet available).
// TODO: Check if the target location somehow is the surface.
if (thisMove.vDistance > MagicVehicle.maxAscend && thisMove.vDistance < MagicVehicle.boatMaxBackToSurfaceAscend) {
if (MagicVehicle.oddInWater(from, to, thisMove, data)) {
// (Assume players can't control sinking boats for now.)
checkAscendMuch = false;
tags.add("back_to_surface");
checkDescendMuch = checkAscendMuch = false;
violation = false;
}
}
else if (from.isOnGround() && to.isOnGround()) {
@ -253,7 +255,7 @@ public class VehicleEnvelope extends Check {
}
}
}
else if (!fromIsSafeMedium && !toIsSafeMedium) {
else if (inAir) {
// In-air move.
// TODO: Common in-air accounting check with parameters.
if (data.debug) {
@ -263,11 +265,11 @@ public class VehicleEnvelope extends Check {
tags.add("ascend_at_all");
return true;
}
// TODO: Workaround: 60+ in-air phase for 2* lastyDist > yDist > 2 * (lastyDist + MagicVehicle.boatGravityMax). Possibly once per in-air phase.
// Absolute vertical distance to set back.
// TODO: Add something like this.
// final double setBackYdistance = to.getY() - data.vehicleSetBacks.getValidSafeMediumEntry().getY();
// if (data.sfJumpPhase > 4) {
// TODO: Realistic cap.
// double estimate = Math.min(2.0, MagicVehicle.boatGravityMin * ((double) data.sfJumpPhase / 4.0) * ((double) data.sfJumpPhase / 4.0 + 1.0) / 2.0);
// if (setBackYdistance > -estimate) {
// tags.add("slow_fall_vdistsb");
@ -275,15 +277,24 @@ public class VehicleEnvelope extends Check {
// }
// }
// Slow falling (vdist).
final double minDescend = -MagicVehicle.boatGravityMin * data.sfJumpPhase;
final double maxDescend = -MagicVehicle.boatGravityMax * data.sfJumpPhase - 0.5;
if (data.sfJumpPhase > 1 && thisMove.vDistance > -MagicVehicle.boatVerticalFallTarget
&& thisMove.vDistance > - MagicVehicle.boatGravityMin * data.sfJumpPhase) {
&& thisMove.vDistance > minDescend) {
tags.add("slow_fall_vdist");
return true;
violation = true;
}
// Fast falling (vdist).
if (data.sfJumpPhase > 1 && thisMove.vDistance < -MagicVehicle.boatGravityMax * data.sfJumpPhase - 0.5) {
else if (data.sfJumpPhase > 1 && thisMove.vDistance < maxDescend) {
tags.add("fast_fall_vdist");
return true;
violation = true;
}
if (violation) {
// Post violation detection workarounds.
if (MagicVehicle.oddInAir(thisMove, minDescend, maxDescend, data)) {
violation = false;
checkDescendMuch = checkAscendMuch = false; // (Full envelope has been checked.)
}
}
}
else {
@ -299,24 +310,41 @@ public class VehicleEnvelope extends Check {
// Maximum ascend speed.
if (checkAscendMuch && thisMove.vDistance > MagicVehicle.maxAscend) {
tags.add("ascend_much");
return true;
violation = true;
}
// Maximum descend speed.
if (checkDescendMuch && thisMove.vDistance < -MagicVehicle.maxDescend) {
// TODO: At times it looks like one move is skipped, resulting in double distance ~ -5 and at the same time 'vehicle moved too quickly'.
// TODO: Test with log this to console to see the order of things.
tags.add("descend_much");
violation = true;
}
// No violation.
// TODO: sfJumpPhase is abused for in-air move counting here.
if (toIsSafeMedium) {
data.vehicleSetBacks.setSafeMediumEntry(to);
data.sfJumpPhase = 0;
if (!violation) {
// No violation.
// TODO: sfJumpPhase is abused for in-air move counting here.
if (inAir) {
data.sfJumpPhase ++;
}
else {
// Adjust set-back.
if (toIsSafeMedium) {
data.vehicleSetBacks.setSafeMediumEntry(to);
data.sfJumpPhase = 0;
}
else if (fromIsSafeMedium) {
data.vehicleSetBacks.setSafeMediumEntry(from);
data.sfJumpPhase = 0;
}
// Reset the resetNotInAir workarounds.
data.ws.resetConditions(WRPT.G_RESET_NOTINAIR);
}
data.vehicleSetBacks.setLastMoveEntry(to);
// TODO: Workaround - reset moving set-backs.
}
else if (fromIsSafeMedium) {
data.vehicleSetBacks.setSafeMediumEntry(from);
data.sfJumpPhase = 0;
}
else {
data.sfJumpPhase ++;
}
data.vehicleSetBacks.setLastMoveEntry(to);
return false;
return violation;
}
private boolean checkMinecart(final Player player, final Entity vehicle,

View File

@ -35,8 +35,8 @@ public class WRPT extends SimpleWorkaroundRegistry {
public static final String W_M_SF_WEB_MICROGRAVITY2 = "m.sf.web.microgravity2";
// oddSlope
public static final String W_M_SF_SLOPE1 = "m.sf.WRPT.SLOPE1";
public static final String W_M_SF_SLOPE2 = "m.sf.WRPT.SLOPE2";
public static final String W_M_SF_SLOPE1 = "m.sf.slope1";
public static final String W_M_SF_SLOPE2 = "m.sf.slope2";
// TODO: oddLiquid
@ -46,12 +46,24 @@ public class WRPT extends SimpleWorkaroundRegistry {
// (TODO: oddElytra)
// Vehicle: oddInAirDescend
/**
* Vehicle descending in-air, skip one vehicle move event during late in-air
* phase.
*/
public static final String W_M_V_ENV_INAIR_SKIP = "m.v.env.inair.skip";
/** Just a counter for back to surface for in-water moves (water-water). */
public static final String W_M_V_ENV_INWATER_BTS = "m.v.env.inwater.bts";
///////////////////////
// Group ids.
///////////////////////
// MOVING_SURVIVALFLY
/** Group: Reset when not in air jump phase. */
/**
* Group: Reset when not in air jump phase. Both used for players and
* vehicles with players inside.
*/
public static final String G_RESET_NOTINAIR = "reset.notinair";
///////////////////////
@ -73,6 +85,7 @@ public class WRPT extends SimpleWorkaroundRegistry {
// Reset once on ground or reset-condition.
final WorkaroundCountDown[] resetNotInAir = new WorkaroundCountDown[] {
new WorkaroundCountDown(W_M_SF_SLIME_JP_2X0, 1),
new WorkaroundCountDown(W_M_V_ENV_INAIR_SKIP, 1),
};
ws_moving.addAll(Arrays.asList(resetNotInAir));
setWorkaroundBluePrint(resetNotInAir);
@ -80,13 +93,15 @@ public class WRPT extends SimpleWorkaroundRegistry {
// Just counters.
final String[] counters = new String[] {
// Player
W_M_SF_WEB_0V1,
W_M_SF_WEB_0V2,
W_M_SF_WEB_MICROGRAVITY1,
W_M_SF_WEB_MICROGRAVITY2,
W_M_SF_SLOPE1,
W_M_SF_SLOPE2,
// TODO: ALL workaorunds.
// Vehicle
W_M_V_ENV_INWATER_BTS
};
for (final String id : counters) {
final WorkaroundCounter counter = new WorkaroundCounter(id);

View File

@ -53,7 +53,7 @@ public class TeleportUtil {
vehicle.eject();
// TODO: Confirm eject worked, handle if not.
vehicleTeleported = vehicle.teleport(LocUtil.clone(location), TeleportCause.PLUGIN);
vehicle.setVelocity(new Vector(0.0, 0.0, 0.0)); // TODO: Does not solve 1.9.2 rubber band issue.
vehicle.setVelocity(new Vector(0.0, 0.0, 0.0)); // TODO: Likely not relevant, should remove.
}
}
else if (passenger == null) {
@ -65,7 +65,8 @@ public class TeleportUtil {
data.prepareSetBack(location);
playerTeleported = player.teleport(LocUtil.clone(location));
data.resetTeleported(); // Just in case.
player.setVelocity(new Vector(0.0, 0.0, 0.0)); // TODO: Does not solve 1.9.2 rubber band issue.
// TODO: Consider resetting player set-backs.
player.setVelocity(new Vector(0.0, 0.0, 0.0)); // TODO: Likely not relevant, should remove.
// TODO: Magic 1.0, plus is this valid with horse, dragon...
if (playerIsPassenger && playerTeleported && vehicleTeleported && player.getLocation().distance(vehicle.getLocation(useLoc)) < 1.0) {
// Somewhat check against tp showing something wrong (< 1.0).