mirror of
https://github.com/NoCheatPlus/NoCheatPlus.git
synced 2025-03-09 13:09:09 +01:00
Keep adjusting time and offsets in raytracing.
* Not actually a fix for anything we encountered. * Nailed down blockinteract.visible raytracing issues to bad end-points for raytracing. * Also test/prepare logging test-cases for raytracing in general. Not enabled, because we should have some flag/permission/command to check before logging ~ 5KB per interact event.
This commit is contained in:
parent
ab88b98704
commit
14049200a2
@ -140,7 +140,7 @@ public class Visible extends Check {
|
||||
tMinZ > tMaxX && tMaxZ > tMaxY) {
|
||||
// TODO: Option to tolerate a minimal difference in t and use a corrected position then.
|
||||
tags.add("block_miss");
|
||||
// Bukkit.getServer().broadcastMessage("visible: " + tMinX + "," + tMaxX + " | " + tMinY + "," + tMaxY + " | " + tMinZ + "," + tMaxZ);
|
||||
// Bukkit.getServer().broadcastMessage("visible: " + tMinX + "," + tMaxX + " | " + tMinY + "," + tMaxY + " | " + tMinZ + "," + tMaxZ);
|
||||
return true;
|
||||
}
|
||||
|
||||
@ -170,7 +170,7 @@ public class Visible extends Check {
|
||||
// Perform ray-tracing.
|
||||
rayTracing.set(eyeX, eyeY, eyeZ, collideX, collideY, collideZ, blockX, blockY, blockZ);
|
||||
rayTracing.loop();
|
||||
|
||||
|
||||
final boolean collides;
|
||||
if (rayTracing.collides()) {
|
||||
tags.add("raytracing");
|
||||
@ -188,7 +188,8 @@ public class Visible extends Check {
|
||||
* Consider using a configuration setting for extended debugging
|
||||
* (e.g. make DEBUG_LEVEL accessible by API and config).
|
||||
*/
|
||||
// TODO: public static void InteractRayTracing.logTestCase(...).
|
||||
// TEST: Log as a false positive (!).
|
||||
//NCPAPIProvider.getNoCheatPlusAPI().getLogManager().debug(Streams.TRACE_FILE, "blockinteract.visible test case:\n" + rayTracing.getTestCase(1.05, false));
|
||||
}
|
||||
return collides;
|
||||
}
|
||||
@ -233,7 +234,7 @@ public class Visible extends Check {
|
||||
// Just the time within range.
|
||||
return tMin + 1.0 / Math.abs(dir);
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* Correct the coordinate to be on the block (only if outside, for
|
||||
* correcting inside-block to edge tMin has to be checked.
|
||||
|
@ -2,6 +2,7 @@ package fr.neatmonster.nocheatplus.utilities;
|
||||
|
||||
import java.util.Iterator;
|
||||
|
||||
import org.bukkit.Location;
|
||||
import org.bukkit.Material;
|
||||
import org.bukkit.World;
|
||||
import org.bukkit.entity.Entity;
|
||||
@ -26,6 +27,42 @@ public class FakeBlockCache extends BlockCache {
|
||||
/** Cached shape values. */
|
||||
private final CoordMap<double[]> boundsMapStored = new CoordMap<double[]>(23);
|
||||
|
||||
/**
|
||||
* Convenience method to copy a cuboid region given by two endpoints without any order specified.
|
||||
* @param other
|
||||
* @param x0
|
||||
* @param y0
|
||||
* @param z0
|
||||
* @param x1
|
||||
* @param y1
|
||||
* @param z1
|
||||
* @param margin
|
||||
*/
|
||||
public void set(BlockCache other, double x0, double y0, double z0, double x1, double y1, double z1, double margin) {
|
||||
set(other, Location.locToBlock(Math.min(x0, x1) - margin), Location.locToBlock(Math.min(y0, y1) - margin), Location.locToBlock(Math.min(z0, z1) - margin),
|
||||
Location.locToBlock(Math.max(x0, x1) + margin), Location.locToBlock(Math.max(y0, y1) + margin), Location.locToBlock(Math.max(z0, z1) + margin));
|
||||
}
|
||||
|
||||
/**
|
||||
* Copy a cuboid region from the other BlockCache instance.
|
||||
* @param other
|
||||
* @param minX
|
||||
* @param minY
|
||||
* @param minZ
|
||||
* @param maxX
|
||||
* @param maxY
|
||||
* @param maxZ
|
||||
*/
|
||||
public void set(BlockCache other, int minX, int minY, int minZ, int maxX, int maxY, int maxZ) {
|
||||
for (int x = minX; x <= maxX; x++) {
|
||||
for (int y = minY; y <= maxY; y ++) {
|
||||
for (int z = minZ; z <= maxZ; z ++) {
|
||||
set(x, y, z, other.getTypeId(x, y, z), other.getData(x, y, z), other.getBounds(x, y, z));
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Set with data=0 and bounds=full.
|
||||
* @param x
|
||||
@ -79,7 +116,7 @@ public class FakeBlockCache extends BlockCache {
|
||||
* @param z
|
||||
* @param typeId
|
||||
* @param data
|
||||
* @param bounds
|
||||
* @param bounds Stores the given bounds directly.
|
||||
*/
|
||||
public void set(int x, int y, int z, int typeId, int data, double[] bounds) {
|
||||
idMapStored.put(x, y, z, typeId);
|
||||
@ -219,9 +256,17 @@ public class FakeBlockCache extends BlockCache {
|
||||
* Return a line of java code to construct a new FakeBlockCache with the same content (no newlines).
|
||||
* @param builder
|
||||
* @param fbcName Variable name of the FakeBlockCache instance.
|
||||
* @param boundsPrefix A prefix for bounds variables for the case of repeated content. If set to null, no optimization will be performed.
|
||||
*/
|
||||
public void toJava(final StringBuilder builder, final String fbcName) {
|
||||
public void toJava(final StringBuilder builder, final String fbcName, final String boundsPrefix) {
|
||||
builder.append("FakeBlockCache " + fbcName + " = new FakeBlockCache();");
|
||||
final String fullBounds;
|
||||
if (boundsPrefix != null) {
|
||||
fullBounds = boundsPrefix + "_fb";
|
||||
builder.append(" double[] " + fullBounds + " = new double[]{0.0, 0.0, 0.0, 1.0, 1.0, 1.0};" );
|
||||
} else {
|
||||
fullBounds = null;
|
||||
}
|
||||
// Assume id is always set.
|
||||
final Iterator<Entry<Integer>> it = idMapStored.iterator();
|
||||
final int airId = BlockProperties.getId(Material.AIR);
|
||||
@ -233,16 +278,22 @@ public class FakeBlockCache extends BlockCache {
|
||||
final Integer id = entry.getValue();
|
||||
if (id == airId) {
|
||||
builder.append(fbcName + ".set(" + x + ", " + y + ", " + z + ", " + id + ");");
|
||||
} else {
|
||||
}
|
||||
else {
|
||||
final Integer data = dataMapStored.get(x, y, z);
|
||||
final double[] bounds = boundsMapStored.get(x, y, z);
|
||||
if (bounds == null) {
|
||||
if (data == null) { // Consider 0 too.
|
||||
builder.append(fbcName + ".set(" + x + ", " + y + ", " + z + ", " + id + ");");
|
||||
} else {
|
||||
}
|
||||
else {
|
||||
builder.append(fbcName + ".set(" + x + ", " + y + ", " + z + ", " + id + ", " + data + ");");
|
||||
}
|
||||
} else {
|
||||
}
|
||||
else if (boundsPrefix != null && BlockCache.isFullBounds(bounds)) {
|
||||
builder.append(fbcName + ".set(" + x + ", " + y + ", " + z + ", " + id + ", " + data + ", " + fullBounds + ");");;
|
||||
}
|
||||
else {
|
||||
builder.append(fbcName + ".set(" + x + ", " + y + ", " + z + ", " + id + ", " + data + ", ");
|
||||
DebugUtil.toJava(bounds, builder);
|
||||
builder.append(");");
|
||||
|
@ -11,32 +11,33 @@ import org.bukkit.Location;
|
||||
*/
|
||||
public class InteractRayTracing extends RayTracing {
|
||||
|
||||
// private static final int[][] incr = new int[][]{
|
||||
// {1, 0, 0},
|
||||
// {0, 1, 0},
|
||||
// {0, 0, 1},
|
||||
// {-1, 0, 0},
|
||||
// {0, -1, 0},
|
||||
// {0, 0, -1},
|
||||
// };
|
||||
// private static final int[][] incr = new int[][]{
|
||||
// {1, 0, 0},
|
||||
// {0, 1, 0},
|
||||
// {0, 0, 1},
|
||||
// {-1, 0, 0},
|
||||
// {0, -1, 0},
|
||||
// {0, 0, -1},
|
||||
// };
|
||||
|
||||
protected BlockCache blockCache = null;
|
||||
|
||||
protected boolean collides = false;
|
||||
|
||||
protected boolean strict = false;
|
||||
protected final boolean strict;
|
||||
|
||||
protected int lastBx, lastBy, lastBz;
|
||||
|
||||
protected int targetX, targetY, targetZ;
|
||||
|
||||
public InteractRayTracing() {
|
||||
super();
|
||||
this(false);
|
||||
}
|
||||
|
||||
public InteractRayTracing(boolean strict) {
|
||||
super();
|
||||
this.strict = strict;
|
||||
this.forceStepEndPos = false; // Not needed here.
|
||||
}
|
||||
|
||||
public BlockCache getBlockCache() {
|
||||
@ -123,53 +124,53 @@ public class InteractRayTracing extends RayTracing {
|
||||
return targetX != Integer.MAX_VALUE && blockX == targetX && blockY == targetY && blockZ == targetZ;
|
||||
}
|
||||
|
||||
// /**
|
||||
// * Check if the block may be interacted through by use of some workaround.
|
||||
// *
|
||||
// * @param blockX
|
||||
// * @param blockY
|
||||
// * @param blockZ
|
||||
// * @return
|
||||
// */
|
||||
// private final boolean allowsWorkaround(final int blockX, final int blockY, final int blockZ) {
|
||||
//
|
||||
// // TODO: Recode this/other.
|
||||
//
|
||||
// // TODO: This could allow some bypasses for "strange" setups.
|
||||
// // TODO: Consider using distance to target as heuristic ? [should not get smaller !?]
|
||||
// // TODO: Consider (min/max) offset for distance.
|
||||
// final int dX = blockX - lastBx;
|
||||
// final int dY = blockY - lastBy;
|
||||
// final int dZ = blockZ - lastBz;
|
||||
// final double dSq = dX * dX + dY * dY + dZ * dZ;
|
||||
// // TODO: Limit distance more here !?
|
||||
// for (int i = 0; i < 6; i++) {
|
||||
// final int[] dir = incr[i];
|
||||
// final int rX = blockX + dir[0];
|
||||
// if (Math.abs(lastBx - rX) > 1) {
|
||||
// continue;
|
||||
// }
|
||||
// final int rY = blockY + dir[1];
|
||||
// if (Math.abs(lastBy - rY) > 1) {
|
||||
// continue;
|
||||
// }
|
||||
// final int rZ = blockZ + dir[2];
|
||||
// if (Math.abs(lastBz - rZ) > 1) {
|
||||
// continue;
|
||||
// }
|
||||
// final int dRx = rX - lastBx;
|
||||
// final int dRy = rY - lastBy;
|
||||
// final int dRz = rZ - lastBz;
|
||||
// if (dRx * dRx + dRy * dRy + dRz * dRz <= dSq) {
|
||||
// continue;
|
||||
// }
|
||||
// if (!doesCollide(rX, rY, rZ)) {
|
||||
// // NOTE: Don't check "rX == targetBx && rZ == targetBz && rY == targetBy".
|
||||
// return true;
|
||||
// }
|
||||
// }
|
||||
// return false;
|
||||
// }
|
||||
// /**
|
||||
// * Check if the block may be interacted through by use of some workaround.
|
||||
// *
|
||||
// * @param blockX
|
||||
// * @param blockY
|
||||
// * @param blockZ
|
||||
// * @return
|
||||
// */
|
||||
// private final boolean allowsWorkaround(final int blockX, final int blockY, final int blockZ) {
|
||||
//
|
||||
// // TODO: Recode this/other.
|
||||
//
|
||||
// // TODO: This could allow some bypasses for "strange" setups.
|
||||
// // TODO: Consider using distance to target as heuristic ? [should not get smaller !?]
|
||||
// // TODO: Consider (min/max) offset for distance.
|
||||
// final int dX = blockX - lastBx;
|
||||
// final int dY = blockY - lastBy;
|
||||
// final int dZ = blockZ - lastBz;
|
||||
// final double dSq = dX * dX + dY * dY + dZ * dZ;
|
||||
// // TODO: Limit distance more here !?
|
||||
// for (int i = 0; i < 6; i++) {
|
||||
// final int[] dir = incr[i];
|
||||
// final int rX = blockX + dir[0];
|
||||
// if (Math.abs(lastBx - rX) > 1) {
|
||||
// continue;
|
||||
// }
|
||||
// final int rY = blockY + dir[1];
|
||||
// if (Math.abs(lastBy - rY) > 1) {
|
||||
// continue;
|
||||
// }
|
||||
// final int rZ = blockZ + dir[2];
|
||||
// if (Math.abs(lastBz - rZ) > 1) {
|
||||
// continue;
|
||||
// }
|
||||
// final int dRx = rX - lastBx;
|
||||
// final int dRy = rY - lastBy;
|
||||
// final int dRz = rZ - lastBz;
|
||||
// if (dRx * dRx + dRy * dRy + dRz * dRz <= dSq) {
|
||||
// continue;
|
||||
// }
|
||||
// if (!doesCollide(rX, rY, rZ)) {
|
||||
// // NOTE: Don't check "rX == targetBx && rZ == targetBz && rY == targetBy".
|
||||
// return true;
|
||||
// }
|
||||
// }
|
||||
// return false;
|
||||
// }
|
||||
|
||||
@Override
|
||||
protected boolean step(final int blockX, final int blockY, final int blockZ, final double oX, final double oY, final double oZ, final double dT, final boolean isPrimary) {
|
||||
@ -184,20 +185,43 @@ public class InteractRayTracing extends RayTracing {
|
||||
}
|
||||
return true;
|
||||
}
|
||||
// if (strict || blockX == lastBx && blockZ == lastBz && blockY == lastBy) {
|
||||
// collides = true;
|
||||
// return false;
|
||||
// }
|
||||
// // Check workarounds...
|
||||
// if (isPrimary && allowsWorkaround(blockX, blockY, blockZ)) {
|
||||
// lastBx = blockX;
|
||||
// lastBy = blockY;
|
||||
// lastBz = blockZ;
|
||||
// return true;
|
||||
// }
|
||||
// if (strict || blockX == lastBx && blockZ == lastBz && blockY == lastBy) {
|
||||
// collides = true;
|
||||
// return false;
|
||||
// }
|
||||
// // Check workarounds...
|
||||
// if (isPrimary && allowsWorkaround(blockX, blockY, blockZ)) {
|
||||
// lastBx = blockX;
|
||||
// lastBy = blockY;
|
||||
// lastBz = blockZ;
|
||||
// return true;
|
||||
// }
|
||||
// No workaround found.
|
||||
collides = true;
|
||||
return false;
|
||||
}
|
||||
|
||||
/**
|
||||
* Get a directly usable test case (in a closure), for copy and paste to TestInteractRayTracing.
|
||||
* @param captureMargin
|
||||
* @param expectCollide
|
||||
* @return
|
||||
*/
|
||||
public String getTestCase(double captureMargin, boolean expectCollide) {
|
||||
FakeBlockCache recorder = new FakeBlockCache();
|
||||
recorder.set(this.blockCache, x0, y0, z0, x0 + dX, y0 + dY, z0 + dZ, captureMargin);
|
||||
StringBuilder builder = new StringBuilder(10000);
|
||||
// Add everything inside a closure for direct copy and paste.
|
||||
builder.append('{');
|
||||
// Set up the block cache.
|
||||
recorder.toJava(builder, "fbc", "");
|
||||
// Add the test case code.
|
||||
builder.append("InteractRayTracing rt = new CenteredInteractRayTracing(false, " + targetX + ", " + targetY + ", " + targetZ + "); rt.setBlockCache(fbc);");
|
||||
builder.append("TestRayTracing.runCoordinates(rt, new double[]{" + x0 + ", " + y0 + ", " + z0 + ", " + (x0 + dX) + ", " + (y0 + dY) + ", " + (z0 + dZ) + "}, " + expectCollide + ", " + !expectCollide + ", 0.0, false, \"ingame\");");
|
||||
builder.append("rt.cleanup(); fbc.cleanup();");
|
||||
builder.append('}');
|
||||
recorder.cleanup();
|
||||
return builder.toString();
|
||||
}
|
||||
|
||||
}
|
||||
|
@ -10,7 +10,7 @@ import org.bukkit.Location;
|
||||
public abstract class RayTracing {
|
||||
|
||||
// /** End point coordinates (from, to) */
|
||||
// protected double x0, y0, z0, x1, y1, z1;
|
||||
protected double x0, y0, z0; // x1, y1, z1;
|
||||
|
||||
// /** Total distance between end points. */
|
||||
// protected double d;
|
||||
@ -33,6 +33,9 @@ public abstract class RayTracing {
|
||||
/** Tolerance for time, for checking the abort condition: 1.0 - t <= tol . */
|
||||
protected double tol = 0.0;
|
||||
|
||||
/** Force calling step at the end position, for the case it is reached with block transitions. */
|
||||
protected boolean forceStepEndPos = true;
|
||||
|
||||
/**
|
||||
* Counting the number of steps along the primary line. Step is incremented
|
||||
* before calling step(), and is 0 after set(...). Checking this from within
|
||||
@ -65,9 +68,9 @@ public abstract class RayTracing {
|
||||
* @param z1
|
||||
*/
|
||||
public void set(double x0, double y0, double z0, double x1, double y1, double z1) {
|
||||
// this.x0 = x0;
|
||||
// this.y0 = y0;
|
||||
// this.z0 = z0;
|
||||
this.x0 = x0;
|
||||
this.y0 = y0;
|
||||
this.z0 = z0;
|
||||
// this.x1 = x1;
|
||||
// this.y1 = y1;
|
||||
// this.z1 = z1;
|
||||
@ -136,7 +139,7 @@ public abstract class RayTracing {
|
||||
* "off by x-th digit" or "t=0 transition"). Consider correcting t on
|
||||
* base of the block coordinates in use.
|
||||
*/
|
||||
while (1.0 - t > tol) {
|
||||
while (t + tol < 1.0) {
|
||||
// Determine smallest time to block edge, per axis.
|
||||
tX = tDiff(dX, oX, blockX == endBlockX);
|
||||
tY = tDiff(dY, oY, blockY == endBlockY);
|
||||
@ -167,7 +170,7 @@ public abstract class RayTracing {
|
||||
}
|
||||
|
||||
// Abort if arrived.
|
||||
if (t + tMin >= 1.0 - tol && isEndBlock()) {
|
||||
if (t + tMin + tol >= 1.0 && isEndBlock()) {
|
||||
break;
|
||||
}
|
||||
|
||||
@ -201,10 +204,18 @@ public abstract class RayTracing {
|
||||
if (!handleTransitions(transitions, transX, transY, transZ, tMin)) {
|
||||
break;
|
||||
}
|
||||
// Check conditions for abort/end.
|
||||
if (forceStepEndPos && t + tol >= 1.0) {
|
||||
// Reached the end with transitions, ensure we check the end block.
|
||||
step(blockX, blockY, blockZ, oX, oY, oZ, 0.0, true);
|
||||
break;
|
||||
}
|
||||
} else {
|
||||
// No transitions, finished.
|
||||
break;
|
||||
}
|
||||
|
||||
// Abort if done or exceeded maxSteps.
|
||||
if (transitions == 0 || step >= maxSteps) {
|
||||
// Ensure not to go beyond maxSteps.
|
||||
if (step >= maxSteps) {
|
||||
break;
|
||||
}
|
||||
}
|
||||
@ -228,36 +239,48 @@ public abstract class RayTracing {
|
||||
}
|
||||
|
||||
// Apply all transitions to the primary line.
|
||||
double tcMin = 1.0; // Corrected absolute time to reach the resulting block position.
|
||||
if (transX) {
|
||||
if (dX > 0.0) {
|
||||
blockX ++;
|
||||
oX = 0.0;
|
||||
tcMin = Math.min(tcMin, ((double) blockX - x0) / dX);
|
||||
}
|
||||
else {
|
||||
blockX --;
|
||||
oX = 1.0;
|
||||
tcMin = Math.min(tcMin, (1.0 + (double) blockX - x0) / dX);
|
||||
}
|
||||
}
|
||||
if (transY) {
|
||||
if (dY > 0.0) {
|
||||
blockY ++;
|
||||
oY = 0.0;
|
||||
tcMin = Math.min(tcMin, ((double) blockY - y0) / dY);
|
||||
}
|
||||
else {
|
||||
blockY --;
|
||||
oY = 1.0;
|
||||
tcMin = Math.min(tcMin, (1.0 + (double) blockY - y0) / dY);
|
||||
}
|
||||
}
|
||||
if (transZ) {
|
||||
if (dZ > 0.0) {
|
||||
blockZ ++;
|
||||
oZ = 0.0;
|
||||
tcMin = Math.min(tcMin, ((double) blockZ - z0) / dZ);
|
||||
}
|
||||
else {
|
||||
blockZ --;
|
||||
oZ = 1.0;
|
||||
tcMin = Math.min(tcMin, (1.0 + (double) blockZ - z0) / dZ);
|
||||
}
|
||||
}
|
||||
// Correct time and offsets based on tcMin.
|
||||
oX = x0 + tcMin * dX - (double) blockX;
|
||||
oY = y0 + tcMin * dY - (double) blockY;
|
||||
oZ = z0 + tcMin * dZ - (double) blockZ;
|
||||
t = tcMin;
|
||||
return true; // Continue loop.
|
||||
}
|
||||
|
||||
|
@ -142,4 +142,14 @@ public class TestInteractRayTracing {
|
||||
bc.cleanup();
|
||||
}
|
||||
|
||||
/**
|
||||
* Test cases taken from ingame logging.
|
||||
*/
|
||||
@Test
|
||||
public void testIngame() {
|
||||
// Circle around the corners of 4 blocks with left button pressed down (random sample).
|
||||
// Bad end coords (should fail):
|
||||
{FakeBlockCache fbc = new FakeBlockCache(); double[] _fb = new double[]{0.0, 0.0, 0.0, 1.0, 1.0, 1.0};fbc.set(142, 67, 221, 3, 0, _fb);fbc.set(142, 67, 217, 3, 0, _fb);fbc.set(142, 69, 219, 0);fbc.set(142, 68, 218, 2, 0, _fb);fbc.set(142, 70, 220, 0);fbc.set(142, 71, 217, 0);fbc.set(142, 71, 221, 0);fbc.set(143, 67, 218, 3, 0, _fb);fbc.set(143, 68, 217, 2, 0, _fb);fbc.set(143, 68, 221, 2, 0, _fb);fbc.set(143, 69, 220, 0);fbc.set(143, 70, 219, 0);fbc.set(143, 71, 218, 0);fbc.set(144, 67, 219, 3, 0, _fb);fbc.set(144, 68, 220, 2, 0, _fb);fbc.set(144, 69, 217, 0);fbc.set(144, 69, 221, 31, 1, new double[] {0.09999999403953552, 0.0, 0.09999999403953552, 0.8999999761581421, 0.800000011920929, 0.8999999761581421});fbc.set(144, 70, 218, 0);fbc.set(144, 71, 219, 0);fbc.set(145, 67, 220, 3, 0, _fb);fbc.set(145, 68, 219, 2, 0, _fb);fbc.set(145, 69, 218, 0);fbc.set(145, 70, 217, 0);fbc.set(145, 70, 221, 0);fbc.set(145, 71, 220, 0);fbc.set(142, 68, 217, 2, 0, _fb);fbc.set(142, 68, 221, 2, 0, _fb);fbc.set(142, 67, 218, 3, 0, _fb);fbc.set(142, 69, 220, 0);fbc.set(142, 70, 219, 0);fbc.set(142, 71, 218, 0);fbc.set(143, 67, 217, 3, 0, _fb);fbc.set(143, 67, 221, 3, 0, _fb);fbc.set(143, 68, 218, 49, 0, _fb);fbc.set(143, 69, 219, 0);fbc.set(143, 70, 220, 0);fbc.set(143, 71, 217, 0);fbc.set(143, 71, 221, 0);fbc.set(144, 67, 220, 3, 0, _fb);fbc.set(144, 68, 219, 49, 0, _fb);fbc.set(144, 69, 218, 0);fbc.set(144, 70, 217, 0);fbc.set(144, 70, 221, 0);fbc.set(144, 71, 220, 0);fbc.set(145, 67, 219, 3, 0, _fb);fbc.set(145, 68, 220, 2, 0, _fb);fbc.set(145, 69, 217, 0);fbc.set(145, 69, 221, 50, 5, new double[] {0.4000000059604645, 0.0, 0.4000000059604645, 0.6000000238418579, 0.6000000238418579, 0.6000000238418579});fbc.set(145, 70, 218, 0);fbc.set(145, 71, 219, 0);fbc.set(142, 67, 219, 3, 0, _fb);fbc.set(142, 70, 218, 0);fbc.set(142, 69, 221, 31, 1, new double[] {0.09999999403953552, 0.0, 0.09999999403953552, 0.8999999761581421, 0.800000011920929, 0.8999999761581421});fbc.set(142, 69, 217, 0);fbc.set(142, 68, 220, 2, 0, _fb);fbc.set(142, 71, 219, 0);fbc.set(143, 67, 220, 3, 0, _fb);fbc.set(143, 68, 219, 49, 0, _fb);fbc.set(143, 69, 218, 0);fbc.set(143, 70, 217, 0);fbc.set(143, 70, 221, 0);fbc.set(143, 71, 220, 0);fbc.set(144, 67, 217, 3, 0, _fb);fbc.set(144, 67, 221, 3, 0, _fb);fbc.set(144, 68, 218, 49, 0, _fb);fbc.set(144, 69, 219, 0);fbc.set(144, 70, 220, 0);fbc.set(144, 71, 217, 0);fbc.set(144, 71, 221, 0);fbc.set(145, 67, 218, 3, 0, _fb);fbc.set(145, 68, 217, 2, 0, _fb);fbc.set(145, 68, 221, 2, 0, _fb);fbc.set(145, 69, 220, 0);fbc.set(145, 70, 219, 0);fbc.set(145, 71, 218, 0);fbc.set(142, 68, 219, 2, 0, _fb);fbc.set(142, 70, 217, 0);fbc.set(142, 67, 220, 3, 0, _fb);fbc.set(142, 69, 218, 31, 1, new double[] {0.09999999403953552, 0.0, 0.09999999403953552, 0.8999999761581421, 0.800000011920929, 0.8999999761581421});fbc.set(142, 70, 221, 0);fbc.set(142, 71, 220, 0);fbc.set(143, 67, 219, 3, 0, _fb);fbc.set(143, 68, 220, 2, 0, _fb);fbc.set(143, 69, 217, 0);fbc.set(143, 69, 221, 0);fbc.set(143, 70, 218, 0);fbc.set(143, 71, 219, 0);fbc.set(144, 67, 218, 3, 0, _fb);fbc.set(144, 68, 217, 2, 0, _fb);fbc.set(144, 68, 221, 2, 0, _fb);fbc.set(144, 69, 220, 0);fbc.set(144, 70, 219, 0);fbc.set(144, 71, 218, 0);fbc.set(145, 67, 217, 3, 0, _fb);fbc.set(145, 67, 221, 3, 0, _fb);fbc.set(145, 68, 218, 2, 0, _fb);fbc.set(145, 69, 219, 0);fbc.set(145, 70, 220, 0);fbc.set(145, 71, 217, 0);fbc.set(145, 71, 221, 0);InteractRayTracing rt = new CenteredInteractRayTracing(false, 144, 68, 218); rt.setBlockCache(fbc);TestRayTracing.runCoordinates(rt, new double[]{144.01901074886095, 70.62, 220.1221052415879, 144.07776715103876, 68.99423513239826, 219.0}, true, false, 0.0, false, "ingame");rt.cleanup(); fbc.cleanup();}
|
||||
}
|
||||
|
||||
}
|
||||
|
@ -111,16 +111,16 @@ public class TestRayTracing {
|
||||
doFail("dT < 0 at t = " + StringUtil.fdec3.format(t), coords);
|
||||
}
|
||||
|
||||
// TODO: Check if this check makes sense at all (dT=0 happens during multi-transitions.)l.
|
||||
// TODO: Check if this check makes sense at all (dT=0 happens during multi-transitions).
|
||||
// if (dT == 0.0 && 1.0 - (t + dT) > tol) {
|
||||
// if (!ignEdge(oX, dX) && !ignEdge(oY, dY) && !ignEdge(oZ, dZ)) {
|
||||
// doFail("Premature dT = 0 at t = " + StringUtil.fdec3.format(t), coords);
|
||||
// }
|
||||
// }
|
||||
|
||||
checkOffset(oX, "x");
|
||||
checkOffset(oY, "y");
|
||||
checkOffset(oZ, "z");
|
||||
// checkOffset(oX, "x");
|
||||
// checkOffset(oY, "y");
|
||||
// checkOffset(oZ, "z");
|
||||
|
||||
// TODO: check with last block coordinates
|
||||
if (lbx == blockX && lby == blockY && lbz == blockZ) {
|
||||
@ -143,11 +143,11 @@ public class TestRayTracing {
|
||||
return true;
|
||||
}
|
||||
|
||||
private void checkOffset(double offset, String name) {
|
||||
if (offset < 0.0 || offset > 1.0) {
|
||||
doFail("Bad " + name + "-offset: " + offset, coords);
|
||||
}
|
||||
}
|
||||
// private void checkOffset(double offset, String name) {
|
||||
// if (offset < 0.0 || offset > 1.0) {
|
||||
// doFail("Bad " + name + "-offset: " + offset, coords);
|
||||
// }
|
||||
// }
|
||||
|
||||
@Override
|
||||
public void loop() {
|
||||
@ -193,17 +193,17 @@ public class TestRayTracing {
|
||||
return crt;
|
||||
}
|
||||
|
||||
public static void dump(int blockX, int blockY, int blockZ, double oX, double oY, double oZ, double t, double dT) {
|
||||
public static void dump(int blockX, int blockY, int blockZ, double oX, double oY, double oZ, double t, double dT, boolean isPrimary) {
|
||||
String sdt = StringUtil.fdec3.format(dT);
|
||||
if ("0".equals(sdt) && dT > 0) sdt = "0.X";
|
||||
System.out.println(StringUtil.fdec3.format(t) + " (+" + sdt + "): " + blockX + ", "+blockY + ", " + blockZ + " / " + StringUtil.fdec3.format(oX) + ", " + StringUtil.fdec3.format(oY)+ ", " + StringUtil.fdec3.format(oZ));
|
||||
System.out.println(StringUtil.fdec3.format(t) + " (+" + sdt + "): " + blockX + ", "+blockY + ", " + blockZ + " / " + StringUtil.fdec3.format(oX) + ", " + StringUtil.fdec3.format(oY)+ ", " + StringUtil.fdec3.format(oZ) + (isPrimary ? " (primary)" : ""));
|
||||
}
|
||||
|
||||
public static RayTracing dumpRawRayTracing(final double[] coords) {
|
||||
RayTracing rt = new RayTracing(coords[0], coords[1], coords[2], coords[3], coords[4], coords[5]) {
|
||||
@Override
|
||||
protected boolean step(int blockX, int blockY, int blockZ, double oX, double oY, double oZ, double dT, boolean isPrimary) {
|
||||
dump(blockX, blockY, blockZ, oX, oY, oZ, t, dT);
|
||||
dump(blockX, blockY, blockZ, oX, oY, oZ, t, dT, isPrimary);
|
||||
if (step > maxSteps(dX, dY, dZ)) {
|
||||
System.out.println("[WARNING] Max steps exceeded: " + maxSteps(dX, dY, dZ));
|
||||
return false;
|
||||
|
Loading…
Reference in New Issue
Block a user